ActivityManagerService.java revision 62515beee67307d8859beec521b7baedfa54b2b5
1/* 2 * Copyright (C) 2006-2008 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17package com.android.server.am; 18 19import static android.Manifest.permission.INTERACT_ACROSS_USERS_FULL; 20import static android.content.pm.PackageManager.PERMISSION_GRANTED; 21import static com.android.internal.util.XmlUtils.readBooleanAttribute; 22import static com.android.internal.util.XmlUtils.readIntAttribute; 23import static com.android.internal.util.XmlUtils.readLongAttribute; 24import static com.android.internal.util.XmlUtils.writeBooleanAttribute; 25import static com.android.internal.util.XmlUtils.writeIntAttribute; 26import static com.android.internal.util.XmlUtils.writeLongAttribute; 27import static com.android.server.Watchdog.NATIVE_STACKS_OF_INTEREST; 28import static org.xmlpull.v1.XmlPullParser.END_DOCUMENT; 29import static org.xmlpull.v1.XmlPullParser.START_TAG; 30import static com.android.server.am.ActivityStackSupervisor.HOME_STACK_ID; 31 32import android.Manifest; 33import android.app.AppOpsManager; 34import android.app.IActivityContainer; 35import android.app.IActivityContainerCallback; 36import android.app.IAppTask; 37import android.app.admin.DevicePolicyManager; 38import android.appwidget.AppWidgetManager; 39import android.content.DialogInterface.OnClickListener; 40import android.content.res.Resources; 41import android.graphics.BitmapFactory; 42import android.graphics.Rect; 43import android.os.BatteryStats; 44import android.os.PersistableBundle; 45import android.service.voice.IVoiceInteractionSession; 46import android.util.ArrayMap; 47 48import com.android.internal.R; 49import com.android.internal.annotations.GuardedBy; 50import com.android.internal.app.IAppOpsService; 51import com.android.internal.app.IVoiceInteractor; 52import com.android.internal.app.ProcessMap; 53import com.android.internal.app.ProcessStats; 54import com.android.internal.content.PackageMonitor; 55import com.android.internal.os.BackgroundThread; 56import com.android.internal.os.BatteryStatsImpl; 57import com.android.internal.os.ProcessCpuTracker; 58import com.android.internal.os.TransferPipe; 59import com.android.internal.os.Zygote; 60import com.android.internal.util.FastPrintWriter; 61import com.android.internal.util.FastXmlSerializer; 62import com.android.internal.util.MemInfoReader; 63import com.android.internal.util.Preconditions; 64import com.android.server.AppOpsService; 65import com.android.server.AttributeCache; 66import com.android.server.IntentResolver; 67import com.android.server.LocalServices; 68import com.android.server.ServiceThread; 69import com.android.server.SystemService; 70import com.android.server.SystemServiceManager; 71import com.android.server.Watchdog; 72import com.android.server.am.ActivityStack.ActivityState; 73import com.android.server.firewall.IntentFirewall; 74import com.android.server.pm.UserManagerService; 75import com.android.server.wm.AppTransition; 76import com.android.server.wm.WindowManagerService; 77import com.google.android.collect.Lists; 78import com.google.android.collect.Maps; 79 80import libcore.io.IoUtils; 81 82import org.xmlpull.v1.XmlPullParser; 83import org.xmlpull.v1.XmlPullParserException; 84import org.xmlpull.v1.XmlSerializer; 85 86import android.app.Activity; 87import android.app.ActivityManager; 88import android.app.ActivityManager.RunningTaskInfo; 89import android.app.ActivityManager.StackInfo; 90import android.app.ActivityManagerInternal; 91import android.app.ActivityManagerNative; 92import android.app.ActivityOptions; 93import android.app.ActivityThread; 94import android.app.AlertDialog; 95import android.app.AppGlobals; 96import android.app.ApplicationErrorReport; 97import android.app.Dialog; 98import android.app.IActivityController; 99import android.app.IApplicationThread; 100import android.app.IInstrumentationWatcher; 101import android.app.INotificationManager; 102import android.app.IProcessObserver; 103import android.app.IServiceConnection; 104import android.app.IStopUserCallback; 105import android.app.IUiAutomationConnection; 106import android.app.IUserSwitchObserver; 107import android.app.Instrumentation; 108import android.app.Notification; 109import android.app.NotificationManager; 110import android.app.PendingIntent; 111import android.app.backup.IBackupManager; 112import android.content.ActivityNotFoundException; 113import android.content.BroadcastReceiver; 114import android.content.ClipData; 115import android.content.ComponentCallbacks2; 116import android.content.ComponentName; 117import android.content.ContentProvider; 118import android.content.ContentResolver; 119import android.content.Context; 120import android.content.DialogInterface; 121import android.content.IContentProvider; 122import android.content.IIntentReceiver; 123import android.content.IIntentSender; 124import android.content.Intent; 125import android.content.IntentFilter; 126import android.content.IntentSender; 127import android.content.pm.ActivityInfo; 128import android.content.pm.ApplicationInfo; 129import android.content.pm.ConfigurationInfo; 130import android.content.pm.IPackageDataObserver; 131import android.content.pm.IPackageManager; 132import android.content.pm.InstrumentationInfo; 133import android.content.pm.PackageInfo; 134import android.content.pm.PackageManager; 135import android.content.pm.ParceledListSlice; 136import android.content.pm.UserInfo; 137import android.content.pm.PackageManager.NameNotFoundException; 138import android.content.pm.PathPermission; 139import android.content.pm.ProviderInfo; 140import android.content.pm.ResolveInfo; 141import android.content.pm.ServiceInfo; 142import android.content.res.CompatibilityInfo; 143import android.content.res.Configuration; 144import android.graphics.Bitmap; 145import android.net.Proxy; 146import android.net.ProxyInfo; 147import android.net.Uri; 148import android.os.Binder; 149import android.os.Build; 150import android.os.Bundle; 151import android.os.Debug; 152import android.os.DropBoxManager; 153import android.os.Environment; 154import android.os.FactoryTest; 155import android.os.FileObserver; 156import android.os.FileUtils; 157import android.os.Handler; 158import android.os.IBinder; 159import android.os.IPermissionController; 160import android.os.IRemoteCallback; 161import android.os.IUserManager; 162import android.os.Looper; 163import android.os.Message; 164import android.os.Parcel; 165import android.os.ParcelFileDescriptor; 166import android.os.Process; 167import android.os.RemoteCallbackList; 168import android.os.RemoteException; 169import android.os.SELinux; 170import android.os.ServiceManager; 171import android.os.StrictMode; 172import android.os.SystemClock; 173import android.os.SystemProperties; 174import android.os.UpdateLock; 175import android.os.UserHandle; 176import android.provider.Settings; 177import android.text.Spannable; 178import android.text.SpannableString; 179import android.text.format.DateUtils; 180import android.text.format.Time; 181import android.text.style.DynamicDrawableSpan; 182import android.text.style.ImageSpan; 183import android.util.AtomicFile; 184import android.util.EventLog; 185import android.util.Log; 186import android.util.Pair; 187import android.util.PrintWriterPrinter; 188import android.util.Slog; 189import android.util.SparseArray; 190import android.util.TimeUtils; 191import android.util.Xml; 192import android.view.Gravity; 193import android.view.LayoutInflater; 194import android.view.View; 195import android.view.WindowManager; 196import android.widget.TextView; 197 198import java.io.BufferedInputStream; 199import java.io.BufferedOutputStream; 200import java.io.DataInputStream; 201import java.io.DataOutputStream; 202import java.io.File; 203import java.io.FileDescriptor; 204import java.io.FileInputStream; 205import java.io.FileNotFoundException; 206import java.io.FileOutputStream; 207import java.io.IOException; 208import java.io.InputStreamReader; 209import java.io.PrintWriter; 210import java.io.StringWriter; 211import java.lang.ref.WeakReference; 212import java.util.ArrayList; 213import java.util.Arrays; 214import java.util.Collections; 215import java.util.Comparator; 216import java.util.HashMap; 217import java.util.HashSet; 218import java.util.Iterator; 219import java.util.List; 220import java.util.Locale; 221import java.util.Map; 222import java.util.Set; 223import java.util.concurrent.atomic.AtomicBoolean; 224import java.util.concurrent.atomic.AtomicLong; 225 226public final class ActivityManagerService extends ActivityManagerNative 227 implements Watchdog.Monitor, BatteryStatsImpl.BatteryCallback { 228 private static final String USER_DATA_DIR = "/data/user/"; 229 static final String TAG = "ActivityManager"; 230 static final String TAG_MU = "ActivityManagerServiceMU"; 231 static final boolean DEBUG = false; 232 static final boolean localLOGV = DEBUG; 233 static final boolean DEBUG_BACKUP = localLOGV || false; 234 static final boolean DEBUG_BROADCAST = localLOGV || false; 235 static final boolean DEBUG_BROADCAST_LIGHT = DEBUG_BROADCAST || false; 236 static final boolean DEBUG_BACKGROUND_BROADCAST = DEBUG_BROADCAST || false; 237 static final boolean DEBUG_CLEANUP = localLOGV || false; 238 static final boolean DEBUG_CONFIGURATION = localLOGV || false; 239 static final boolean DEBUG_FOCUS = false; 240 static final boolean DEBUG_IMMERSIVE = localLOGV || false; 241 static final boolean DEBUG_MU = localLOGV || false; 242 static final boolean DEBUG_OOM_ADJ = localLOGV || false; 243 static final boolean DEBUG_LRU = localLOGV || false; 244 static final boolean DEBUG_PAUSE = localLOGV || false; 245 static final boolean DEBUG_POWER = localLOGV || false; 246 static final boolean DEBUG_POWER_QUICK = DEBUG_POWER || false; 247 static final boolean DEBUG_PROCESS_OBSERVERS = localLOGV || false; 248 static final boolean DEBUG_PROCESSES = localLOGV || false; 249 static final boolean DEBUG_PROVIDER = localLOGV || false; 250 static final boolean DEBUG_RESULTS = localLOGV || false; 251 static final boolean DEBUG_SERVICE = localLOGV || false; 252 static final boolean DEBUG_SERVICE_EXECUTING = localLOGV || false; 253 static final boolean DEBUG_STACK = localLOGV || false; 254 static final boolean DEBUG_SWITCH = localLOGV || false; 255 static final boolean DEBUG_TASKS = localLOGV || false; 256 static final boolean DEBUG_THUMBNAILS = localLOGV || false; 257 static final boolean DEBUG_TRANSITION = localLOGV || false; 258 static final boolean DEBUG_URI_PERMISSION = localLOGV || false; 259 static final boolean DEBUG_USER_LEAVING = localLOGV || false; 260 static final boolean DEBUG_VISBILITY = localLOGV || false; 261 static final boolean DEBUG_PSS = localLOGV || false; 262 static final boolean DEBUG_LOCKSCREEN = localLOGV || false; 263 static final boolean VALIDATE_TOKENS = false; 264 static final boolean SHOW_ACTIVITY_START_TIME = true; 265 266 // Control over CPU and battery monitoring. 267 static final long BATTERY_STATS_TIME = 30*60*1000; // write battery stats every 30 minutes. 268 static final boolean MONITOR_CPU_USAGE = true; 269 static final long MONITOR_CPU_MIN_TIME = 5*1000; // don't sample cpu less than every 5 seconds. 270 static final long MONITOR_CPU_MAX_TIME = 0x0fffffff; // wait possibly forever for next cpu sample. 271 static final boolean MONITOR_THREAD_CPU_USAGE = false; 272 273 // The flags that are set for all calls we make to the package manager. 274 static final int STOCK_PM_FLAGS = PackageManager.GET_SHARED_LIBRARY_FILES; 275 276 private static final String SYSTEM_DEBUGGABLE = "ro.debuggable"; 277 278 static final boolean IS_USER_BUILD = "user".equals(Build.TYPE); 279 280 // Maximum number of recent tasks that we can remember. 281 static final int MAX_RECENT_TASKS = ActivityManager.isLowRamDeviceStatic() ? 10 : 200; 282 283 // Amount of time after a call to stopAppSwitches() during which we will 284 // prevent further untrusted switches from happening. 285 static final long APP_SWITCH_DELAY_TIME = 5*1000; 286 287 // How long we wait for a launched process to attach to the activity manager 288 // before we decide it's never going to come up for real. 289 static final int PROC_START_TIMEOUT = 10*1000; 290 291 // How long we wait for a launched process to attach to the activity manager 292 // before we decide it's never going to come up for real, when the process was 293 // started with a wrapper for instrumentation (such as Valgrind) because it 294 // could take much longer than usual. 295 static final int PROC_START_TIMEOUT_WITH_WRAPPER = 1200*1000; 296 297 // How long to wait after going idle before forcing apps to GC. 298 static final int GC_TIMEOUT = 5*1000; 299 300 // The minimum amount of time between successive GC requests for a process. 301 static final int GC_MIN_INTERVAL = 60*1000; 302 303 // The minimum amount of time between successive PSS requests for a process. 304 static final int FULL_PSS_MIN_INTERVAL = 10*60*1000; 305 306 // The minimum amount of time between successive PSS requests for a process 307 // when the request is due to the memory state being lowered. 308 static final int FULL_PSS_LOWERED_INTERVAL = 2*60*1000; 309 310 // The rate at which we check for apps using excessive power -- 15 mins. 311 static final int POWER_CHECK_DELAY = (DEBUG_POWER_QUICK ? 2 : 15) * 60*1000; 312 313 // The minimum sample duration we will allow before deciding we have 314 // enough data on wake locks to start killing things. 315 static final int WAKE_LOCK_MIN_CHECK_DURATION = (DEBUG_POWER_QUICK ? 1 : 5) * 60*1000; 316 317 // The minimum sample duration we will allow before deciding we have 318 // enough data on CPU usage to start killing things. 319 static final int CPU_MIN_CHECK_DURATION = (DEBUG_POWER_QUICK ? 1 : 5) * 60*1000; 320 321 // How long we allow a receiver to run before giving up on it. 322 static final int BROADCAST_FG_TIMEOUT = 10*1000; 323 static final int BROADCAST_BG_TIMEOUT = 60*1000; 324 325 // How long we wait until we timeout on key dispatching. 326 static final int KEY_DISPATCHING_TIMEOUT = 5*1000; 327 328 // How long we wait until we timeout on key dispatching during instrumentation. 329 static final int INSTRUMENTATION_KEY_DISPATCHING_TIMEOUT = 60*1000; 330 331 // Amount of time we wait for observers to handle a user switch before 332 // giving up on them and unfreezing the screen. 333 static final int USER_SWITCH_TIMEOUT = 2*1000; 334 335 // Maximum number of users we allow to be running at a time. 336 static final int MAX_RUNNING_USERS = 3; 337 338 // How long to wait in getAssistContextExtras for the activity and foreground services 339 // to respond with the result. 340 static final int PENDING_ASSIST_EXTRAS_TIMEOUT = 500; 341 342 // Maximum number of persisted Uri grants a package is allowed 343 static final int MAX_PERSISTED_URI_GRANTS = 128; 344 345 static final int MY_PID = Process.myPid(); 346 347 static final String[] EMPTY_STRING_ARRAY = new String[0]; 348 349 // How many bytes to write into the dropbox log before truncating 350 static final int DROPBOX_MAX_SIZE = 256 * 1024; 351 352 /** All system services */ 353 SystemServiceManager mSystemServiceManager; 354 355 /** Run all ActivityStacks through this */ 356 ActivityStackSupervisor mStackSupervisor; 357 358 public IntentFirewall mIntentFirewall; 359 360 // Whether we should show our dialogs (ANR, crash, etc) or just perform their 361 // default actuion automatically. Important for devices without direct input 362 // devices. 363 private boolean mShowDialogs = true; 364 365 /** 366 * Description of a request to start a new activity, which has been held 367 * due to app switches being disabled. 368 */ 369 static class PendingActivityLaunch { 370 final ActivityRecord r; 371 final ActivityRecord sourceRecord; 372 final int startFlags; 373 final ActivityStack stack; 374 375 PendingActivityLaunch(ActivityRecord _r, ActivityRecord _sourceRecord, 376 int _startFlags, ActivityStack _stack) { 377 r = _r; 378 sourceRecord = _sourceRecord; 379 startFlags = _startFlags; 380 stack = _stack; 381 } 382 } 383 384 final ArrayList<PendingActivityLaunch> mPendingActivityLaunches 385 = new ArrayList<PendingActivityLaunch>(); 386 387 BroadcastQueue mFgBroadcastQueue; 388 BroadcastQueue mBgBroadcastQueue; 389 // Convenient for easy iteration over the queues. Foreground is first 390 // so that dispatch of foreground broadcasts gets precedence. 391 final BroadcastQueue[] mBroadcastQueues = new BroadcastQueue[2]; 392 393 BroadcastQueue broadcastQueueForIntent(Intent intent) { 394 final boolean isFg = (intent.getFlags() & Intent.FLAG_RECEIVER_FOREGROUND) != 0; 395 if (DEBUG_BACKGROUND_BROADCAST) { 396 Slog.i(TAG, "Broadcast intent " + intent + " on " 397 + (isFg ? "foreground" : "background") 398 + " queue"); 399 } 400 return (isFg) ? mFgBroadcastQueue : mBgBroadcastQueue; 401 } 402 403 BroadcastRecord broadcastRecordForReceiverLocked(IBinder receiver) { 404 for (BroadcastQueue queue : mBroadcastQueues) { 405 BroadcastRecord r = queue.getMatchingOrderedReceiver(receiver); 406 if (r != null) { 407 return r; 408 } 409 } 410 return null; 411 } 412 413 /** 414 * Activity we have told the window manager to have key focus. 415 */ 416 ActivityRecord mFocusedActivity = null; 417 418 /** 419 * List of intents that were used to start the most recent tasks. 420 */ 421 ArrayList<TaskRecord> mRecentTasks; 422 423 public class PendingAssistExtras extends Binder implements Runnable { 424 public final ActivityRecord activity; 425 public boolean haveResult = false; 426 public Bundle result = null; 427 public PendingAssistExtras(ActivityRecord _activity) { 428 activity = _activity; 429 } 430 @Override 431 public void run() { 432 Slog.w(TAG, "getAssistContextExtras failed: timeout retrieving from " + activity); 433 synchronized (this) { 434 haveResult = true; 435 notifyAll(); 436 } 437 } 438 } 439 440 final ArrayList<PendingAssistExtras> mPendingAssistExtras 441 = new ArrayList<PendingAssistExtras>(); 442 443 /** 444 * Process management. 445 */ 446 final ProcessList mProcessList = new ProcessList(); 447 448 /** 449 * All of the applications we currently have running organized by name. 450 * The keys are strings of the application package name (as 451 * returned by the package manager), and the keys are ApplicationRecord 452 * objects. 453 */ 454 final ProcessMap<ProcessRecord> mProcessNames = new ProcessMap<ProcessRecord>(); 455 456 /** 457 * Tracking long-term execution of processes to look for abuse and other 458 * bad app behavior. 459 */ 460 final ProcessStatsService mProcessStats; 461 462 /** 463 * The currently running isolated processes. 464 */ 465 final SparseArray<ProcessRecord> mIsolatedProcesses = new SparseArray<ProcessRecord>(); 466 467 /** 468 * Counter for assigning isolated process uids, to avoid frequently reusing the 469 * same ones. 470 */ 471 int mNextIsolatedProcessUid = 0; 472 473 /** 474 * The currently running heavy-weight process, if any. 475 */ 476 ProcessRecord mHeavyWeightProcess = null; 477 478 /** 479 * The last time that various processes have crashed. 480 */ 481 final ProcessMap<Long> mProcessCrashTimes = new ProcessMap<Long>(); 482 483 /** 484 * Information about a process that is currently marked as bad. 485 */ 486 static final class BadProcessInfo { 487 BadProcessInfo(long time, String shortMsg, String longMsg, String stack) { 488 this.time = time; 489 this.shortMsg = shortMsg; 490 this.longMsg = longMsg; 491 this.stack = stack; 492 } 493 494 final long time; 495 final String shortMsg; 496 final String longMsg; 497 final String stack; 498 } 499 500 /** 501 * Set of applications that we consider to be bad, and will reject 502 * incoming broadcasts from (which the user has no control over). 503 * Processes are added to this set when they have crashed twice within 504 * a minimum amount of time; they are removed from it when they are 505 * later restarted (hopefully due to some user action). The value is the 506 * time it was added to the list. 507 */ 508 final ProcessMap<BadProcessInfo> mBadProcesses = new ProcessMap<BadProcessInfo>(); 509 510 /** 511 * All of the processes we currently have running organized by pid. 512 * The keys are the pid running the application. 513 * 514 * <p>NOTE: This object is protected by its own lock, NOT the global 515 * activity manager lock! 516 */ 517 final SparseArray<ProcessRecord> mPidsSelfLocked = new SparseArray<ProcessRecord>(); 518 519 /** 520 * All of the processes that have been forced to be foreground. The key 521 * is the pid of the caller who requested it (we hold a death 522 * link on it). 523 */ 524 abstract class ForegroundToken implements IBinder.DeathRecipient { 525 int pid; 526 IBinder token; 527 } 528 final SparseArray<ForegroundToken> mForegroundProcesses = new SparseArray<ForegroundToken>(); 529 530 /** 531 * List of records for processes that someone had tried to start before the 532 * system was ready. We don't start them at that point, but ensure they 533 * are started by the time booting is complete. 534 */ 535 final ArrayList<ProcessRecord> mProcessesOnHold = new ArrayList<ProcessRecord>(); 536 537 /** 538 * List of persistent applications that are in the process 539 * of being started. 540 */ 541 final ArrayList<ProcessRecord> mPersistentStartingProcesses = new ArrayList<ProcessRecord>(); 542 543 /** 544 * Processes that are being forcibly torn down. 545 */ 546 final ArrayList<ProcessRecord> mRemovedProcesses = new ArrayList<ProcessRecord>(); 547 548 /** 549 * List of running applications, sorted by recent usage. 550 * The first entry in the list is the least recently used. 551 */ 552 final ArrayList<ProcessRecord> mLruProcesses = new ArrayList<ProcessRecord>(); 553 554 /** 555 * Where in mLruProcesses that the processes hosting activities start. 556 */ 557 int mLruProcessActivityStart = 0; 558 559 /** 560 * Where in mLruProcesses that the processes hosting services start. 561 * This is after (lower index) than mLruProcessesActivityStart. 562 */ 563 int mLruProcessServiceStart = 0; 564 565 /** 566 * List of processes that should gc as soon as things are idle. 567 */ 568 final ArrayList<ProcessRecord> mProcessesToGc = new ArrayList<ProcessRecord>(); 569 570 /** 571 * Processes we want to collect PSS data from. 572 */ 573 final ArrayList<ProcessRecord> mPendingPssProcesses = new ArrayList<ProcessRecord>(); 574 575 /** 576 * Last time we requested PSS data of all processes. 577 */ 578 long mLastFullPssTime = SystemClock.uptimeMillis(); 579 580 /** 581 * This is the process holding what we currently consider to be 582 * the "home" activity. 583 */ 584 ProcessRecord mHomeProcess; 585 586 /** 587 * This is the process holding the activity the user last visited that 588 * is in a different process from the one they are currently in. 589 */ 590 ProcessRecord mPreviousProcess; 591 592 /** 593 * The time at which the previous process was last visible. 594 */ 595 long mPreviousProcessVisibleTime; 596 597 /** 598 * Which uses have been started, so are allowed to run code. 599 */ 600 final SparseArray<UserStartedState> mStartedUsers = new SparseArray<UserStartedState>(); 601 602 /** 603 * LRU list of history of current users. Most recently current is at the end. 604 */ 605 final ArrayList<Integer> mUserLru = new ArrayList<Integer>(); 606 607 /** 608 * Constant array of the users that are currently started. 609 */ 610 int[] mStartedUserArray = new int[] { 0 }; 611 612 /** 613 * Registered observers of the user switching mechanics. 614 */ 615 final RemoteCallbackList<IUserSwitchObserver> mUserSwitchObservers 616 = new RemoteCallbackList<IUserSwitchObserver>(); 617 618 /** 619 * Currently active user switch. 620 */ 621 Object mCurUserSwitchCallback; 622 623 /** 624 * Packages that the user has asked to have run in screen size 625 * compatibility mode instead of filling the screen. 626 */ 627 final CompatModePackages mCompatModePackages; 628 629 /** 630 * Set of IntentSenderRecord objects that are currently active. 631 */ 632 final HashMap<PendingIntentRecord.Key, WeakReference<PendingIntentRecord>> mIntentSenderRecords 633 = new HashMap<PendingIntentRecord.Key, WeakReference<PendingIntentRecord>>(); 634 635 /** 636 * Fingerprints (hashCode()) of stack traces that we've 637 * already logged DropBox entries for. Guarded by itself. If 638 * something (rogue user app) forces this over 639 * MAX_DUP_SUPPRESSED_STACKS entries, the contents are cleared. 640 */ 641 private final HashSet<Integer> mAlreadyLoggedViolatedStacks = new HashSet<Integer>(); 642 private static final int MAX_DUP_SUPPRESSED_STACKS = 5000; 643 644 /** 645 * Strict Mode background batched logging state. 646 * 647 * The string buffer is guarded by itself, and its lock is also 648 * used to determine if another batched write is already 649 * in-flight. 650 */ 651 private final StringBuilder mStrictModeBuffer = new StringBuilder(); 652 653 /** 654 * Keeps track of all IIntentReceivers that have been registered for 655 * broadcasts. Hash keys are the receiver IBinder, hash value is 656 * a ReceiverList. 657 */ 658 final HashMap<IBinder, ReceiverList> mRegisteredReceivers = 659 new HashMap<IBinder, ReceiverList>(); 660 661 /** 662 * Resolver for broadcast intents to registered receivers. 663 * Holds BroadcastFilter (subclass of IntentFilter). 664 */ 665 final IntentResolver<BroadcastFilter, BroadcastFilter> mReceiverResolver 666 = new IntentResolver<BroadcastFilter, BroadcastFilter>() { 667 @Override 668 protected boolean allowFilterResult( 669 BroadcastFilter filter, List<BroadcastFilter> dest) { 670 IBinder target = filter.receiverList.receiver.asBinder(); 671 for (int i=dest.size()-1; i>=0; i--) { 672 if (dest.get(i).receiverList.receiver.asBinder() == target) { 673 return false; 674 } 675 } 676 return true; 677 } 678 679 @Override 680 protected BroadcastFilter newResult(BroadcastFilter filter, int match, int userId) { 681 if (userId == UserHandle.USER_ALL || filter.owningUserId == UserHandle.USER_ALL 682 || userId == filter.owningUserId) { 683 return super.newResult(filter, match, userId); 684 } 685 return null; 686 } 687 688 @Override 689 protected BroadcastFilter[] newArray(int size) { 690 return new BroadcastFilter[size]; 691 } 692 693 @Override 694 protected boolean isPackageForFilter(String packageName, BroadcastFilter filter) { 695 return packageName.equals(filter.packageName); 696 } 697 }; 698 699 /** 700 * State of all active sticky broadcasts per user. Keys are the action of the 701 * sticky Intent, values are an ArrayList of all broadcasted intents with 702 * that action (which should usually be one). The SparseArray is keyed 703 * by the user ID the sticky is for, and can include UserHandle.USER_ALL 704 * for stickies that are sent to all users. 705 */ 706 final SparseArray<ArrayMap<String, ArrayList<Intent>>> mStickyBroadcasts = 707 new SparseArray<ArrayMap<String, ArrayList<Intent>>>(); 708 709 final ActiveServices mServices; 710 711 /** 712 * Backup/restore process management 713 */ 714 String mBackupAppName = null; 715 BackupRecord mBackupTarget = null; 716 717 final ProviderMap mProviderMap; 718 719 /** 720 * List of content providers who have clients waiting for them. The 721 * application is currently being launched and the provider will be 722 * removed from this list once it is published. 723 */ 724 final ArrayList<ContentProviderRecord> mLaunchingProviders 725 = new ArrayList<ContentProviderRecord>(); 726 727 /** 728 * File storing persisted {@link #mGrantedUriPermissions}. 729 */ 730 private final AtomicFile mGrantFile; 731 732 /** XML constants used in {@link #mGrantFile} */ 733 private static final String TAG_URI_GRANTS = "uri-grants"; 734 private static final String TAG_URI_GRANT = "uri-grant"; 735 private static final String ATTR_USER_HANDLE = "userHandle"; 736 private static final String ATTR_SOURCE_USER_ID = "sourceUserId"; 737 private static final String ATTR_TARGET_USER_ID = "targetUserId"; 738 private static final String ATTR_SOURCE_PKG = "sourcePkg"; 739 private static final String ATTR_TARGET_PKG = "targetPkg"; 740 private static final String ATTR_URI = "uri"; 741 private static final String ATTR_MODE_FLAGS = "modeFlags"; 742 private static final String ATTR_CREATED_TIME = "createdTime"; 743 private static final String ATTR_PREFIX = "prefix"; 744 745 /** 746 * Global set of specific {@link Uri} permissions that have been granted. 747 * This optimized lookup structure maps from {@link UriPermission#targetUid} 748 * to {@link UriPermission#uri} to {@link UriPermission}. 749 */ 750 @GuardedBy("this") 751 private final SparseArray<ArrayMap<GrantUri, UriPermission>> 752 mGrantedUriPermissions = new SparseArray<ArrayMap<GrantUri, UriPermission>>(); 753 754 public static class GrantUri { 755 public final int sourceUserId; 756 public final Uri uri; 757 public boolean prefix; 758 759 public GrantUri(int sourceUserId, Uri uri, boolean prefix) { 760 this.sourceUserId = sourceUserId; 761 this.uri = uri; 762 this.prefix = prefix; 763 } 764 765 @Override 766 public int hashCode() { 767 return toString().hashCode(); 768 } 769 770 @Override 771 public boolean equals(Object o) { 772 if (o instanceof GrantUri) { 773 GrantUri other = (GrantUri) o; 774 return uri.equals(other.uri) && (sourceUserId == other.sourceUserId) 775 && prefix == other.prefix; 776 } 777 return false; 778 } 779 780 @Override 781 public String toString() { 782 String result = Integer.toString(sourceUserId) + " @ " + uri.toString(); 783 if (prefix) result += " [prefix]"; 784 return result; 785 } 786 787 public String toSafeString() { 788 String result = Integer.toString(sourceUserId) + " @ " + uri.toSafeString(); 789 if (prefix) result += " [prefix]"; 790 return result; 791 } 792 793 public static GrantUri resolve(int defaultSourceUserHandle, Uri uri) { 794 return new GrantUri(ContentProvider.getUserIdFromUri(uri, defaultSourceUserHandle), 795 ContentProvider.getUriWithoutUserId(uri), false); 796 } 797 } 798 799 CoreSettingsObserver mCoreSettingsObserver; 800 801 /** 802 * Thread-local storage used to carry caller permissions over through 803 * indirect content-provider access. 804 */ 805 private class Identity { 806 public int pid; 807 public int uid; 808 809 Identity(int _pid, int _uid) { 810 pid = _pid; 811 uid = _uid; 812 } 813 } 814 815 private static final ThreadLocal<Identity> sCallerIdentity = new ThreadLocal<Identity>(); 816 817 /** 818 * All information we have collected about the runtime performance of 819 * any user id that can impact battery performance. 820 */ 821 final BatteryStatsService mBatteryStatsService; 822 823 /** 824 * Information about component usage 825 */ 826 final UsageStatsService mUsageStatsService; 827 828 /** 829 * Information about and control over application operations 830 */ 831 final AppOpsService mAppOpsService; 832 833 /** 834 * Save recent tasks information across reboots. 835 */ 836 final TaskPersister mTaskPersister; 837 838 /** 839 * Current configuration information. HistoryRecord objects are given 840 * a reference to this object to indicate which configuration they are 841 * currently running in, so this object must be kept immutable. 842 */ 843 Configuration mConfiguration = new Configuration(); 844 845 /** 846 * Current sequencing integer of the configuration, for skipping old 847 * configurations. 848 */ 849 int mConfigurationSeq = 0; 850 851 /** 852 * Hardware-reported OpenGLES version. 853 */ 854 final int GL_ES_VERSION; 855 856 /** 857 * List of initialization arguments to pass to all processes when binding applications to them. 858 * For example, references to the commonly used services. 859 */ 860 HashMap<String, IBinder> mAppBindArgs; 861 862 /** 863 * Temporary to avoid allocations. Protected by main lock. 864 */ 865 final StringBuilder mStringBuilder = new StringBuilder(256); 866 867 /** 868 * Used to control how we initialize the service. 869 */ 870 ComponentName mTopComponent; 871 String mTopAction = Intent.ACTION_MAIN; 872 String mTopData; 873 boolean mProcessesReady = false; 874 boolean mSystemReady = false; 875 boolean mBooting = false; 876 boolean mWaitingUpdate = false; 877 boolean mDidUpdate = false; 878 boolean mOnBattery = false; 879 boolean mLaunchWarningShown = false; 880 881 Context mContext; 882 883 int mFactoryTest; 884 885 boolean mCheckedForSetup; 886 887 /** 888 * The time at which we will allow normal application switches again, 889 * after a call to {@link #stopAppSwitches()}. 890 */ 891 long mAppSwitchesAllowedTime; 892 893 /** 894 * This is set to true after the first switch after mAppSwitchesAllowedTime 895 * is set; any switches after that will clear the time. 896 */ 897 boolean mDidAppSwitch; 898 899 /** 900 * Last time (in realtime) at which we checked for power usage. 901 */ 902 long mLastPowerCheckRealtime; 903 904 /** 905 * Last time (in uptime) at which we checked for power usage. 906 */ 907 long mLastPowerCheckUptime; 908 909 /** 910 * Set while we are wanting to sleep, to prevent any 911 * activities from being started/resumed. 912 */ 913 private boolean mSleeping = false; 914 915 /** 916 * Set while we are running a voice interaction. This overrides 917 * sleeping while it is active. 918 */ 919 private boolean mRunningVoice = false; 920 921 /** 922 * State of external calls telling us if the device is asleep. 923 */ 924 private boolean mWentToSleep = false; 925 926 /** 927 * State of external call telling us if the lock screen is shown. 928 */ 929 private boolean mLockScreenShown = false; 930 931 /** 932 * Set if we are shutting down the system, similar to sleeping. 933 */ 934 boolean mShuttingDown = false; 935 936 /** 937 * Current sequence id for oom_adj computation traversal. 938 */ 939 int mAdjSeq = 0; 940 941 /** 942 * Current sequence id for process LRU updating. 943 */ 944 int mLruSeq = 0; 945 946 /** 947 * Keep track of the non-cached/empty process we last found, to help 948 * determine how to distribute cached/empty processes next time. 949 */ 950 int mNumNonCachedProcs = 0; 951 952 /** 953 * Keep track of the number of cached hidden procs, to balance oom adj 954 * distribution between those and empty procs. 955 */ 956 int mNumCachedHiddenProcs = 0; 957 958 /** 959 * Keep track of the number of service processes we last found, to 960 * determine on the next iteration which should be B services. 961 */ 962 int mNumServiceProcs = 0; 963 int mNewNumAServiceProcs = 0; 964 int mNewNumServiceProcs = 0; 965 966 /** 967 * Allow the current computed overall memory level of the system to go down? 968 * This is set to false when we are killing processes for reasons other than 969 * memory management, so that the now smaller process list will not be taken as 970 * an indication that memory is tighter. 971 */ 972 boolean mAllowLowerMemLevel = false; 973 974 /** 975 * The last computed memory level, for holding when we are in a state that 976 * processes are going away for other reasons. 977 */ 978 int mLastMemoryLevel = ProcessStats.ADJ_MEM_FACTOR_NORMAL; 979 980 /** 981 * The last total number of process we have, to determine if changes actually look 982 * like a shrinking number of process due to lower RAM. 983 */ 984 int mLastNumProcesses; 985 986 /** 987 * The uptime of the last time we performed idle maintenance. 988 */ 989 long mLastIdleTime = SystemClock.uptimeMillis(); 990 991 /** 992 * Total time spent with RAM that has been added in the past since the last idle time. 993 */ 994 long mLowRamTimeSinceLastIdle = 0; 995 996 /** 997 * If RAM is currently low, when that horrible situation started. 998 */ 999 long mLowRamStartTime = 0; 1000 1001 /** 1002 * For reporting to battery stats the current top application. 1003 */ 1004 private String mCurResumedPackage = null; 1005 private int mCurResumedUid = -1; 1006 1007 /** 1008 * For reporting to battery stats the apps currently running foreground 1009 * service. The ProcessMap is package/uid tuples; each of these contain 1010 * an array of the currently foreground processes. 1011 */ 1012 final ProcessMap<ArrayList<ProcessRecord>> mForegroundPackages 1013 = new ProcessMap<ArrayList<ProcessRecord>>(); 1014 1015 /** 1016 * This is set if we had to do a delayed dexopt of an app before launching 1017 * it, to increase the ANR timeouts in that case. 1018 */ 1019 boolean mDidDexOpt; 1020 1021 /** 1022 * Set if the systemServer made a call to enterSafeMode. 1023 */ 1024 boolean mSafeMode; 1025 1026 String mDebugApp = null; 1027 boolean mWaitForDebugger = false; 1028 boolean mDebugTransient = false; 1029 String mOrigDebugApp = null; 1030 boolean mOrigWaitForDebugger = false; 1031 boolean mAlwaysFinishActivities = false; 1032 IActivityController mController = null; 1033 String mProfileApp = null; 1034 ProcessRecord mProfileProc = null; 1035 String mProfileFile; 1036 ParcelFileDescriptor mProfileFd; 1037 int mProfileType = 0; 1038 boolean mAutoStopProfiler = false; 1039 String mOpenGlTraceApp = null; 1040 1041 static class ProcessChangeItem { 1042 static final int CHANGE_ACTIVITIES = 1<<0; 1043 static final int CHANGE_PROCESS_STATE = 1<<1; 1044 int changes; 1045 int uid; 1046 int pid; 1047 int processState; 1048 boolean foregroundActivities; 1049 } 1050 1051 final RemoteCallbackList<IProcessObserver> mProcessObservers 1052 = new RemoteCallbackList<IProcessObserver>(); 1053 ProcessChangeItem[] mActiveProcessChanges = new ProcessChangeItem[5]; 1054 1055 final ArrayList<ProcessChangeItem> mPendingProcessChanges 1056 = new ArrayList<ProcessChangeItem>(); 1057 final ArrayList<ProcessChangeItem> mAvailProcessChanges 1058 = new ArrayList<ProcessChangeItem>(); 1059 1060 /** 1061 * Runtime CPU use collection thread. This object's lock is used to 1062 * protect all related state. 1063 */ 1064 final Thread mProcessCpuThread; 1065 1066 /** 1067 * Used to collect process stats when showing not responding dialog. 1068 * Protected by mProcessCpuThread. 1069 */ 1070 final ProcessCpuTracker mProcessCpuTracker = new ProcessCpuTracker( 1071 MONITOR_THREAD_CPU_USAGE); 1072 final AtomicLong mLastCpuTime = new AtomicLong(0); 1073 final AtomicBoolean mProcessCpuMutexFree = new AtomicBoolean(true); 1074 1075 long mLastWriteTime = 0; 1076 1077 /** 1078 * Used to retain an update lock when the foreground activity is in 1079 * immersive mode. 1080 */ 1081 final UpdateLock mUpdateLock = new UpdateLock("immersive"); 1082 1083 /** 1084 * Set to true after the system has finished booting. 1085 */ 1086 boolean mBooted = false; 1087 1088 int mProcessLimit = ProcessList.MAX_CACHED_APPS; 1089 int mProcessLimitOverride = -1; 1090 1091 WindowManagerService mWindowManager; 1092 1093 final ActivityThread mSystemThread; 1094 1095 int mCurrentUserId = 0; 1096 int[] mCurrentProfileIds = new int[] {UserHandle.USER_OWNER}; // Accessed by ActivityStack 1097 private UserManagerService mUserManager; 1098 1099 private final class AppDeathRecipient implements IBinder.DeathRecipient { 1100 final ProcessRecord mApp; 1101 final int mPid; 1102 final IApplicationThread mAppThread; 1103 1104 AppDeathRecipient(ProcessRecord app, int pid, 1105 IApplicationThread thread) { 1106 if (localLOGV) Slog.v( 1107 TAG, "New death recipient " + this 1108 + " for thread " + thread.asBinder()); 1109 mApp = app; 1110 mPid = pid; 1111 mAppThread = thread; 1112 } 1113 1114 @Override 1115 public void binderDied() { 1116 if (localLOGV) Slog.v( 1117 TAG, "Death received in " + this 1118 + " for thread " + mAppThread.asBinder()); 1119 synchronized(ActivityManagerService.this) { 1120 appDiedLocked(mApp, mPid, mAppThread); 1121 } 1122 } 1123 } 1124 1125 static final int SHOW_ERROR_MSG = 1; 1126 static final int SHOW_NOT_RESPONDING_MSG = 2; 1127 static final int SHOW_FACTORY_ERROR_MSG = 3; 1128 static final int UPDATE_CONFIGURATION_MSG = 4; 1129 static final int GC_BACKGROUND_PROCESSES_MSG = 5; 1130 static final int WAIT_FOR_DEBUGGER_MSG = 6; 1131 static final int SERVICE_TIMEOUT_MSG = 12; 1132 static final int UPDATE_TIME_ZONE = 13; 1133 static final int SHOW_UID_ERROR_MSG = 14; 1134 static final int IM_FEELING_LUCKY_MSG = 15; 1135 static final int PROC_START_TIMEOUT_MSG = 20; 1136 static final int DO_PENDING_ACTIVITY_LAUNCHES_MSG = 21; 1137 static final int KILL_APPLICATION_MSG = 22; 1138 static final int FINALIZE_PENDING_INTENT_MSG = 23; 1139 static final int POST_HEAVY_NOTIFICATION_MSG = 24; 1140 static final int CANCEL_HEAVY_NOTIFICATION_MSG = 25; 1141 static final int SHOW_STRICT_MODE_VIOLATION_MSG = 26; 1142 static final int CHECK_EXCESSIVE_WAKE_LOCKS_MSG = 27; 1143 static final int CLEAR_DNS_CACHE_MSG = 28; 1144 static final int UPDATE_HTTP_PROXY_MSG = 29; 1145 static final int SHOW_COMPAT_MODE_DIALOG_MSG = 30; 1146 static final int DISPATCH_PROCESSES_CHANGED = 31; 1147 static final int DISPATCH_PROCESS_DIED = 32; 1148 static final int REPORT_MEM_USAGE_MSG = 33; 1149 static final int REPORT_USER_SWITCH_MSG = 34; 1150 static final int CONTINUE_USER_SWITCH_MSG = 35; 1151 static final int USER_SWITCH_TIMEOUT_MSG = 36; 1152 static final int IMMERSIVE_MODE_LOCK_MSG = 37; 1153 static final int PERSIST_URI_GRANTS_MSG = 38; 1154 static final int REQUEST_ALL_PSS_MSG = 39; 1155 static final int START_PROFILES_MSG = 40; 1156 static final int UPDATE_TIME = 41; 1157 static final int SYSTEM_USER_START_MSG = 42; 1158 static final int SYSTEM_USER_CURRENT_MSG = 43; 1159 1160 static final int FIRST_ACTIVITY_STACK_MSG = 100; 1161 static final int FIRST_BROADCAST_QUEUE_MSG = 200; 1162 static final int FIRST_COMPAT_MODE_MSG = 300; 1163 static final int FIRST_SUPERVISOR_STACK_MSG = 100; 1164 1165 AlertDialog mUidAlert; 1166 CompatModeDialog mCompatModeDialog; 1167 long mLastMemUsageReportTime = 0; 1168 1169 private LockToAppRequestDialog mLockToAppRequest; 1170 1171 /** 1172 * Flag whether the current user is a "monkey", i.e. whether 1173 * the UI is driven by a UI automation tool. 1174 */ 1175 private boolean mUserIsMonkey; 1176 1177 final ServiceThread mHandlerThread; 1178 final MainHandler mHandler; 1179 1180 final class MainHandler extends Handler { 1181 public MainHandler(Looper looper) { 1182 super(looper, null, true); 1183 } 1184 1185 @Override 1186 public void handleMessage(Message msg) { 1187 switch (msg.what) { 1188 case SHOW_ERROR_MSG: { 1189 HashMap<String, Object> data = (HashMap<String, Object>) msg.obj; 1190 boolean showBackground = Settings.Secure.getInt(mContext.getContentResolver(), 1191 Settings.Secure.ANR_SHOW_BACKGROUND, 0) != 0; 1192 synchronized (ActivityManagerService.this) { 1193 ProcessRecord proc = (ProcessRecord)data.get("app"); 1194 AppErrorResult res = (AppErrorResult) data.get("result"); 1195 if (proc != null && proc.crashDialog != null) { 1196 Slog.e(TAG, "App already has crash dialog: " + proc); 1197 if (res != null) { 1198 res.set(0); 1199 } 1200 return; 1201 } 1202 if (!showBackground && UserHandle.getAppId(proc.uid) 1203 >= Process.FIRST_APPLICATION_UID && proc.userId != mCurrentUserId 1204 && proc.pid != MY_PID) { 1205 Slog.w(TAG, "Skipping crash dialog of " + proc + ": background"); 1206 if (res != null) { 1207 res.set(0); 1208 } 1209 return; 1210 } 1211 if (mShowDialogs && !mSleeping && !mShuttingDown) { 1212 Dialog d = new AppErrorDialog(mContext, 1213 ActivityManagerService.this, res, proc); 1214 d.show(); 1215 proc.crashDialog = d; 1216 } else { 1217 // The device is asleep, so just pretend that the user 1218 // saw a crash dialog and hit "force quit". 1219 if (res != null) { 1220 res.set(0); 1221 } 1222 } 1223 } 1224 1225 ensureBootCompleted(); 1226 } break; 1227 case SHOW_NOT_RESPONDING_MSG: { 1228 synchronized (ActivityManagerService.this) { 1229 HashMap<String, Object> data = (HashMap<String, Object>) msg.obj; 1230 ProcessRecord proc = (ProcessRecord)data.get("app"); 1231 if (proc != null && proc.anrDialog != null) { 1232 Slog.e(TAG, "App already has anr dialog: " + proc); 1233 return; 1234 } 1235 1236 Intent intent = new Intent("android.intent.action.ANR"); 1237 if (!mProcessesReady) { 1238 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 1239 | Intent.FLAG_RECEIVER_FOREGROUND); 1240 } 1241 broadcastIntentLocked(null, null, intent, 1242 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 1243 false, false, MY_PID, Process.SYSTEM_UID, 0 /* TODO: Verify */); 1244 1245 if (mShowDialogs) { 1246 Dialog d = new AppNotRespondingDialog(ActivityManagerService.this, 1247 mContext, proc, (ActivityRecord)data.get("activity"), 1248 msg.arg1 != 0); 1249 d.show(); 1250 proc.anrDialog = d; 1251 } else { 1252 // Just kill the app if there is no dialog to be shown. 1253 killAppAtUsersRequest(proc, null); 1254 } 1255 } 1256 1257 ensureBootCompleted(); 1258 } break; 1259 case SHOW_STRICT_MODE_VIOLATION_MSG: { 1260 HashMap<String, Object> data = (HashMap<String, Object>) msg.obj; 1261 synchronized (ActivityManagerService.this) { 1262 ProcessRecord proc = (ProcessRecord) data.get("app"); 1263 if (proc == null) { 1264 Slog.e(TAG, "App not found when showing strict mode dialog."); 1265 break; 1266 } 1267 if (proc.crashDialog != null) { 1268 Slog.e(TAG, "App already has strict mode dialog: " + proc); 1269 return; 1270 } 1271 AppErrorResult res = (AppErrorResult) data.get("result"); 1272 if (mShowDialogs && !mSleeping && !mShuttingDown) { 1273 Dialog d = new StrictModeViolationDialog(mContext, 1274 ActivityManagerService.this, res, proc); 1275 d.show(); 1276 proc.crashDialog = d; 1277 } else { 1278 // The device is asleep, so just pretend that the user 1279 // saw a crash dialog and hit "force quit". 1280 res.set(0); 1281 } 1282 } 1283 ensureBootCompleted(); 1284 } break; 1285 case SHOW_FACTORY_ERROR_MSG: { 1286 Dialog d = new FactoryErrorDialog( 1287 mContext, msg.getData().getCharSequence("msg")); 1288 d.show(); 1289 ensureBootCompleted(); 1290 } break; 1291 case UPDATE_CONFIGURATION_MSG: { 1292 final ContentResolver resolver = mContext.getContentResolver(); 1293 Settings.System.putConfiguration(resolver, (Configuration)msg.obj); 1294 } break; 1295 case GC_BACKGROUND_PROCESSES_MSG: { 1296 synchronized (ActivityManagerService.this) { 1297 performAppGcsIfAppropriateLocked(); 1298 } 1299 } break; 1300 case WAIT_FOR_DEBUGGER_MSG: { 1301 synchronized (ActivityManagerService.this) { 1302 ProcessRecord app = (ProcessRecord)msg.obj; 1303 if (msg.arg1 != 0) { 1304 if (!app.waitedForDebugger) { 1305 Dialog d = new AppWaitingForDebuggerDialog( 1306 ActivityManagerService.this, 1307 mContext, app); 1308 app.waitDialog = d; 1309 app.waitedForDebugger = true; 1310 d.show(); 1311 } 1312 } else { 1313 if (app.waitDialog != null) { 1314 app.waitDialog.dismiss(); 1315 app.waitDialog = null; 1316 } 1317 } 1318 } 1319 } break; 1320 case SERVICE_TIMEOUT_MSG: { 1321 if (mDidDexOpt) { 1322 mDidDexOpt = false; 1323 Message nmsg = mHandler.obtainMessage(SERVICE_TIMEOUT_MSG); 1324 nmsg.obj = msg.obj; 1325 mHandler.sendMessageDelayed(nmsg, ActiveServices.SERVICE_TIMEOUT); 1326 return; 1327 } 1328 mServices.serviceTimeout((ProcessRecord)msg.obj); 1329 } break; 1330 case UPDATE_TIME_ZONE: { 1331 synchronized (ActivityManagerService.this) { 1332 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 1333 ProcessRecord r = mLruProcesses.get(i); 1334 if (r.thread != null) { 1335 try { 1336 r.thread.updateTimeZone(); 1337 } catch (RemoteException ex) { 1338 Slog.w(TAG, "Failed to update time zone for: " + r.info.processName); 1339 } 1340 } 1341 } 1342 } 1343 } break; 1344 case CLEAR_DNS_CACHE_MSG: { 1345 synchronized (ActivityManagerService.this) { 1346 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 1347 ProcessRecord r = mLruProcesses.get(i); 1348 if (r.thread != null) { 1349 try { 1350 r.thread.clearDnsCache(); 1351 } catch (RemoteException ex) { 1352 Slog.w(TAG, "Failed to clear dns cache for: " + r.info.processName); 1353 } 1354 } 1355 } 1356 } 1357 } break; 1358 case UPDATE_HTTP_PROXY_MSG: { 1359 ProxyInfo proxy = (ProxyInfo)msg.obj; 1360 String host = ""; 1361 String port = ""; 1362 String exclList = ""; 1363 Uri pacFileUrl = Uri.EMPTY; 1364 if (proxy != null) { 1365 host = proxy.getHost(); 1366 port = Integer.toString(proxy.getPort()); 1367 exclList = proxy.getExclusionListAsString(); 1368 pacFileUrl = proxy.getPacFileUrl(); 1369 } 1370 synchronized (ActivityManagerService.this) { 1371 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 1372 ProcessRecord r = mLruProcesses.get(i); 1373 if (r.thread != null) { 1374 try { 1375 r.thread.setHttpProxy(host, port, exclList, pacFileUrl); 1376 } catch (RemoteException ex) { 1377 Slog.w(TAG, "Failed to update http proxy for: " + 1378 r.info.processName); 1379 } 1380 } 1381 } 1382 } 1383 } break; 1384 case SHOW_UID_ERROR_MSG: { 1385 String title = "System UIDs Inconsistent"; 1386 String text = "UIDs on the system are inconsistent, you need to wipe your" 1387 + " data partition or your device will be unstable."; 1388 Log.e(TAG, title + ": " + text); 1389 if (mShowDialogs) { 1390 // XXX This is a temporary dialog, no need to localize. 1391 AlertDialog d = new BaseErrorDialog(mContext); 1392 d.getWindow().setType(WindowManager.LayoutParams.TYPE_SYSTEM_ERROR); 1393 d.setCancelable(false); 1394 d.setTitle(title); 1395 d.setMessage(text); 1396 d.setButton(DialogInterface.BUTTON_POSITIVE, "I'm Feeling Lucky", 1397 mHandler.obtainMessage(IM_FEELING_LUCKY_MSG)); 1398 mUidAlert = d; 1399 d.show(); 1400 } 1401 } break; 1402 case IM_FEELING_LUCKY_MSG: { 1403 if (mUidAlert != null) { 1404 mUidAlert.dismiss(); 1405 mUidAlert = null; 1406 } 1407 } break; 1408 case PROC_START_TIMEOUT_MSG: { 1409 if (mDidDexOpt) { 1410 mDidDexOpt = false; 1411 Message nmsg = mHandler.obtainMessage(PROC_START_TIMEOUT_MSG); 1412 nmsg.obj = msg.obj; 1413 mHandler.sendMessageDelayed(nmsg, PROC_START_TIMEOUT); 1414 return; 1415 } 1416 ProcessRecord app = (ProcessRecord)msg.obj; 1417 synchronized (ActivityManagerService.this) { 1418 processStartTimedOutLocked(app); 1419 } 1420 } break; 1421 case DO_PENDING_ACTIVITY_LAUNCHES_MSG: { 1422 synchronized (ActivityManagerService.this) { 1423 doPendingActivityLaunchesLocked(true); 1424 } 1425 } break; 1426 case KILL_APPLICATION_MSG: { 1427 synchronized (ActivityManagerService.this) { 1428 int appid = msg.arg1; 1429 boolean restart = (msg.arg2 == 1); 1430 Bundle bundle = (Bundle)msg.obj; 1431 String pkg = bundle.getString("pkg"); 1432 String reason = bundle.getString("reason"); 1433 forceStopPackageLocked(pkg, appid, restart, false, true, false, 1434 false, UserHandle.USER_ALL, reason); 1435 } 1436 } break; 1437 case FINALIZE_PENDING_INTENT_MSG: { 1438 ((PendingIntentRecord)msg.obj).completeFinalize(); 1439 } break; 1440 case POST_HEAVY_NOTIFICATION_MSG: { 1441 INotificationManager inm = NotificationManager.getService(); 1442 if (inm == null) { 1443 return; 1444 } 1445 1446 ActivityRecord root = (ActivityRecord)msg.obj; 1447 ProcessRecord process = root.app; 1448 if (process == null) { 1449 return; 1450 } 1451 1452 try { 1453 Context context = mContext.createPackageContext(process.info.packageName, 0); 1454 String text = mContext.getString(R.string.heavy_weight_notification, 1455 context.getApplicationInfo().loadLabel(context.getPackageManager())); 1456 Notification notification = new Notification(); 1457 notification.icon = com.android.internal.R.drawable.stat_sys_adb; //context.getApplicationInfo().icon; 1458 notification.when = 0; 1459 notification.flags = Notification.FLAG_ONGOING_EVENT; 1460 notification.tickerText = text; 1461 notification.defaults = 0; // please be quiet 1462 notification.sound = null; 1463 notification.vibrate = null; 1464 notification.setLatestEventInfo(context, text, 1465 mContext.getText(R.string.heavy_weight_notification_detail), 1466 PendingIntent.getActivityAsUser(mContext, 0, root.intent, 1467 PendingIntent.FLAG_CANCEL_CURRENT, null, 1468 new UserHandle(root.userId))); 1469 1470 try { 1471 int[] outId = new int[1]; 1472 inm.enqueueNotificationWithTag("android", "android", null, 1473 R.string.heavy_weight_notification, 1474 notification, outId, root.userId); 1475 } catch (RuntimeException e) { 1476 Slog.w(ActivityManagerService.TAG, 1477 "Error showing notification for heavy-weight app", e); 1478 } catch (RemoteException e) { 1479 } 1480 } catch (NameNotFoundException e) { 1481 Slog.w(TAG, "Unable to create context for heavy notification", e); 1482 } 1483 } break; 1484 case CANCEL_HEAVY_NOTIFICATION_MSG: { 1485 INotificationManager inm = NotificationManager.getService(); 1486 if (inm == null) { 1487 return; 1488 } 1489 try { 1490 inm.cancelNotificationWithTag("android", null, 1491 R.string.heavy_weight_notification, msg.arg1); 1492 } catch (RuntimeException e) { 1493 Slog.w(ActivityManagerService.TAG, 1494 "Error canceling notification for service", e); 1495 } catch (RemoteException e) { 1496 } 1497 } break; 1498 case CHECK_EXCESSIVE_WAKE_LOCKS_MSG: { 1499 synchronized (ActivityManagerService.this) { 1500 checkExcessivePowerUsageLocked(true); 1501 removeMessages(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 1502 Message nmsg = obtainMessage(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 1503 sendMessageDelayed(nmsg, POWER_CHECK_DELAY); 1504 } 1505 } break; 1506 case SHOW_COMPAT_MODE_DIALOG_MSG: { 1507 synchronized (ActivityManagerService.this) { 1508 ActivityRecord ar = (ActivityRecord)msg.obj; 1509 if (mCompatModeDialog != null) { 1510 if (mCompatModeDialog.mAppInfo.packageName.equals( 1511 ar.info.applicationInfo.packageName)) { 1512 return; 1513 } 1514 mCompatModeDialog.dismiss(); 1515 mCompatModeDialog = null; 1516 } 1517 if (ar != null && false) { 1518 if (mCompatModePackages.getPackageAskCompatModeLocked( 1519 ar.packageName)) { 1520 int mode = mCompatModePackages.computeCompatModeLocked( 1521 ar.info.applicationInfo); 1522 if (mode == ActivityManager.COMPAT_MODE_DISABLED 1523 || mode == ActivityManager.COMPAT_MODE_ENABLED) { 1524 mCompatModeDialog = new CompatModeDialog( 1525 ActivityManagerService.this, mContext, 1526 ar.info.applicationInfo); 1527 mCompatModeDialog.show(); 1528 } 1529 } 1530 } 1531 } 1532 break; 1533 } 1534 case DISPATCH_PROCESSES_CHANGED: { 1535 dispatchProcessesChanged(); 1536 break; 1537 } 1538 case DISPATCH_PROCESS_DIED: { 1539 final int pid = msg.arg1; 1540 final int uid = msg.arg2; 1541 dispatchProcessDied(pid, uid); 1542 break; 1543 } 1544 case REPORT_MEM_USAGE_MSG: { 1545 final ArrayList<ProcessMemInfo> memInfos = (ArrayList<ProcessMemInfo>)msg.obj; 1546 Thread thread = new Thread() { 1547 @Override public void run() { 1548 final SparseArray<ProcessMemInfo> infoMap 1549 = new SparseArray<ProcessMemInfo>(memInfos.size()); 1550 for (int i=0, N=memInfos.size(); i<N; i++) { 1551 ProcessMemInfo mi = memInfos.get(i); 1552 infoMap.put(mi.pid, mi); 1553 } 1554 updateCpuStatsNow(); 1555 synchronized (mProcessCpuThread) { 1556 final int N = mProcessCpuTracker.countStats(); 1557 for (int i=0; i<N; i++) { 1558 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(i); 1559 if (st.vsize > 0) { 1560 long pss = Debug.getPss(st.pid, null); 1561 if (pss > 0) { 1562 if (infoMap.indexOfKey(st.pid) < 0) { 1563 ProcessMemInfo mi = new ProcessMemInfo(st.name, st.pid, 1564 ProcessList.NATIVE_ADJ, -1, "native", null); 1565 mi.pss = pss; 1566 memInfos.add(mi); 1567 } 1568 } 1569 } 1570 } 1571 } 1572 1573 long totalPss = 0; 1574 for (int i=0, N=memInfos.size(); i<N; i++) { 1575 ProcessMemInfo mi = memInfos.get(i); 1576 if (mi.pss == 0) { 1577 mi.pss = Debug.getPss(mi.pid, null); 1578 } 1579 totalPss += mi.pss; 1580 } 1581 Collections.sort(memInfos, new Comparator<ProcessMemInfo>() { 1582 @Override public int compare(ProcessMemInfo lhs, ProcessMemInfo rhs) { 1583 if (lhs.oomAdj != rhs.oomAdj) { 1584 return lhs.oomAdj < rhs.oomAdj ? -1 : 1; 1585 } 1586 if (lhs.pss != rhs.pss) { 1587 return lhs.pss < rhs.pss ? 1 : -1; 1588 } 1589 return 0; 1590 } 1591 }); 1592 1593 StringBuilder tag = new StringBuilder(128); 1594 StringBuilder stack = new StringBuilder(128); 1595 tag.append("Low on memory -- "); 1596 appendMemBucket(tag, totalPss, "total", false); 1597 appendMemBucket(stack, totalPss, "total", true); 1598 1599 StringBuilder logBuilder = new StringBuilder(1024); 1600 logBuilder.append("Low on memory:\n"); 1601 1602 boolean firstLine = true; 1603 int lastOomAdj = Integer.MIN_VALUE; 1604 for (int i=0, N=memInfos.size(); i<N; i++) { 1605 ProcessMemInfo mi = memInfos.get(i); 1606 1607 if (mi.oomAdj != ProcessList.NATIVE_ADJ 1608 && (mi.oomAdj < ProcessList.SERVICE_ADJ 1609 || mi.oomAdj == ProcessList.HOME_APP_ADJ 1610 || mi.oomAdj == ProcessList.PREVIOUS_APP_ADJ)) { 1611 if (lastOomAdj != mi.oomAdj) { 1612 lastOomAdj = mi.oomAdj; 1613 if (mi.oomAdj <= ProcessList.FOREGROUND_APP_ADJ) { 1614 tag.append(" / "); 1615 } 1616 if (mi.oomAdj >= ProcessList.FOREGROUND_APP_ADJ) { 1617 if (firstLine) { 1618 stack.append(":"); 1619 firstLine = false; 1620 } 1621 stack.append("\n\t at "); 1622 } else { 1623 stack.append("$"); 1624 } 1625 } else { 1626 tag.append(" "); 1627 stack.append("$"); 1628 } 1629 if (mi.oomAdj <= ProcessList.FOREGROUND_APP_ADJ) { 1630 appendMemBucket(tag, mi.pss, mi.name, false); 1631 } 1632 appendMemBucket(stack, mi.pss, mi.name, true); 1633 if (mi.oomAdj >= ProcessList.FOREGROUND_APP_ADJ 1634 && ((i+1) >= N || memInfos.get(i+1).oomAdj != lastOomAdj)) { 1635 stack.append("("); 1636 for (int k=0; k<DUMP_MEM_OOM_ADJ.length; k++) { 1637 if (DUMP_MEM_OOM_ADJ[k] == mi.oomAdj) { 1638 stack.append(DUMP_MEM_OOM_LABEL[k]); 1639 stack.append(":"); 1640 stack.append(DUMP_MEM_OOM_ADJ[k]); 1641 } 1642 } 1643 stack.append(")"); 1644 } 1645 } 1646 1647 logBuilder.append(" "); 1648 logBuilder.append(ProcessList.makeOomAdjString(mi.oomAdj)); 1649 logBuilder.append(' '); 1650 logBuilder.append(ProcessList.makeProcStateString(mi.procState)); 1651 logBuilder.append(' '); 1652 ProcessList.appendRamKb(logBuilder, mi.pss); 1653 logBuilder.append(" kB: "); 1654 logBuilder.append(mi.name); 1655 logBuilder.append(" ("); 1656 logBuilder.append(mi.pid); 1657 logBuilder.append(") "); 1658 logBuilder.append(mi.adjType); 1659 logBuilder.append('\n'); 1660 if (mi.adjReason != null) { 1661 logBuilder.append(" "); 1662 logBuilder.append(mi.adjReason); 1663 logBuilder.append('\n'); 1664 } 1665 } 1666 1667 logBuilder.append(" "); 1668 ProcessList.appendRamKb(logBuilder, totalPss); 1669 logBuilder.append(" kB: TOTAL\n"); 1670 1671 long[] infos = new long[Debug.MEMINFO_COUNT]; 1672 Debug.getMemInfo(infos); 1673 logBuilder.append(" MemInfo: "); 1674 logBuilder.append(infos[Debug.MEMINFO_SLAB]).append(" kB slab, "); 1675 logBuilder.append(infos[Debug.MEMINFO_SHMEM]).append(" kB shmem, "); 1676 logBuilder.append(infos[Debug.MEMINFO_BUFFERS]).append(" kB buffers, "); 1677 logBuilder.append(infos[Debug.MEMINFO_CACHED]).append(" kB cached, "); 1678 logBuilder.append(infos[Debug.MEMINFO_FREE]).append(" kB free\n"); 1679 if (infos[Debug.MEMINFO_ZRAM_TOTAL] != 0) { 1680 logBuilder.append(" ZRAM: "); 1681 logBuilder.append(infos[Debug.MEMINFO_ZRAM_TOTAL]); 1682 logBuilder.append(" kB RAM, "); 1683 logBuilder.append(infos[Debug.MEMINFO_SWAP_TOTAL]); 1684 logBuilder.append(" kB swap total, "); 1685 logBuilder.append(infos[Debug.MEMINFO_SWAP_FREE]); 1686 logBuilder.append(" kB swap free\n"); 1687 } 1688 Slog.i(TAG, logBuilder.toString()); 1689 1690 StringBuilder dropBuilder = new StringBuilder(1024); 1691 /* 1692 StringWriter oomSw = new StringWriter(); 1693 PrintWriter oomPw = new FastPrintWriter(oomSw, false, 256); 1694 StringWriter catSw = new StringWriter(); 1695 PrintWriter catPw = new FastPrintWriter(catSw, false, 256); 1696 String[] emptyArgs = new String[] { }; 1697 dumpApplicationMemoryUsage(null, oomPw, " ", emptyArgs, true, catPw); 1698 oomPw.flush(); 1699 String oomString = oomSw.toString(); 1700 */ 1701 dropBuilder.append(stack); 1702 dropBuilder.append('\n'); 1703 dropBuilder.append('\n'); 1704 dropBuilder.append(logBuilder); 1705 dropBuilder.append('\n'); 1706 /* 1707 dropBuilder.append(oomString); 1708 dropBuilder.append('\n'); 1709 */ 1710 StringWriter catSw = new StringWriter(); 1711 synchronized (ActivityManagerService.this) { 1712 PrintWriter catPw = new FastPrintWriter(catSw, false, 256); 1713 String[] emptyArgs = new String[] { }; 1714 catPw.println(); 1715 dumpProcessesLocked(null, catPw, emptyArgs, 0, false, null); 1716 catPw.println(); 1717 mServices.dumpServicesLocked(null, catPw, emptyArgs, 0, 1718 false, false, null); 1719 catPw.println(); 1720 dumpActivitiesLocked(null, catPw, emptyArgs, 0, false, false, null); 1721 catPw.flush(); 1722 } 1723 dropBuilder.append(catSw.toString()); 1724 addErrorToDropBox("lowmem", null, "system_server", null, 1725 null, tag.toString(), dropBuilder.toString(), null, null); 1726 //Slog.i(TAG, "Sent to dropbox:"); 1727 //Slog.i(TAG, dropBuilder.toString()); 1728 synchronized (ActivityManagerService.this) { 1729 long now = SystemClock.uptimeMillis(); 1730 if (mLastMemUsageReportTime < now) { 1731 mLastMemUsageReportTime = now; 1732 } 1733 } 1734 } 1735 }; 1736 thread.start(); 1737 break; 1738 } 1739 case REPORT_USER_SWITCH_MSG: { 1740 dispatchUserSwitch((UserStartedState) msg.obj, msg.arg1, msg.arg2); 1741 break; 1742 } 1743 case CONTINUE_USER_SWITCH_MSG: { 1744 continueUserSwitch((UserStartedState) msg.obj, msg.arg1, msg.arg2); 1745 break; 1746 } 1747 case USER_SWITCH_TIMEOUT_MSG: { 1748 timeoutUserSwitch((UserStartedState) msg.obj, msg.arg1, msg.arg2); 1749 break; 1750 } 1751 case IMMERSIVE_MODE_LOCK_MSG: { 1752 final boolean nextState = (msg.arg1 != 0); 1753 if (mUpdateLock.isHeld() != nextState) { 1754 if (DEBUG_IMMERSIVE) { 1755 final ActivityRecord r = (ActivityRecord) msg.obj; 1756 Slog.d(TAG, "Applying new update lock state '" + nextState + "' for " + r); 1757 } 1758 if (nextState) { 1759 mUpdateLock.acquire(); 1760 } else { 1761 mUpdateLock.release(); 1762 } 1763 } 1764 break; 1765 } 1766 case PERSIST_URI_GRANTS_MSG: { 1767 writeGrantedUriPermissions(); 1768 break; 1769 } 1770 case REQUEST_ALL_PSS_MSG: { 1771 requestPssAllProcsLocked(SystemClock.uptimeMillis(), true, false); 1772 break; 1773 } 1774 case START_PROFILES_MSG: { 1775 synchronized (ActivityManagerService.this) { 1776 startProfilesLocked(); 1777 } 1778 break; 1779 } 1780 case UPDATE_TIME: { 1781 synchronized (ActivityManagerService.this) { 1782 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 1783 ProcessRecord r = mLruProcesses.get(i); 1784 if (r.thread != null) { 1785 try { 1786 r.thread.updateTimePrefs(msg.arg1 == 0 ? false : true); 1787 } catch (RemoteException ex) { 1788 Slog.w(TAG, "Failed to update preferences for: " + r.info.processName); 1789 } 1790 } 1791 } 1792 } 1793 break; 1794 } 1795 case SYSTEM_USER_START_MSG: { 1796 mSystemServiceManager.startUser(msg.arg1); 1797 break; 1798 } 1799 case SYSTEM_USER_CURRENT_MSG: { 1800 mSystemServiceManager.switchUser(msg.arg1); 1801 break; 1802 } 1803 } 1804 } 1805 }; 1806 1807 static final int COLLECT_PSS_BG_MSG = 1; 1808 1809 final Handler mBgHandler = new Handler(BackgroundThread.getHandler().getLooper()) { 1810 @Override 1811 public void handleMessage(Message msg) { 1812 switch (msg.what) { 1813 case COLLECT_PSS_BG_MSG: { 1814 int i=0, num=0; 1815 long start = SystemClock.uptimeMillis(); 1816 long[] tmp = new long[1]; 1817 do { 1818 ProcessRecord proc; 1819 int procState; 1820 int pid; 1821 synchronized (ActivityManagerService.this) { 1822 if (i >= mPendingPssProcesses.size()) { 1823 if (DEBUG_PSS) Slog.d(TAG, "Collected PSS of " + num + " of " + i 1824 + " processes in " + (SystemClock.uptimeMillis()-start) + "ms"); 1825 mPendingPssProcesses.clear(); 1826 return; 1827 } 1828 proc = mPendingPssProcesses.get(i); 1829 procState = proc.pssProcState; 1830 if (proc.thread != null && procState == proc.setProcState) { 1831 pid = proc.pid; 1832 } else { 1833 proc = null; 1834 pid = 0; 1835 } 1836 i++; 1837 } 1838 if (proc != null) { 1839 long pss = Debug.getPss(pid, tmp); 1840 synchronized (ActivityManagerService.this) { 1841 if (proc.thread != null && proc.setProcState == procState 1842 && proc.pid == pid) { 1843 num++; 1844 proc.lastPssTime = SystemClock.uptimeMillis(); 1845 proc.baseProcessTracker.addPss(pss, tmp[0], true, proc.pkgList); 1846 if (DEBUG_PSS) Slog.d(TAG, "PSS of " + proc.toShortString() 1847 + ": " + pss + " lastPss=" + proc.lastPss 1848 + " state=" + ProcessList.makeProcStateString(procState)); 1849 if (proc.initialIdlePss == 0) { 1850 proc.initialIdlePss = pss; 1851 } 1852 proc.lastPss = pss; 1853 if (procState >= ActivityManager.PROCESS_STATE_HOME) { 1854 proc.lastCachedPss = pss; 1855 } 1856 } 1857 } 1858 } 1859 } while (true); 1860 } 1861 } 1862 } 1863 }; 1864 1865 /** 1866 * Monitor for package changes and update our internal state. 1867 */ 1868 private final PackageMonitor mPackageMonitor = new PackageMonitor() { 1869 @Override 1870 public void onPackageRemoved(String packageName, int uid) { 1871 // Remove all tasks with activities in the specified package from the list of recent tasks 1872 synchronized (ActivityManagerService.this) { 1873 for (int i = mRecentTasks.size() - 1; i >= 0; i--) { 1874 TaskRecord tr = mRecentTasks.get(i); 1875 ComponentName cn = tr.intent.getComponent(); 1876 if (cn != null && cn.getPackageName().equals(packageName)) { 1877 // If the package name matches, remove the task and kill the process 1878 removeTaskByIdLocked(tr.taskId, ActivityManager.REMOVE_TASK_KILL_PROCESS); 1879 } 1880 } 1881 } 1882 } 1883 1884 @Override 1885 public boolean onPackageChanged(String packageName, int uid, String[] components) { 1886 onPackageModified(packageName); 1887 return true; 1888 } 1889 1890 @Override 1891 public void onPackageModified(String packageName) { 1892 final PackageManager pm = mContext.getPackageManager(); 1893 final ArrayList<Pair<Intent, Integer>> recentTaskIntents = 1894 new ArrayList<Pair<Intent, Integer>>(); 1895 final ArrayList<Integer> tasksToRemove = new ArrayList<Integer>(); 1896 // Copy the list of recent tasks so that we don't hold onto the lock on 1897 // ActivityManagerService for long periods while checking if components exist. 1898 synchronized (ActivityManagerService.this) { 1899 for (int i = mRecentTasks.size() - 1; i >= 0; i--) { 1900 TaskRecord tr = mRecentTasks.get(i); 1901 recentTaskIntents.add(new Pair<Intent, Integer>(tr.intent, tr.taskId)); 1902 } 1903 } 1904 // Check the recent tasks and filter out all tasks with components that no longer exist. 1905 Intent tmpI = new Intent(); 1906 for (int i = recentTaskIntents.size() - 1; i >= 0; i--) { 1907 Pair<Intent, Integer> p = recentTaskIntents.get(i); 1908 ComponentName cn = p.first.getComponent(); 1909 if (cn != null && cn.getPackageName().equals(packageName)) { 1910 try { 1911 // Add the task to the list to remove if the component no longer exists 1912 tmpI.setComponent(cn); 1913 if (pm.queryIntentActivities(tmpI, PackageManager.MATCH_DEFAULT_ONLY).isEmpty()) { 1914 tasksToRemove.add(p.second); 1915 } 1916 } catch (Exception e) {} 1917 } 1918 } 1919 // Prune all the tasks with removed components from the list of recent tasks 1920 synchronized (ActivityManagerService.this) { 1921 for (int i = tasksToRemove.size() - 1; i >= 0; i--) { 1922 // Remove the task but don't kill the process (since other components in that 1923 // package may still be running and in the background) 1924 removeTaskByIdLocked(tasksToRemove.get(i), 0); 1925 } 1926 } 1927 } 1928 1929 @Override 1930 public boolean onHandleForceStop(Intent intent, String[] packages, int uid, boolean doit) { 1931 // Force stop the specified packages 1932 if (packages != null) { 1933 for (String pkg : packages) { 1934 synchronized (ActivityManagerService.this) { 1935 if (forceStopPackageLocked(pkg, -1, false, false, false, false, false, 0, 1936 "finished booting")) { 1937 return true; 1938 } 1939 } 1940 } 1941 } 1942 return false; 1943 } 1944 }; 1945 1946 public void setSystemProcess() { 1947 try { 1948 ServiceManager.addService(Context.ACTIVITY_SERVICE, this, true); 1949 ServiceManager.addService(ProcessStats.SERVICE_NAME, mProcessStats); 1950 ServiceManager.addService("meminfo", new MemBinder(this)); 1951 ServiceManager.addService("gfxinfo", new GraphicsBinder(this)); 1952 ServiceManager.addService("dbinfo", new DbBinder(this)); 1953 if (MONITOR_CPU_USAGE) { 1954 ServiceManager.addService("cpuinfo", new CpuBinder(this)); 1955 } 1956 ServiceManager.addService("permission", new PermissionController(this)); 1957 1958 ApplicationInfo info = mContext.getPackageManager().getApplicationInfo( 1959 "android", STOCK_PM_FLAGS); 1960 mSystemThread.installSystemApplicationInfo(info); 1961 1962 synchronized (this) { 1963 ProcessRecord app = newProcessRecordLocked(info, info.processName, false); 1964 app.persistent = true; 1965 app.pid = MY_PID; 1966 app.maxAdj = ProcessList.SYSTEM_ADJ; 1967 app.makeActive(mSystemThread.getApplicationThread(), mProcessStats); 1968 mProcessNames.put(app.processName, app.uid, app); 1969 synchronized (mPidsSelfLocked) { 1970 mPidsSelfLocked.put(app.pid, app); 1971 } 1972 updateLruProcessLocked(app, false, null); 1973 updateOomAdjLocked(); 1974 } 1975 } catch (PackageManager.NameNotFoundException e) { 1976 throw new RuntimeException( 1977 "Unable to find android system package", e); 1978 } 1979 } 1980 1981 public void setWindowManager(WindowManagerService wm) { 1982 mWindowManager = wm; 1983 mStackSupervisor.setWindowManager(wm); 1984 } 1985 1986 public void startObservingNativeCrashes() { 1987 final NativeCrashListener ncl = new NativeCrashListener(this); 1988 ncl.start(); 1989 } 1990 1991 public IAppOpsService getAppOpsService() { 1992 return mAppOpsService; 1993 } 1994 1995 static class MemBinder extends Binder { 1996 ActivityManagerService mActivityManagerService; 1997 MemBinder(ActivityManagerService activityManagerService) { 1998 mActivityManagerService = activityManagerService; 1999 } 2000 2001 @Override 2002 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 2003 if (mActivityManagerService.checkCallingPermission(android.Manifest.permission.DUMP) 2004 != PackageManager.PERMISSION_GRANTED) { 2005 pw.println("Permission Denial: can't dump meminfo from from pid=" 2006 + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid() 2007 + " without permission " + android.Manifest.permission.DUMP); 2008 return; 2009 } 2010 2011 mActivityManagerService.dumpApplicationMemoryUsage(fd, pw, " ", args, false, null); 2012 } 2013 } 2014 2015 static class GraphicsBinder extends Binder { 2016 ActivityManagerService mActivityManagerService; 2017 GraphicsBinder(ActivityManagerService activityManagerService) { 2018 mActivityManagerService = activityManagerService; 2019 } 2020 2021 @Override 2022 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 2023 if (mActivityManagerService.checkCallingPermission(android.Manifest.permission.DUMP) 2024 != PackageManager.PERMISSION_GRANTED) { 2025 pw.println("Permission Denial: can't dump gfxinfo from from pid=" 2026 + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid() 2027 + " without permission " + android.Manifest.permission.DUMP); 2028 return; 2029 } 2030 2031 mActivityManagerService.dumpGraphicsHardwareUsage(fd, pw, args); 2032 } 2033 } 2034 2035 static class DbBinder extends Binder { 2036 ActivityManagerService mActivityManagerService; 2037 DbBinder(ActivityManagerService activityManagerService) { 2038 mActivityManagerService = activityManagerService; 2039 } 2040 2041 @Override 2042 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 2043 if (mActivityManagerService.checkCallingPermission(android.Manifest.permission.DUMP) 2044 != PackageManager.PERMISSION_GRANTED) { 2045 pw.println("Permission Denial: can't dump dbinfo from from pid=" 2046 + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid() 2047 + " without permission " + android.Manifest.permission.DUMP); 2048 return; 2049 } 2050 2051 mActivityManagerService.dumpDbInfo(fd, pw, args); 2052 } 2053 } 2054 2055 static class CpuBinder extends Binder { 2056 ActivityManagerService mActivityManagerService; 2057 CpuBinder(ActivityManagerService activityManagerService) { 2058 mActivityManagerService = activityManagerService; 2059 } 2060 2061 @Override 2062 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 2063 if (mActivityManagerService.checkCallingPermission(android.Manifest.permission.DUMP) 2064 != PackageManager.PERMISSION_GRANTED) { 2065 pw.println("Permission Denial: can't dump cpuinfo from from pid=" 2066 + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid() 2067 + " without permission " + android.Manifest.permission.DUMP); 2068 return; 2069 } 2070 2071 synchronized (mActivityManagerService.mProcessCpuThread) { 2072 pw.print(mActivityManagerService.mProcessCpuTracker.printCurrentLoad()); 2073 pw.print(mActivityManagerService.mProcessCpuTracker.printCurrentState( 2074 SystemClock.uptimeMillis())); 2075 } 2076 } 2077 } 2078 2079 public static final class Lifecycle extends SystemService { 2080 private final ActivityManagerService mService; 2081 2082 public Lifecycle(Context context) { 2083 super(context); 2084 mService = new ActivityManagerService(context); 2085 } 2086 2087 @Override 2088 public void onStart() { 2089 mService.start(); 2090 } 2091 2092 public ActivityManagerService getService() { 2093 return mService; 2094 } 2095 } 2096 2097 // Note: This method is invoked on the main thread but may need to attach various 2098 // handlers to other threads. So take care to be explicit about the looper. 2099 public ActivityManagerService(Context systemContext) { 2100 mContext = systemContext; 2101 mFactoryTest = FactoryTest.getMode(); 2102 mSystemThread = ActivityThread.currentActivityThread(); 2103 2104 Slog.i(TAG, "Memory class: " + ActivityManager.staticGetMemoryClass()); 2105 2106 mHandlerThread = new ServiceThread(TAG, 2107 android.os.Process.THREAD_PRIORITY_FOREGROUND, false /*allowIo*/); 2108 mHandlerThread.start(); 2109 mHandler = new MainHandler(mHandlerThread.getLooper()); 2110 2111 mFgBroadcastQueue = new BroadcastQueue(this, mHandler, 2112 "foreground", BROADCAST_FG_TIMEOUT, false); 2113 mBgBroadcastQueue = new BroadcastQueue(this, mHandler, 2114 "background", BROADCAST_BG_TIMEOUT, true); 2115 mBroadcastQueues[0] = mFgBroadcastQueue; 2116 mBroadcastQueues[1] = mBgBroadcastQueue; 2117 2118 mServices = new ActiveServices(this); 2119 mProviderMap = new ProviderMap(this); 2120 2121 // TODO: Move creation of battery stats service outside of activity manager service. 2122 File dataDir = Environment.getDataDirectory(); 2123 File systemDir = new File(dataDir, "system"); 2124 systemDir.mkdirs(); 2125 mBatteryStatsService = new BatteryStatsService(new File( 2126 systemDir, "batterystats.bin").toString(), mHandler); 2127 mBatteryStatsService.getActiveStatistics().readLocked(); 2128 mBatteryStatsService.getActiveStatistics().writeAsyncLocked(); 2129 mOnBattery = DEBUG_POWER ? true 2130 : mBatteryStatsService.getActiveStatistics().getIsOnBattery(); 2131 mBatteryStatsService.getActiveStatistics().setCallback(this); 2132 2133 mProcessStats = new ProcessStatsService(this, new File(systemDir, "procstats")); 2134 2135 mUsageStatsService = new UsageStatsService(new File(systemDir, "usagestats").toString()); 2136 mAppOpsService = new AppOpsService(new File(systemDir, "appops.xml"), mHandler); 2137 2138 mGrantFile = new AtomicFile(new File(systemDir, "urigrants.xml")); 2139 2140 // User 0 is the first and only user that runs at boot. 2141 mStartedUsers.put(0, new UserStartedState(new UserHandle(0), true)); 2142 mUserLru.add(Integer.valueOf(0)); 2143 updateStartedUserArrayLocked(); 2144 2145 GL_ES_VERSION = SystemProperties.getInt("ro.opengles.version", 2146 ConfigurationInfo.GL_ES_VERSION_UNDEFINED); 2147 2148 mConfiguration.setToDefaults(); 2149 mConfiguration.setLocale(Locale.getDefault()); 2150 2151 mConfigurationSeq = mConfiguration.seq = 1; 2152 mProcessCpuTracker.init(); 2153 2154 mCompatModePackages = new CompatModePackages(this, systemDir, mHandler); 2155 mIntentFirewall = new IntentFirewall(new IntentFirewallInterface(), mHandler); 2156 mStackSupervisor = new ActivityStackSupervisor(this); 2157 mTaskPersister = new TaskPersister(systemDir, mStackSupervisor); 2158 2159 mProcessCpuThread = new Thread("CpuTracker") { 2160 @Override 2161 public void run() { 2162 while (true) { 2163 try { 2164 try { 2165 synchronized(this) { 2166 final long now = SystemClock.uptimeMillis(); 2167 long nextCpuDelay = (mLastCpuTime.get()+MONITOR_CPU_MAX_TIME)-now; 2168 long nextWriteDelay = (mLastWriteTime+BATTERY_STATS_TIME)-now; 2169 //Slog.i(TAG, "Cpu delay=" + nextCpuDelay 2170 // + ", write delay=" + nextWriteDelay); 2171 if (nextWriteDelay < nextCpuDelay) { 2172 nextCpuDelay = nextWriteDelay; 2173 } 2174 if (nextCpuDelay > 0) { 2175 mProcessCpuMutexFree.set(true); 2176 this.wait(nextCpuDelay); 2177 } 2178 } 2179 } catch (InterruptedException e) { 2180 } 2181 updateCpuStatsNow(); 2182 } catch (Exception e) { 2183 Slog.e(TAG, "Unexpected exception collecting process stats", e); 2184 } 2185 } 2186 } 2187 }; 2188 2189 mLockToAppRequest = new LockToAppRequestDialog(mContext, this); 2190 2191 Watchdog.getInstance().addMonitor(this); 2192 Watchdog.getInstance().addThread(mHandler); 2193 } 2194 2195 public void setSystemServiceManager(SystemServiceManager mgr) { 2196 mSystemServiceManager = mgr; 2197 } 2198 2199 private void start() { 2200 mProcessCpuThread.start(); 2201 2202 mBatteryStatsService.publish(mContext); 2203 mUsageStatsService.publish(mContext); 2204 mAppOpsService.publish(mContext); 2205 Slog.d("AppOps", "AppOpsService published"); 2206 LocalServices.addService(ActivityManagerInternal.class, new LocalService()); 2207 } 2208 2209 public void initPowerManagement() { 2210 mStackSupervisor.initPowerManagement(); 2211 mBatteryStatsService.initPowerManagement(); 2212 } 2213 2214 @Override 2215 public boolean onTransact(int code, Parcel data, Parcel reply, int flags) 2216 throws RemoteException { 2217 if (code == SYSPROPS_TRANSACTION) { 2218 // We need to tell all apps about the system property change. 2219 ArrayList<IBinder> procs = new ArrayList<IBinder>(); 2220 synchronized(this) { 2221 final int NP = mProcessNames.getMap().size(); 2222 for (int ip=0; ip<NP; ip++) { 2223 SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 2224 final int NA = apps.size(); 2225 for (int ia=0; ia<NA; ia++) { 2226 ProcessRecord app = apps.valueAt(ia); 2227 if (app.thread != null) { 2228 procs.add(app.thread.asBinder()); 2229 } 2230 } 2231 } 2232 } 2233 2234 int N = procs.size(); 2235 for (int i=0; i<N; i++) { 2236 Parcel data2 = Parcel.obtain(); 2237 try { 2238 procs.get(i).transact(IBinder.SYSPROPS_TRANSACTION, data2, null, 0); 2239 } catch (RemoteException e) { 2240 } 2241 data2.recycle(); 2242 } 2243 } 2244 try { 2245 return super.onTransact(code, data, reply, flags); 2246 } catch (RuntimeException e) { 2247 // The activity manager only throws security exceptions, so let's 2248 // log all others. 2249 if (!(e instanceof SecurityException)) { 2250 Slog.wtf(TAG, "Activity Manager Crash", e); 2251 } 2252 throw e; 2253 } 2254 } 2255 2256 void updateCpuStats() { 2257 final long now = SystemClock.uptimeMillis(); 2258 if (mLastCpuTime.get() >= now - MONITOR_CPU_MIN_TIME) { 2259 return; 2260 } 2261 if (mProcessCpuMutexFree.compareAndSet(true, false)) { 2262 synchronized (mProcessCpuThread) { 2263 mProcessCpuThread.notify(); 2264 } 2265 } 2266 } 2267 2268 void updateCpuStatsNow() { 2269 synchronized (mProcessCpuThread) { 2270 mProcessCpuMutexFree.set(false); 2271 final long now = SystemClock.uptimeMillis(); 2272 boolean haveNewCpuStats = false; 2273 2274 if (MONITOR_CPU_USAGE && 2275 mLastCpuTime.get() < (now-MONITOR_CPU_MIN_TIME)) { 2276 mLastCpuTime.set(now); 2277 haveNewCpuStats = true; 2278 mProcessCpuTracker.update(); 2279 //Slog.i(TAG, mProcessCpu.printCurrentState()); 2280 //Slog.i(TAG, "Total CPU usage: " 2281 // + mProcessCpu.getTotalCpuPercent() + "%"); 2282 2283 // Slog the cpu usage if the property is set. 2284 if ("true".equals(SystemProperties.get("events.cpu"))) { 2285 int user = mProcessCpuTracker.getLastUserTime(); 2286 int system = mProcessCpuTracker.getLastSystemTime(); 2287 int iowait = mProcessCpuTracker.getLastIoWaitTime(); 2288 int irq = mProcessCpuTracker.getLastIrqTime(); 2289 int softIrq = mProcessCpuTracker.getLastSoftIrqTime(); 2290 int idle = mProcessCpuTracker.getLastIdleTime(); 2291 2292 int total = user + system + iowait + irq + softIrq + idle; 2293 if (total == 0) total = 1; 2294 2295 EventLog.writeEvent(EventLogTags.CPU, 2296 ((user+system+iowait+irq+softIrq) * 100) / total, 2297 (user * 100) / total, 2298 (system * 100) / total, 2299 (iowait * 100) / total, 2300 (irq * 100) / total, 2301 (softIrq * 100) / total); 2302 } 2303 } 2304 2305 long[] cpuSpeedTimes = mProcessCpuTracker.getLastCpuSpeedTimes(); 2306 final BatteryStatsImpl bstats = mBatteryStatsService.getActiveStatistics(); 2307 synchronized(bstats) { 2308 synchronized(mPidsSelfLocked) { 2309 if (haveNewCpuStats) { 2310 if (mOnBattery) { 2311 int perc = bstats.startAddingCpuLocked(); 2312 int totalUTime = 0; 2313 int totalSTime = 0; 2314 final int N = mProcessCpuTracker.countStats(); 2315 for (int i=0; i<N; i++) { 2316 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(i); 2317 if (!st.working) { 2318 continue; 2319 } 2320 ProcessRecord pr = mPidsSelfLocked.get(st.pid); 2321 int otherUTime = (st.rel_utime*perc)/100; 2322 int otherSTime = (st.rel_stime*perc)/100; 2323 totalUTime += otherUTime; 2324 totalSTime += otherSTime; 2325 if (pr != null) { 2326 BatteryStatsImpl.Uid.Proc ps = pr.curProcBatteryStats; 2327 if (ps == null || !ps.isActive()) { 2328 pr.curProcBatteryStats = ps = bstats.getProcessStatsLocked( 2329 pr.info.uid, pr.processName); 2330 } 2331 ps.addCpuTimeLocked(st.rel_utime-otherUTime, 2332 st.rel_stime-otherSTime); 2333 ps.addSpeedStepTimes(cpuSpeedTimes); 2334 pr.curCpuTime += (st.rel_utime+st.rel_stime) * 10; 2335 } else { 2336 BatteryStatsImpl.Uid.Proc ps = st.batteryStats; 2337 if (ps == null || !ps.isActive()) { 2338 st.batteryStats = ps = bstats.getProcessStatsLocked( 2339 bstats.mapUid(st.uid), st.name); 2340 } 2341 ps.addCpuTimeLocked(st.rel_utime-otherUTime, 2342 st.rel_stime-otherSTime); 2343 ps.addSpeedStepTimes(cpuSpeedTimes); 2344 } 2345 } 2346 bstats.finishAddingCpuLocked(perc, totalUTime, 2347 totalSTime, cpuSpeedTimes); 2348 } 2349 } 2350 } 2351 2352 if (mLastWriteTime < (now-BATTERY_STATS_TIME)) { 2353 mLastWriteTime = now; 2354 mBatteryStatsService.getActiveStatistics().writeAsyncLocked(); 2355 } 2356 } 2357 } 2358 } 2359 2360 @Override 2361 public void batteryNeedsCpuUpdate() { 2362 updateCpuStatsNow(); 2363 } 2364 2365 @Override 2366 public void batteryPowerChanged(boolean onBattery) { 2367 // When plugging in, update the CPU stats first before changing 2368 // the plug state. 2369 updateCpuStatsNow(); 2370 synchronized (this) { 2371 synchronized(mPidsSelfLocked) { 2372 mOnBattery = DEBUG_POWER ? true : onBattery; 2373 } 2374 } 2375 } 2376 2377 /** 2378 * Initialize the application bind args. These are passed to each 2379 * process when the bindApplication() IPC is sent to the process. They're 2380 * lazily setup to make sure the services are running when they're asked for. 2381 */ 2382 private HashMap<String, IBinder> getCommonServicesLocked() { 2383 if (mAppBindArgs == null) { 2384 mAppBindArgs = new HashMap<String, IBinder>(); 2385 2386 // Setup the application init args 2387 mAppBindArgs.put("package", ServiceManager.getService("package")); 2388 mAppBindArgs.put("window", ServiceManager.getService("window")); 2389 mAppBindArgs.put(Context.ALARM_SERVICE, 2390 ServiceManager.getService(Context.ALARM_SERVICE)); 2391 } 2392 return mAppBindArgs; 2393 } 2394 2395 final void setFocusedActivityLocked(ActivityRecord r) { 2396 if (mFocusedActivity != r) { 2397 if (DEBUG_FOCUS) Slog.d(TAG, "setFocusedActivityLocked: r=" + r); 2398 mFocusedActivity = r; 2399 if (r.task != null && r.task.voiceInteractor != null) { 2400 startRunningVoiceLocked(); 2401 } else { 2402 finishRunningVoiceLocked(); 2403 } 2404 mStackSupervisor.setFocusedStack(r); 2405 if (r != null) { 2406 mWindowManager.setFocusedApp(r.appToken, true); 2407 } 2408 applyUpdateLockStateLocked(r); 2409 } 2410 } 2411 2412 final void clearFocusedActivity(ActivityRecord r) { 2413 if (mFocusedActivity == r) { 2414 mFocusedActivity = null; 2415 } 2416 } 2417 2418 @Override 2419 public void setFocusedStack(int stackId) { 2420 if (DEBUG_FOCUS) Slog.d(TAG, "setFocusedStack: stackId=" + stackId); 2421 synchronized (ActivityManagerService.this) { 2422 ActivityStack stack = mStackSupervisor.getStack(stackId); 2423 if (stack != null) { 2424 ActivityRecord r = stack.topRunningActivityLocked(null); 2425 if (r != null) { 2426 setFocusedActivityLocked(r); 2427 } 2428 } 2429 } 2430 } 2431 2432 @Override 2433 public void notifyActivityDrawn(IBinder token) { 2434 if (DEBUG_VISBILITY) Slog.d(TAG, "notifyActivityDrawn: token=" + token); 2435 synchronized (this) { 2436 ActivityRecord r= mStackSupervisor.isInAnyStackLocked(token); 2437 if (r != null) { 2438 r.task.stack.notifyActivityDrawnLocked(r); 2439 } 2440 } 2441 } 2442 2443 final void applyUpdateLockStateLocked(ActivityRecord r) { 2444 // Modifications to the UpdateLock state are done on our handler, outside 2445 // the activity manager's locks. The new state is determined based on the 2446 // state *now* of the relevant activity record. The object is passed to 2447 // the handler solely for logging detail, not to be consulted/modified. 2448 final boolean nextState = r != null && r.immersive; 2449 mHandler.sendMessage( 2450 mHandler.obtainMessage(IMMERSIVE_MODE_LOCK_MSG, (nextState) ? 1 : 0, 0, r)); 2451 } 2452 2453 final void showAskCompatModeDialogLocked(ActivityRecord r) { 2454 Message msg = Message.obtain(); 2455 msg.what = SHOW_COMPAT_MODE_DIALOG_MSG; 2456 msg.obj = r.task.askedCompatMode ? null : r; 2457 mHandler.sendMessage(msg); 2458 } 2459 2460 private final int updateLruProcessInternalLocked(ProcessRecord app, long now, int index, 2461 String what, Object obj, ProcessRecord srcApp) { 2462 app.lastActivityTime = now; 2463 2464 if (app.activities.size() > 0) { 2465 // Don't want to touch dependent processes that are hosting activities. 2466 return index; 2467 } 2468 2469 int lrui = mLruProcesses.lastIndexOf(app); 2470 if (lrui < 0) { 2471 Slog.wtf(TAG, "Adding dependent process " + app + " not on LRU list: " 2472 + what + " " + obj + " from " + srcApp); 2473 return index; 2474 } 2475 2476 if (lrui >= index) { 2477 // Don't want to cause this to move dependent processes *back* in the 2478 // list as if they were less frequently used. 2479 return index; 2480 } 2481 2482 if (lrui >= mLruProcessActivityStart) { 2483 // Don't want to touch dependent processes that are hosting activities. 2484 return index; 2485 } 2486 2487 mLruProcesses.remove(lrui); 2488 if (index > 0) { 2489 index--; 2490 } 2491 if (DEBUG_LRU) Slog.d(TAG, "Moving dep from " + lrui + " to " + index 2492 + " in LRU list: " + app); 2493 mLruProcesses.add(index, app); 2494 return index; 2495 } 2496 2497 final void removeLruProcessLocked(ProcessRecord app) { 2498 int lrui = mLruProcesses.lastIndexOf(app); 2499 if (lrui >= 0) { 2500 if (lrui <= mLruProcessActivityStart) { 2501 mLruProcessActivityStart--; 2502 } 2503 if (lrui <= mLruProcessServiceStart) { 2504 mLruProcessServiceStart--; 2505 } 2506 mLruProcesses.remove(lrui); 2507 } 2508 } 2509 2510 final void updateLruProcessLocked(ProcessRecord app, boolean activityChange, 2511 ProcessRecord client) { 2512 final boolean hasActivity = app.activities.size() > 0 || app.hasClientActivities 2513 || app.treatLikeActivity; 2514 final boolean hasService = false; // not impl yet. app.services.size() > 0; 2515 if (!activityChange && hasActivity) { 2516 // The process has activities, so we are only allowing activity-based adjustments 2517 // to move it. It should be kept in the front of the list with other 2518 // processes that have activities, and we don't want those to change their 2519 // order except due to activity operations. 2520 return; 2521 } 2522 2523 mLruSeq++; 2524 final long now = SystemClock.uptimeMillis(); 2525 app.lastActivityTime = now; 2526 2527 // First a quick reject: if the app is already at the position we will 2528 // put it, then there is nothing to do. 2529 if (hasActivity) { 2530 final int N = mLruProcesses.size(); 2531 if (N > 0 && mLruProcesses.get(N-1) == app) { 2532 if (DEBUG_LRU) Slog.d(TAG, "Not moving, already top activity: " + app); 2533 return; 2534 } 2535 } else { 2536 if (mLruProcessServiceStart > 0 2537 && mLruProcesses.get(mLruProcessServiceStart-1) == app) { 2538 if (DEBUG_LRU) Slog.d(TAG, "Not moving, already top other: " + app); 2539 return; 2540 } 2541 } 2542 2543 int lrui = mLruProcesses.lastIndexOf(app); 2544 2545 if (app.persistent && lrui >= 0) { 2546 // We don't care about the position of persistent processes, as long as 2547 // they are in the list. 2548 if (DEBUG_LRU) Slog.d(TAG, "Not moving, persistent: " + app); 2549 return; 2550 } 2551 2552 /* In progress: compute new position first, so we can avoid doing work 2553 if the process is not actually going to move. Not yet working. 2554 int addIndex; 2555 int nextIndex; 2556 boolean inActivity = false, inService = false; 2557 if (hasActivity) { 2558 // Process has activities, put it at the very tipsy-top. 2559 addIndex = mLruProcesses.size(); 2560 nextIndex = mLruProcessServiceStart; 2561 inActivity = true; 2562 } else if (hasService) { 2563 // Process has services, put it at the top of the service list. 2564 addIndex = mLruProcessActivityStart; 2565 nextIndex = mLruProcessServiceStart; 2566 inActivity = true; 2567 inService = true; 2568 } else { 2569 // Process not otherwise of interest, it goes to the top of the non-service area. 2570 addIndex = mLruProcessServiceStart; 2571 if (client != null) { 2572 int clientIndex = mLruProcesses.lastIndexOf(client); 2573 if (clientIndex < 0) Slog.d(TAG, "Unknown client " + client + " when updating " 2574 + app); 2575 if (clientIndex >= 0 && addIndex > clientIndex) { 2576 addIndex = clientIndex; 2577 } 2578 } 2579 nextIndex = addIndex > 0 ? addIndex-1 : addIndex; 2580 } 2581 2582 Slog.d(TAG, "Update LRU at " + lrui + " to " + addIndex + " (act=" 2583 + mLruProcessActivityStart + "): " + app); 2584 */ 2585 2586 if (lrui >= 0) { 2587 if (lrui < mLruProcessActivityStart) { 2588 mLruProcessActivityStart--; 2589 } 2590 if (lrui < mLruProcessServiceStart) { 2591 mLruProcessServiceStart--; 2592 } 2593 /* 2594 if (addIndex > lrui) { 2595 addIndex--; 2596 } 2597 if (nextIndex > lrui) { 2598 nextIndex--; 2599 } 2600 */ 2601 mLruProcesses.remove(lrui); 2602 } 2603 2604 /* 2605 mLruProcesses.add(addIndex, app); 2606 if (inActivity) { 2607 mLruProcessActivityStart++; 2608 } 2609 if (inService) { 2610 mLruProcessActivityStart++; 2611 } 2612 */ 2613 2614 int nextIndex; 2615 if (hasActivity) { 2616 final int N = mLruProcesses.size(); 2617 if (app.activities.size() == 0 && mLruProcessActivityStart < (N-1)) { 2618 // Process doesn't have activities, but has clients with 2619 // activities... move it up, but one below the top (the top 2620 // should always have a real activity). 2621 if (DEBUG_LRU) Slog.d(TAG, "Adding to second-top of LRU activity list: " + app); 2622 mLruProcesses.add(N-1, app); 2623 // To keep it from spamming the LRU list (by making a bunch of clients), 2624 // we will push down any other entries owned by the app. 2625 final int uid = app.info.uid; 2626 for (int i=N-2; i>mLruProcessActivityStart; i--) { 2627 ProcessRecord subProc = mLruProcesses.get(i); 2628 if (subProc.info.uid == uid) { 2629 // We want to push this one down the list. If the process after 2630 // it is for the same uid, however, don't do so, because we don't 2631 // want them internally to be re-ordered. 2632 if (mLruProcesses.get(i-1).info.uid != uid) { 2633 if (DEBUG_LRU) Slog.d(TAG, "Pushing uid " + uid + " swapping at " + i 2634 + ": " + mLruProcesses.get(i) + " : " + mLruProcesses.get(i-1)); 2635 ProcessRecord tmp = mLruProcesses.get(i); 2636 mLruProcesses.set(i, mLruProcesses.get(i-1)); 2637 mLruProcesses.set(i-1, tmp); 2638 i--; 2639 } 2640 } else { 2641 // A gap, we can stop here. 2642 break; 2643 } 2644 } 2645 } else { 2646 // Process has activities, put it at the very tipsy-top. 2647 if (DEBUG_LRU) Slog.d(TAG, "Adding to top of LRU activity list: " + app); 2648 mLruProcesses.add(app); 2649 } 2650 nextIndex = mLruProcessServiceStart; 2651 } else if (hasService) { 2652 // Process has services, put it at the top of the service list. 2653 if (DEBUG_LRU) Slog.d(TAG, "Adding to top of LRU service list: " + app); 2654 mLruProcesses.add(mLruProcessActivityStart, app); 2655 nextIndex = mLruProcessServiceStart; 2656 mLruProcessActivityStart++; 2657 } else { 2658 // Process not otherwise of interest, it goes to the top of the non-service area. 2659 int index = mLruProcessServiceStart; 2660 if (client != null) { 2661 // If there is a client, don't allow the process to be moved up higher 2662 // in the list than that client. 2663 int clientIndex = mLruProcesses.lastIndexOf(client); 2664 if (DEBUG_LRU && clientIndex < 0) Slog.d(TAG, "Unknown client " + client 2665 + " when updating " + app); 2666 if (clientIndex <= lrui) { 2667 // Don't allow the client index restriction to push it down farther in the 2668 // list than it already is. 2669 clientIndex = lrui; 2670 } 2671 if (clientIndex >= 0 && index > clientIndex) { 2672 index = clientIndex; 2673 } 2674 } 2675 if (DEBUG_LRU) Slog.d(TAG, "Adding at " + index + " of LRU list: " + app); 2676 mLruProcesses.add(index, app); 2677 nextIndex = index-1; 2678 mLruProcessActivityStart++; 2679 mLruProcessServiceStart++; 2680 } 2681 2682 // If the app is currently using a content provider or service, 2683 // bump those processes as well. 2684 for (int j=app.connections.size()-1; j>=0; j--) { 2685 ConnectionRecord cr = app.connections.valueAt(j); 2686 if (cr.binding != null && !cr.serviceDead && cr.binding.service != null 2687 && cr.binding.service.app != null 2688 && cr.binding.service.app.lruSeq != mLruSeq 2689 && !cr.binding.service.app.persistent) { 2690 nextIndex = updateLruProcessInternalLocked(cr.binding.service.app, now, nextIndex, 2691 "service connection", cr, app); 2692 } 2693 } 2694 for (int j=app.conProviders.size()-1; j>=0; j--) { 2695 ContentProviderRecord cpr = app.conProviders.get(j).provider; 2696 if (cpr.proc != null && cpr.proc.lruSeq != mLruSeq && !cpr.proc.persistent) { 2697 nextIndex = updateLruProcessInternalLocked(cpr.proc, now, nextIndex, 2698 "provider reference", cpr, app); 2699 } 2700 } 2701 } 2702 2703 final ProcessRecord getProcessRecordLocked(String processName, int uid, boolean keepIfLarge) { 2704 if (uid == Process.SYSTEM_UID) { 2705 // The system gets to run in any process. If there are multiple 2706 // processes with the same uid, just pick the first (this 2707 // should never happen). 2708 SparseArray<ProcessRecord> procs = mProcessNames.getMap().get(processName); 2709 if (procs == null) return null; 2710 final int N = procs.size(); 2711 for (int i = 0; i < N; i++) { 2712 if (UserHandle.isSameUser(procs.keyAt(i), uid)) return procs.valueAt(i); 2713 } 2714 } 2715 ProcessRecord proc = mProcessNames.get(processName, uid); 2716 if (false && proc != null && !keepIfLarge 2717 && proc.setProcState >= ActivityManager.PROCESS_STATE_CACHED_EMPTY 2718 && proc.lastCachedPss >= 4000) { 2719 // Turn this condition on to cause killing to happen regularly, for testing. 2720 if (proc.baseProcessTracker != null) { 2721 proc.baseProcessTracker.reportCachedKill(proc.pkgList, proc.lastCachedPss); 2722 } 2723 killUnneededProcessLocked(proc, Long.toString(proc.lastCachedPss) 2724 + "k from cached"); 2725 } else if (proc != null && !keepIfLarge 2726 && mLastMemoryLevel > ProcessStats.ADJ_MEM_FACTOR_NORMAL 2727 && proc.setProcState >= ActivityManager.PROCESS_STATE_CACHED_EMPTY) { 2728 if (DEBUG_PSS) Slog.d(TAG, "May not keep " + proc + ": pss=" + proc.lastCachedPss); 2729 if (proc.lastCachedPss >= mProcessList.getCachedRestoreThresholdKb()) { 2730 if (proc.baseProcessTracker != null) { 2731 proc.baseProcessTracker.reportCachedKill(proc.pkgList, proc.lastCachedPss); 2732 } 2733 killUnneededProcessLocked(proc, Long.toString(proc.lastCachedPss) 2734 + "k from cached"); 2735 } 2736 } 2737 return proc; 2738 } 2739 2740 void ensurePackageDexOpt(String packageName) { 2741 IPackageManager pm = AppGlobals.getPackageManager(); 2742 try { 2743 if (pm.performDexOpt(packageName)) { 2744 mDidDexOpt = true; 2745 } 2746 } catch (RemoteException e) { 2747 } 2748 } 2749 2750 boolean isNextTransitionForward() { 2751 int transit = mWindowManager.getPendingAppTransition(); 2752 return transit == AppTransition.TRANSIT_ACTIVITY_OPEN 2753 || transit == AppTransition.TRANSIT_TASK_OPEN 2754 || transit == AppTransition.TRANSIT_TASK_TO_FRONT; 2755 } 2756 2757 final ProcessRecord startProcessLocked(String processName, 2758 ApplicationInfo info, boolean knownToBeDead, int intentFlags, 2759 String hostingType, ComponentName hostingName, boolean allowWhileBooting, 2760 boolean isolated, boolean keepIfLarge) { 2761 ProcessRecord app; 2762 if (!isolated) { 2763 app = getProcessRecordLocked(processName, info.uid, keepIfLarge); 2764 } else { 2765 // If this is an isolated process, it can't re-use an existing process. 2766 app = null; 2767 } 2768 // We don't have to do anything more if: 2769 // (1) There is an existing application record; and 2770 // (2) The caller doesn't think it is dead, OR there is no thread 2771 // object attached to it so we know it couldn't have crashed; and 2772 // (3) There is a pid assigned to it, so it is either starting or 2773 // already running. 2774 if (DEBUG_PROCESSES) Slog.v(TAG, "startProcess: name=" + processName 2775 + " app=" + app + " knownToBeDead=" + knownToBeDead 2776 + " thread=" + (app != null ? app.thread : null) 2777 + " pid=" + (app != null ? app.pid : -1)); 2778 if (app != null && app.pid > 0) { 2779 if (!knownToBeDead || app.thread == null) { 2780 // We already have the app running, or are waiting for it to 2781 // come up (we have a pid but not yet its thread), so keep it. 2782 if (DEBUG_PROCESSES) Slog.v(TAG, "App already running: " + app); 2783 // If this is a new package in the process, add the package to the list 2784 app.addPackage(info.packageName, mProcessStats); 2785 return app; 2786 } 2787 2788 // An application record is attached to a previous process, 2789 // clean it up now. 2790 if (DEBUG_PROCESSES || DEBUG_CLEANUP) Slog.v(TAG, "App died: " + app); 2791 handleAppDiedLocked(app, true, true); 2792 } 2793 2794 String hostingNameStr = hostingName != null 2795 ? hostingName.flattenToShortString() : null; 2796 2797 if (!isolated) { 2798 if ((intentFlags&Intent.FLAG_FROM_BACKGROUND) != 0) { 2799 // If we are in the background, then check to see if this process 2800 // is bad. If so, we will just silently fail. 2801 if (mBadProcesses.get(info.processName, info.uid) != null) { 2802 if (DEBUG_PROCESSES) Slog.v(TAG, "Bad process: " + info.uid 2803 + "/" + info.processName); 2804 return null; 2805 } 2806 } else { 2807 // When the user is explicitly starting a process, then clear its 2808 // crash count so that we won't make it bad until they see at 2809 // least one crash dialog again, and make the process good again 2810 // if it had been bad. 2811 if (DEBUG_PROCESSES) Slog.v(TAG, "Clearing bad process: " + info.uid 2812 + "/" + info.processName); 2813 mProcessCrashTimes.remove(info.processName, info.uid); 2814 if (mBadProcesses.get(info.processName, info.uid) != null) { 2815 EventLog.writeEvent(EventLogTags.AM_PROC_GOOD, 2816 UserHandle.getUserId(info.uid), info.uid, 2817 info.processName); 2818 mBadProcesses.remove(info.processName, info.uid); 2819 if (app != null) { 2820 app.bad = false; 2821 } 2822 } 2823 } 2824 } 2825 2826 if (app == null) { 2827 app = newProcessRecordLocked(info, processName, isolated); 2828 if (app == null) { 2829 Slog.w(TAG, "Failed making new process record for " 2830 + processName + "/" + info.uid + " isolated=" + isolated); 2831 return null; 2832 } 2833 mProcessNames.put(processName, app.uid, app); 2834 if (isolated) { 2835 mIsolatedProcesses.put(app.uid, app); 2836 } 2837 } else { 2838 // If this is a new package in the process, add the package to the list 2839 app.addPackage(info.packageName, mProcessStats); 2840 } 2841 2842 // If the system is not ready yet, then hold off on starting this 2843 // process until it is. 2844 if (!mProcessesReady 2845 && !isAllowedWhileBooting(info) 2846 && !allowWhileBooting) { 2847 if (!mProcessesOnHold.contains(app)) { 2848 mProcessesOnHold.add(app); 2849 } 2850 if (DEBUG_PROCESSES) Slog.v(TAG, "System not ready, putting on hold: " + app); 2851 return app; 2852 } 2853 2854 startProcessLocked(app, hostingType, hostingNameStr, null /* ABI override */); 2855 return (app.pid != 0) ? app : null; 2856 } 2857 2858 boolean isAllowedWhileBooting(ApplicationInfo ai) { 2859 return (ai.flags&ApplicationInfo.FLAG_PERSISTENT) != 0; 2860 } 2861 2862 private final void startProcessLocked(ProcessRecord app, 2863 String hostingType, String hostingNameStr, String abiOverride) { 2864 if (app.pid > 0 && app.pid != MY_PID) { 2865 synchronized (mPidsSelfLocked) { 2866 mPidsSelfLocked.remove(app.pid); 2867 mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app); 2868 } 2869 app.setPid(0); 2870 } 2871 2872 if (DEBUG_PROCESSES && mProcessesOnHold.contains(app)) Slog.v(TAG, 2873 "startProcessLocked removing on hold: " + app); 2874 mProcessesOnHold.remove(app); 2875 2876 updateCpuStats(); 2877 2878 try { 2879 int uid = app.uid; 2880 2881 int[] gids = null; 2882 int mountExternal = Zygote.MOUNT_EXTERNAL_NONE; 2883 if (!app.isolated) { 2884 int[] permGids = null; 2885 try { 2886 final PackageManager pm = mContext.getPackageManager(); 2887 permGids = pm.getPackageGids(app.info.packageName); 2888 2889 if (Environment.isExternalStorageEmulated()) { 2890 if (pm.checkPermission( 2891 android.Manifest.permission.ACCESS_ALL_EXTERNAL_STORAGE, 2892 app.info.packageName) == PERMISSION_GRANTED) { 2893 mountExternal = Zygote.MOUNT_EXTERNAL_MULTIUSER_ALL; 2894 } else { 2895 mountExternal = Zygote.MOUNT_EXTERNAL_MULTIUSER; 2896 } 2897 } 2898 } catch (PackageManager.NameNotFoundException e) { 2899 Slog.w(TAG, "Unable to retrieve gids", e); 2900 } 2901 2902 /* 2903 * Add shared application and profile GIDs so applications can share some 2904 * resources like shared libraries and access user-wide resources 2905 */ 2906 if (permGids == null) { 2907 gids = new int[2]; 2908 } else { 2909 gids = new int[permGids.length + 2]; 2910 System.arraycopy(permGids, 0, gids, 2, permGids.length); 2911 } 2912 gids[0] = UserHandle.getSharedAppGid(UserHandle.getAppId(uid)); 2913 gids[1] = UserHandle.getUserGid(UserHandle.getUserId(uid)); 2914 } 2915 if (mFactoryTest != FactoryTest.FACTORY_TEST_OFF) { 2916 if (mFactoryTest == FactoryTest.FACTORY_TEST_LOW_LEVEL 2917 && mTopComponent != null 2918 && app.processName.equals(mTopComponent.getPackageName())) { 2919 uid = 0; 2920 } 2921 if (mFactoryTest == FactoryTest.FACTORY_TEST_HIGH_LEVEL 2922 && (app.info.flags&ApplicationInfo.FLAG_FACTORY_TEST) != 0) { 2923 uid = 0; 2924 } 2925 } 2926 int debugFlags = 0; 2927 if ((app.info.flags & ApplicationInfo.FLAG_DEBUGGABLE) != 0) { 2928 debugFlags |= Zygote.DEBUG_ENABLE_DEBUGGER; 2929 // Also turn on CheckJNI for debuggable apps. It's quite 2930 // awkward to turn on otherwise. 2931 debugFlags |= Zygote.DEBUG_ENABLE_CHECKJNI; 2932 } 2933 // Run the app in safe mode if its manifest requests so or the 2934 // system is booted in safe mode. 2935 if ((app.info.flags & ApplicationInfo.FLAG_VM_SAFE_MODE) != 0 || 2936 mSafeMode == true) { 2937 debugFlags |= Zygote.DEBUG_ENABLE_SAFEMODE; 2938 } 2939 if ("1".equals(SystemProperties.get("debug.checkjni"))) { 2940 debugFlags |= Zygote.DEBUG_ENABLE_CHECKJNI; 2941 } 2942 if ("1".equals(SystemProperties.get("debug.jni.logging"))) { 2943 debugFlags |= Zygote.DEBUG_ENABLE_JNI_LOGGING; 2944 } 2945 if ("1".equals(SystemProperties.get("debug.assert"))) { 2946 debugFlags |= Zygote.DEBUG_ENABLE_ASSERT; 2947 } 2948 2949 String requiredAbi = (abiOverride != null) ? abiOverride : app.info.cpuAbi; 2950 if (requiredAbi == null) { 2951 requiredAbi = Build.SUPPORTED_ABIS[0]; 2952 } 2953 2954 // Start the process. It will either succeed and return a result containing 2955 // the PID of the new process, or else throw a RuntimeException. 2956 Process.ProcessStartResult startResult = Process.start("android.app.ActivityThread", 2957 app.processName, uid, uid, gids, debugFlags, mountExternal, 2958 app.info.targetSdkVersion, app.info.seinfo, requiredAbi, null); 2959 2960 BatteryStatsImpl bs = mBatteryStatsService.getActiveStatistics(); 2961 synchronized (bs) { 2962 if (bs.isOnBattery()) { 2963 bs.getProcessStatsLocked(app.uid, app.processName).incStartsLocked(); 2964 } 2965 } 2966 2967 EventLog.writeEvent(EventLogTags.AM_PROC_START, 2968 UserHandle.getUserId(uid), startResult.pid, uid, 2969 app.processName, hostingType, 2970 hostingNameStr != null ? hostingNameStr : ""); 2971 2972 if (app.persistent) { 2973 Watchdog.getInstance().processStarted(app.processName, startResult.pid); 2974 } 2975 2976 StringBuilder buf = mStringBuilder; 2977 buf.setLength(0); 2978 buf.append("Start proc "); 2979 buf.append(app.processName); 2980 buf.append(" for "); 2981 buf.append(hostingType); 2982 if (hostingNameStr != null) { 2983 buf.append(" "); 2984 buf.append(hostingNameStr); 2985 } 2986 buf.append(": pid="); 2987 buf.append(startResult.pid); 2988 buf.append(" uid="); 2989 buf.append(uid); 2990 buf.append(" gids={"); 2991 if (gids != null) { 2992 for (int gi=0; gi<gids.length; gi++) { 2993 if (gi != 0) buf.append(", "); 2994 buf.append(gids[gi]); 2995 2996 } 2997 } 2998 buf.append("}"); 2999 if (requiredAbi != null) { 3000 buf.append(" abi="); 3001 buf.append(requiredAbi); 3002 } 3003 Slog.i(TAG, buf.toString()); 3004 app.setPid(startResult.pid); 3005 app.usingWrapper = startResult.usingWrapper; 3006 app.removed = false; 3007 synchronized (mPidsSelfLocked) { 3008 this.mPidsSelfLocked.put(startResult.pid, app); 3009 Message msg = mHandler.obtainMessage(PROC_START_TIMEOUT_MSG); 3010 msg.obj = app; 3011 mHandler.sendMessageDelayed(msg, startResult.usingWrapper 3012 ? PROC_START_TIMEOUT_WITH_WRAPPER : PROC_START_TIMEOUT); 3013 } 3014 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_PROC_START, 3015 app.processName, app.info.uid); 3016 if (app.isolated) { 3017 mBatteryStatsService.addIsolatedUid(app.uid, app.info.uid); 3018 } 3019 } catch (RuntimeException e) { 3020 // XXX do better error recovery. 3021 app.setPid(0); 3022 Slog.e(TAG, "Failure starting process " + app.processName, e); 3023 } 3024 } 3025 3026 void updateUsageStats(ActivityRecord component, boolean resumed) { 3027 if (DEBUG_SWITCH) Slog.d(TAG, "updateUsageStats: comp=" + component + "res=" + resumed); 3028 final BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 3029 if (resumed) { 3030 mUsageStatsService.noteResumeComponent(component.realActivity); 3031 synchronized (stats) { 3032 stats.noteActivityResumedLocked(component.app.uid); 3033 } 3034 } else { 3035 mUsageStatsService.notePauseComponent(component.realActivity); 3036 synchronized (stats) { 3037 stats.noteActivityPausedLocked(component.app.uid); 3038 } 3039 } 3040 } 3041 3042 Intent getHomeIntent() { 3043 Intent intent = new Intent(mTopAction, mTopData != null ? Uri.parse(mTopData) : null); 3044 intent.setComponent(mTopComponent); 3045 if (mFactoryTest != FactoryTest.FACTORY_TEST_LOW_LEVEL) { 3046 intent.addCategory(Intent.CATEGORY_HOME); 3047 } 3048 return intent; 3049 } 3050 3051 boolean startHomeActivityLocked(int userId) { 3052 if (mFactoryTest == FactoryTest.FACTORY_TEST_LOW_LEVEL 3053 && mTopAction == null) { 3054 // We are running in factory test mode, but unable to find 3055 // the factory test app, so just sit around displaying the 3056 // error message and don't try to start anything. 3057 return false; 3058 } 3059 Intent intent = getHomeIntent(); 3060 ActivityInfo aInfo = 3061 resolveActivityInfo(intent, STOCK_PM_FLAGS, userId); 3062 if (aInfo != null) { 3063 intent.setComponent(new ComponentName( 3064 aInfo.applicationInfo.packageName, aInfo.name)); 3065 // Don't do this if the home app is currently being 3066 // instrumented. 3067 aInfo = new ActivityInfo(aInfo); 3068 aInfo.applicationInfo = getAppInfoForUser(aInfo.applicationInfo, userId); 3069 ProcessRecord app = getProcessRecordLocked(aInfo.processName, 3070 aInfo.applicationInfo.uid, true); 3071 if (app == null || app.instrumentationClass == null) { 3072 intent.setFlags(intent.getFlags() | Intent.FLAG_ACTIVITY_NEW_TASK); 3073 mStackSupervisor.startHomeActivity(intent, aInfo); 3074 } 3075 } 3076 3077 return true; 3078 } 3079 3080 private ActivityInfo resolveActivityInfo(Intent intent, int flags, int userId) { 3081 ActivityInfo ai = null; 3082 ComponentName comp = intent.getComponent(); 3083 try { 3084 if (comp != null) { 3085 ai = AppGlobals.getPackageManager().getActivityInfo(comp, flags, userId); 3086 } else { 3087 ResolveInfo info = AppGlobals.getPackageManager().resolveIntent( 3088 intent, 3089 intent.resolveTypeIfNeeded(mContext.getContentResolver()), 3090 flags, userId); 3091 3092 if (info != null) { 3093 ai = info.activityInfo; 3094 } 3095 } 3096 } catch (RemoteException e) { 3097 // ignore 3098 } 3099 3100 return ai; 3101 } 3102 3103 /** 3104 * Starts the "new version setup screen" if appropriate. 3105 */ 3106 void startSetupActivityLocked() { 3107 // Only do this once per boot. 3108 if (mCheckedForSetup) { 3109 return; 3110 } 3111 3112 // We will show this screen if the current one is a different 3113 // version than the last one shown, and we are not running in 3114 // low-level factory test mode. 3115 final ContentResolver resolver = mContext.getContentResolver(); 3116 if (mFactoryTest != FactoryTest.FACTORY_TEST_LOW_LEVEL && 3117 Settings.Global.getInt(resolver, 3118 Settings.Global.DEVICE_PROVISIONED, 0) != 0) { 3119 mCheckedForSetup = true; 3120 3121 // See if we should be showing the platform update setup UI. 3122 Intent intent = new Intent(Intent.ACTION_UPGRADE_SETUP); 3123 List<ResolveInfo> ris = mContext.getPackageManager() 3124 .queryIntentActivities(intent, PackageManager.GET_META_DATA); 3125 3126 // We don't allow third party apps to replace this. 3127 ResolveInfo ri = null; 3128 for (int i=0; ris != null && i<ris.size(); i++) { 3129 if ((ris.get(i).activityInfo.applicationInfo.flags 3130 & ApplicationInfo.FLAG_SYSTEM) != 0) { 3131 ri = ris.get(i); 3132 break; 3133 } 3134 } 3135 3136 if (ri != null) { 3137 String vers = ri.activityInfo.metaData != null 3138 ? ri.activityInfo.metaData.getString(Intent.METADATA_SETUP_VERSION) 3139 : null; 3140 if (vers == null && ri.activityInfo.applicationInfo.metaData != null) { 3141 vers = ri.activityInfo.applicationInfo.metaData.getString( 3142 Intent.METADATA_SETUP_VERSION); 3143 } 3144 String lastVers = Settings.Secure.getString( 3145 resolver, Settings.Secure.LAST_SETUP_SHOWN); 3146 if (vers != null && !vers.equals(lastVers)) { 3147 intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK); 3148 intent.setComponent(new ComponentName( 3149 ri.activityInfo.packageName, ri.activityInfo.name)); 3150 mStackSupervisor.startActivityLocked(null, intent, null, ri.activityInfo, 3151 null, null, null, null, 0, 0, 0, null, 0, null, false, null, null); 3152 } 3153 } 3154 } 3155 } 3156 3157 CompatibilityInfo compatibilityInfoForPackageLocked(ApplicationInfo ai) { 3158 return mCompatModePackages.compatibilityInfoForPackageLocked(ai); 3159 } 3160 3161 void enforceNotIsolatedCaller(String caller) { 3162 if (UserHandle.isIsolated(Binder.getCallingUid())) { 3163 throw new SecurityException("Isolated process not allowed to call " + caller); 3164 } 3165 } 3166 3167 @Override 3168 public int getFrontActivityScreenCompatMode() { 3169 enforceNotIsolatedCaller("getFrontActivityScreenCompatMode"); 3170 synchronized (this) { 3171 return mCompatModePackages.getFrontActivityScreenCompatModeLocked(); 3172 } 3173 } 3174 3175 @Override 3176 public void setFrontActivityScreenCompatMode(int mode) { 3177 enforceCallingPermission(android.Manifest.permission.SET_SCREEN_COMPATIBILITY, 3178 "setFrontActivityScreenCompatMode"); 3179 synchronized (this) { 3180 mCompatModePackages.setFrontActivityScreenCompatModeLocked(mode); 3181 } 3182 } 3183 3184 @Override 3185 public int getPackageScreenCompatMode(String packageName) { 3186 enforceNotIsolatedCaller("getPackageScreenCompatMode"); 3187 synchronized (this) { 3188 return mCompatModePackages.getPackageScreenCompatModeLocked(packageName); 3189 } 3190 } 3191 3192 @Override 3193 public void setPackageScreenCompatMode(String packageName, int mode) { 3194 enforceCallingPermission(android.Manifest.permission.SET_SCREEN_COMPATIBILITY, 3195 "setPackageScreenCompatMode"); 3196 synchronized (this) { 3197 mCompatModePackages.setPackageScreenCompatModeLocked(packageName, mode); 3198 } 3199 } 3200 3201 @Override 3202 public boolean getPackageAskScreenCompat(String packageName) { 3203 enforceNotIsolatedCaller("getPackageAskScreenCompat"); 3204 synchronized (this) { 3205 return mCompatModePackages.getPackageAskCompatModeLocked(packageName); 3206 } 3207 } 3208 3209 @Override 3210 public void setPackageAskScreenCompat(String packageName, boolean ask) { 3211 enforceCallingPermission(android.Manifest.permission.SET_SCREEN_COMPATIBILITY, 3212 "setPackageAskScreenCompat"); 3213 synchronized (this) { 3214 mCompatModePackages.setPackageAskCompatModeLocked(packageName, ask); 3215 } 3216 } 3217 3218 private void dispatchProcessesChanged() { 3219 int N; 3220 synchronized (this) { 3221 N = mPendingProcessChanges.size(); 3222 if (mActiveProcessChanges.length < N) { 3223 mActiveProcessChanges = new ProcessChangeItem[N]; 3224 } 3225 mPendingProcessChanges.toArray(mActiveProcessChanges); 3226 mAvailProcessChanges.addAll(mPendingProcessChanges); 3227 mPendingProcessChanges.clear(); 3228 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "*** Delivering " + N + " process changes"); 3229 } 3230 3231 int i = mProcessObservers.beginBroadcast(); 3232 while (i > 0) { 3233 i--; 3234 final IProcessObserver observer = mProcessObservers.getBroadcastItem(i); 3235 if (observer != null) { 3236 try { 3237 for (int j=0; j<N; j++) { 3238 ProcessChangeItem item = mActiveProcessChanges[j]; 3239 if ((item.changes&ProcessChangeItem.CHANGE_ACTIVITIES) != 0) { 3240 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "ACTIVITIES CHANGED pid=" 3241 + item.pid + " uid=" + item.uid + ": " 3242 + item.foregroundActivities); 3243 observer.onForegroundActivitiesChanged(item.pid, item.uid, 3244 item.foregroundActivities); 3245 } 3246 if ((item.changes&ProcessChangeItem.CHANGE_PROCESS_STATE) != 0) { 3247 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "PROCSTATE CHANGED pid=" 3248 + item.pid + " uid=" + item.uid + ": " + item.processState); 3249 observer.onProcessStateChanged(item.pid, item.uid, item.processState); 3250 } 3251 } 3252 } catch (RemoteException e) { 3253 } 3254 } 3255 } 3256 mProcessObservers.finishBroadcast(); 3257 } 3258 3259 private void dispatchProcessDied(int pid, int uid) { 3260 int i = mProcessObservers.beginBroadcast(); 3261 while (i > 0) { 3262 i--; 3263 final IProcessObserver observer = mProcessObservers.getBroadcastItem(i); 3264 if (observer != null) { 3265 try { 3266 observer.onProcessDied(pid, uid); 3267 } catch (RemoteException e) { 3268 } 3269 } 3270 } 3271 mProcessObservers.finishBroadcast(); 3272 } 3273 3274 final void doPendingActivityLaunchesLocked(boolean doResume) { 3275 final int N = mPendingActivityLaunches.size(); 3276 if (N <= 0) { 3277 return; 3278 } 3279 for (int i=0; i<N; i++) { 3280 PendingActivityLaunch pal = mPendingActivityLaunches.get(i); 3281 mStackSupervisor.startActivityUncheckedLocked(pal.r, pal.sourceRecord, null, null, pal.startFlags, 3282 doResume && i == (N-1), null); 3283 } 3284 mPendingActivityLaunches.clear(); 3285 } 3286 3287 @Override 3288 public final int startActivity(IApplicationThread caller, String callingPackage, 3289 Intent intent, String resolvedType, IBinder resultTo, 3290 String resultWho, int requestCode, int startFlags, 3291 String profileFile, ParcelFileDescriptor profileFd, Bundle options) { 3292 return startActivityAsUser(caller, callingPackage, intent, resolvedType, resultTo, 3293 resultWho, requestCode, 3294 startFlags, profileFile, profileFd, options, UserHandle.getCallingUserId()); 3295 } 3296 3297 @Override 3298 public final int startActivityAsUser(IApplicationThread caller, String callingPackage, 3299 Intent intent, String resolvedType, IBinder resultTo, 3300 String resultWho, int requestCode, int startFlags, 3301 String profileFile, ParcelFileDescriptor profileFd, Bundle options, int userId) { 3302 enforceNotIsolatedCaller("startActivity"); 3303 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3304 false, true, "startActivity", null); 3305 // TODO: Switch to user app stacks here. 3306 return mStackSupervisor.startActivityMayWait(caller, -1, callingPackage, intent, resolvedType, 3307 null, null, resultTo, resultWho, requestCode, startFlags, profileFile, profileFd, 3308 null, null, options, userId, null); 3309 } 3310 3311 @Override 3312 public final WaitResult startActivityAndWait(IApplicationThread caller, String callingPackage, 3313 Intent intent, String resolvedType, IBinder resultTo, 3314 String resultWho, int requestCode, int startFlags, String profileFile, 3315 ParcelFileDescriptor profileFd, Bundle options, int userId) { 3316 enforceNotIsolatedCaller("startActivityAndWait"); 3317 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3318 false, true, "startActivityAndWait", null); 3319 WaitResult res = new WaitResult(); 3320 // TODO: Switch to user app stacks here. 3321 mStackSupervisor.startActivityMayWait(caller, -1, callingPackage, intent, resolvedType, 3322 null, null, resultTo, resultWho, requestCode, startFlags, profileFile, profileFd, 3323 res, null, options, UserHandle.getCallingUserId(), null); 3324 return res; 3325 } 3326 3327 @Override 3328 public final int startActivityWithConfig(IApplicationThread caller, String callingPackage, 3329 Intent intent, String resolvedType, IBinder resultTo, 3330 String resultWho, int requestCode, int startFlags, Configuration config, 3331 Bundle options, int userId) { 3332 enforceNotIsolatedCaller("startActivityWithConfig"); 3333 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3334 false, true, "startActivityWithConfig", null); 3335 // TODO: Switch to user app stacks here. 3336 int ret = mStackSupervisor.startActivityMayWait(caller, -1, callingPackage, intent, 3337 resolvedType, null, null, resultTo, resultWho, requestCode, startFlags, 3338 null, null, null, config, options, userId, null); 3339 return ret; 3340 } 3341 3342 @Override 3343 public int startActivityIntentSender(IApplicationThread caller, 3344 IntentSender intent, Intent fillInIntent, String resolvedType, 3345 IBinder resultTo, String resultWho, int requestCode, 3346 int flagsMask, int flagsValues, Bundle options) { 3347 enforceNotIsolatedCaller("startActivityIntentSender"); 3348 // Refuse possible leaked file descriptors 3349 if (fillInIntent != null && fillInIntent.hasFileDescriptors()) { 3350 throw new IllegalArgumentException("File descriptors passed in Intent"); 3351 } 3352 3353 IIntentSender sender = intent.getTarget(); 3354 if (!(sender instanceof PendingIntentRecord)) { 3355 throw new IllegalArgumentException("Bad PendingIntent object"); 3356 } 3357 3358 PendingIntentRecord pir = (PendingIntentRecord)sender; 3359 3360 synchronized (this) { 3361 // If this is coming from the currently resumed activity, it is 3362 // effectively saying that app switches are allowed at this point. 3363 final ActivityStack stack = getFocusedStack(); 3364 if (stack.mResumedActivity != null && 3365 stack.mResumedActivity.info.applicationInfo.uid == Binder.getCallingUid()) { 3366 mAppSwitchesAllowedTime = 0; 3367 } 3368 } 3369 int ret = pir.sendInner(0, fillInIntent, resolvedType, null, null, 3370 resultTo, resultWho, requestCode, flagsMask, flagsValues, options, null); 3371 return ret; 3372 } 3373 3374 @Override 3375 public int startVoiceActivity(String callingPackage, int callingPid, int callingUid, 3376 Intent intent, String resolvedType, IVoiceInteractionSession session, 3377 IVoiceInteractor interactor, int startFlags, String profileFile, 3378 ParcelFileDescriptor profileFd, Bundle options, int userId) { 3379 if (checkCallingPermission(Manifest.permission.BIND_VOICE_INTERACTION) 3380 != PackageManager.PERMISSION_GRANTED) { 3381 String msg = "Permission Denial: startVoiceActivity() from pid=" 3382 + Binder.getCallingPid() 3383 + ", uid=" + Binder.getCallingUid() 3384 + " requires " + android.Manifest.permission.BIND_VOICE_INTERACTION; 3385 Slog.w(TAG, msg); 3386 throw new SecurityException(msg); 3387 } 3388 if (session == null || interactor == null) { 3389 throw new NullPointerException("null session or interactor"); 3390 } 3391 userId = handleIncomingUser(callingPid, callingUid, userId, 3392 false, true, "startVoiceActivity", null); 3393 // TODO: Switch to user app stacks here. 3394 return mStackSupervisor.startActivityMayWait(null, callingUid, callingPackage, intent, 3395 resolvedType, session, interactor, null, null, 0, startFlags, 3396 profileFile, profileFd, null, null, options, userId, null); 3397 } 3398 3399 @Override 3400 public boolean startNextMatchingActivity(IBinder callingActivity, 3401 Intent intent, Bundle options) { 3402 // Refuse possible leaked file descriptors 3403 if (intent != null && intent.hasFileDescriptors() == true) { 3404 throw new IllegalArgumentException("File descriptors passed in Intent"); 3405 } 3406 3407 synchronized (this) { 3408 final ActivityRecord r = ActivityRecord.isInStackLocked(callingActivity); 3409 if (r == null) { 3410 ActivityOptions.abort(options); 3411 return false; 3412 } 3413 if (r.app == null || r.app.thread == null) { 3414 // The caller is not running... d'oh! 3415 ActivityOptions.abort(options); 3416 return false; 3417 } 3418 intent = new Intent(intent); 3419 // The caller is not allowed to change the data. 3420 intent.setDataAndType(r.intent.getData(), r.intent.getType()); 3421 // And we are resetting to find the next component... 3422 intent.setComponent(null); 3423 3424 final boolean debug = ((intent.getFlags() & Intent.FLAG_DEBUG_LOG_RESOLUTION) != 0); 3425 3426 ActivityInfo aInfo = null; 3427 try { 3428 List<ResolveInfo> resolves = 3429 AppGlobals.getPackageManager().queryIntentActivities( 3430 intent, r.resolvedType, 3431 PackageManager.MATCH_DEFAULT_ONLY | STOCK_PM_FLAGS, 3432 UserHandle.getCallingUserId()); 3433 3434 // Look for the original activity in the list... 3435 final int N = resolves != null ? resolves.size() : 0; 3436 for (int i=0; i<N; i++) { 3437 ResolveInfo rInfo = resolves.get(i); 3438 if (rInfo.activityInfo.packageName.equals(r.packageName) 3439 && rInfo.activityInfo.name.equals(r.info.name)) { 3440 // We found the current one... the next matching is 3441 // after it. 3442 i++; 3443 if (i<N) { 3444 aInfo = resolves.get(i).activityInfo; 3445 } 3446 if (debug) { 3447 Slog.v(TAG, "Next matching activity: found current " + r.packageName 3448 + "/" + r.info.name); 3449 Slog.v(TAG, "Next matching activity: next is " + aInfo.packageName 3450 + "/" + aInfo.name); 3451 } 3452 break; 3453 } 3454 } 3455 } catch (RemoteException e) { 3456 } 3457 3458 if (aInfo == null) { 3459 // Nobody who is next! 3460 ActivityOptions.abort(options); 3461 if (debug) Slog.d(TAG, "Next matching activity: nothing found"); 3462 return false; 3463 } 3464 3465 intent.setComponent(new ComponentName( 3466 aInfo.applicationInfo.packageName, aInfo.name)); 3467 intent.setFlags(intent.getFlags()&~( 3468 Intent.FLAG_ACTIVITY_FORWARD_RESULT| 3469 Intent.FLAG_ACTIVITY_CLEAR_TOP| 3470 Intent.FLAG_ACTIVITY_MULTIPLE_TASK| 3471 Intent.FLAG_ACTIVITY_NEW_TASK)); 3472 3473 // Okay now we need to start the new activity, replacing the 3474 // currently running activity. This is a little tricky because 3475 // we want to start the new one as if the current one is finished, 3476 // but not finish the current one first so that there is no flicker. 3477 // And thus... 3478 final boolean wasFinishing = r.finishing; 3479 r.finishing = true; 3480 3481 // Propagate reply information over to the new activity. 3482 final ActivityRecord resultTo = r.resultTo; 3483 final String resultWho = r.resultWho; 3484 final int requestCode = r.requestCode; 3485 r.resultTo = null; 3486 if (resultTo != null) { 3487 resultTo.removeResultsLocked(r, resultWho, requestCode); 3488 } 3489 3490 final long origId = Binder.clearCallingIdentity(); 3491 int res = mStackSupervisor.startActivityLocked(r.app.thread, intent, 3492 r.resolvedType, aInfo, null, null, resultTo != null ? resultTo.appToken : null, 3493 resultWho, requestCode, -1, r.launchedFromUid, r.launchedFromPackage, 0, 3494 options, false, null, null); 3495 Binder.restoreCallingIdentity(origId); 3496 3497 r.finishing = wasFinishing; 3498 if (res != ActivityManager.START_SUCCESS) { 3499 return false; 3500 } 3501 return true; 3502 } 3503 } 3504 3505 final int startActivityInPackage(int uid, String callingPackage, 3506 Intent intent, String resolvedType, IBinder resultTo, 3507 String resultWho, int requestCode, int startFlags, Bundle options, int userId, 3508 IActivityContainer container) { 3509 3510 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3511 false, true, "startActivityInPackage", null); 3512 3513 // TODO: Switch to user app stacks here. 3514 int ret = mStackSupervisor.startActivityMayWait(null, uid, callingPackage, intent, resolvedType, 3515 null, null, resultTo, resultWho, requestCode, startFlags, 3516 null, null, null, null, options, userId, container); 3517 return ret; 3518 } 3519 3520 @Override 3521 public final int startActivities(IApplicationThread caller, String callingPackage, 3522 Intent[] intents, String[] resolvedTypes, IBinder resultTo, Bundle options, 3523 int userId) { 3524 enforceNotIsolatedCaller("startActivities"); 3525 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3526 false, true, "startActivity", null); 3527 // TODO: Switch to user app stacks here. 3528 int ret = mStackSupervisor.startActivities(caller, -1, callingPackage, intents, 3529 resolvedTypes, resultTo, options, userId); 3530 return ret; 3531 } 3532 3533 final int startActivitiesInPackage(int uid, String callingPackage, 3534 Intent[] intents, String[] resolvedTypes, IBinder resultTo, 3535 Bundle options, int userId) { 3536 3537 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3538 false, true, "startActivityInPackage", null); 3539 // TODO: Switch to user app stacks here. 3540 int ret = mStackSupervisor.startActivities(null, uid, callingPackage, intents, resolvedTypes, 3541 resultTo, options, userId); 3542 return ret; 3543 } 3544 3545 final void addRecentTaskLocked(TaskRecord task) { 3546 int N = mRecentTasks.size(); 3547 // Quick case: check if the top-most recent task is the same. 3548 if (N > 0 && mRecentTasks.get(0) == task) { 3549 return; 3550 } 3551 // Another quick case: never add voice sessions. 3552 if (task.voiceSession != null) { 3553 return; 3554 } 3555 // Remove any existing entries that are the same kind of task. 3556 final Intent intent = task.intent; 3557 final boolean document = intent != null && intent.isDocument(); 3558 final ComponentName comp = intent.getComponent(); 3559 3560 int maxRecents = task.maxRecents - 1; 3561 for (int i=0; i<N; i++) { 3562 TaskRecord tr = mRecentTasks.get(i); 3563 if (task != tr) { 3564 if (task.userId != tr.userId) { 3565 continue; 3566 } 3567 final Intent trIntent = tr.intent; 3568 if ((task.affinity == null || !task.affinity.equals(tr.affinity)) && 3569 (intent == null || !intent.filterEquals(trIntent))) { 3570 continue; 3571 } 3572 final boolean trIsDocument = trIntent != null && trIntent.isDocument(); 3573 if (document && trIsDocument) { 3574 // These are the same document activity (not necessarily the same doc). 3575 if (maxRecents > 0) { 3576 --maxRecents; 3577 continue; 3578 } 3579 // Hit the maximum number of documents for this task. Fall through 3580 // and remove this document from recents. 3581 } else if (document || trIsDocument) { 3582 // Only one of these is a document. Not the droid we're looking for. 3583 continue; 3584 } 3585 } 3586 3587 // Either task and tr are the same or, their affinities match or their intents match 3588 // and neither of them is a document, or they are documents using the same activity 3589 // and their maxRecents has been reached. 3590 tr.disposeThumbnail(); 3591 mRecentTasks.remove(i); 3592 i--; 3593 N--; 3594 if (task.intent == null) { 3595 // If the new recent task we are adding is not fully 3596 // specified, then replace it with the existing recent task. 3597 task = tr; 3598 } 3599 mTaskPersister.notify(tr, false); 3600 } 3601 if (N >= MAX_RECENT_TASKS) { 3602 mRecentTasks.remove(N-1).disposeThumbnail(); 3603 } 3604 mRecentTasks.add(0, task); 3605 } 3606 3607 @Override 3608 public void reportActivityFullyDrawn(IBinder token) { 3609 synchronized (this) { 3610 ActivityRecord r = ActivityRecord.isInStackLocked(token); 3611 if (r == null) { 3612 return; 3613 } 3614 r.reportFullyDrawnLocked(); 3615 } 3616 } 3617 3618 @Override 3619 public void setRequestedOrientation(IBinder token, int requestedOrientation) { 3620 synchronized (this) { 3621 ActivityRecord r = ActivityRecord.isInStackLocked(token); 3622 if (r == null) { 3623 return; 3624 } 3625 final long origId = Binder.clearCallingIdentity(); 3626 mWindowManager.setAppOrientation(r.appToken, requestedOrientation); 3627 Configuration config = mWindowManager.updateOrientationFromAppTokens( 3628 mConfiguration, r.mayFreezeScreenLocked(r.app) ? r.appToken : null); 3629 if (config != null) { 3630 r.frozenBeforeDestroy = true; 3631 if (!updateConfigurationLocked(config, r, false, false)) { 3632 mStackSupervisor.resumeTopActivitiesLocked(); 3633 } 3634 } 3635 Binder.restoreCallingIdentity(origId); 3636 } 3637 } 3638 3639 @Override 3640 public int getRequestedOrientation(IBinder token) { 3641 synchronized (this) { 3642 ActivityRecord r = ActivityRecord.isInStackLocked(token); 3643 if (r == null) { 3644 return ActivityInfo.SCREEN_ORIENTATION_UNSPECIFIED; 3645 } 3646 return mWindowManager.getAppOrientation(r.appToken); 3647 } 3648 } 3649 3650 /** 3651 * This is the internal entry point for handling Activity.finish(). 3652 * 3653 * @param token The Binder token referencing the Activity we want to finish. 3654 * @param resultCode Result code, if any, from this Activity. 3655 * @param resultData Result data (Intent), if any, from this Activity. 3656 * @param finishTask Whether to finish the task associated with this Activity. Only applies to 3657 * the root Activity in the task. 3658 * 3659 * @return Returns true if the activity successfully finished, or false if it is still running. 3660 */ 3661 @Override 3662 public final boolean finishActivity(IBinder token, int resultCode, Intent resultData, 3663 boolean finishTask) { 3664 // Refuse possible leaked file descriptors 3665 if (resultData != null && resultData.hasFileDescriptors() == true) { 3666 throw new IllegalArgumentException("File descriptors passed in Intent"); 3667 } 3668 3669 synchronized(this) { 3670 ActivityRecord r = ActivityRecord.isInStackLocked(token); 3671 if (r == null) { 3672 return true; 3673 } 3674 // Keep track of the root activity of the task before we finish it 3675 TaskRecord tr = r.task; 3676 ActivityRecord rootR = tr.getRootActivity(); 3677 // Do not allow task to finish in Lock Task mode. 3678 if (tr == mStackSupervisor.mLockTaskModeTask) { 3679 if (rootR == r) { 3680 return false; 3681 } 3682 } 3683 if (mController != null) { 3684 // Find the first activity that is not finishing. 3685 ActivityRecord next = r.task.stack.topRunningActivityLocked(token, 0); 3686 if (next != null) { 3687 // ask watcher if this is allowed 3688 boolean resumeOK = true; 3689 try { 3690 resumeOK = mController.activityResuming(next.packageName); 3691 } catch (RemoteException e) { 3692 mController = null; 3693 Watchdog.getInstance().setActivityController(null); 3694 } 3695 3696 if (!resumeOK) { 3697 return false; 3698 } 3699 } 3700 } 3701 final long origId = Binder.clearCallingIdentity(); 3702 try { 3703 boolean res; 3704 if (finishTask && r == rootR) { 3705 // If requested, remove the task that is associated to this activity only if it 3706 // was the root activity in the task. The result code and data is ignored because 3707 // we don't support returning them across task boundaries. 3708 res = removeTaskByIdLocked(tr.taskId, 0); 3709 } else { 3710 res = tr.stack.requestFinishActivityLocked(token, resultCode, 3711 resultData, "app-request", true); 3712 } 3713 return res; 3714 } finally { 3715 Binder.restoreCallingIdentity(origId); 3716 } 3717 } 3718 } 3719 3720 @Override 3721 public final void finishHeavyWeightApp() { 3722 if (checkCallingPermission(android.Manifest.permission.FORCE_STOP_PACKAGES) 3723 != PackageManager.PERMISSION_GRANTED) { 3724 String msg = "Permission Denial: finishHeavyWeightApp() from pid=" 3725 + Binder.getCallingPid() 3726 + ", uid=" + Binder.getCallingUid() 3727 + " requires " + android.Manifest.permission.FORCE_STOP_PACKAGES; 3728 Slog.w(TAG, msg); 3729 throw new SecurityException(msg); 3730 } 3731 3732 synchronized(this) { 3733 if (mHeavyWeightProcess == null) { 3734 return; 3735 } 3736 3737 ArrayList<ActivityRecord> activities = new ArrayList<ActivityRecord>( 3738 mHeavyWeightProcess.activities); 3739 for (int i=0; i<activities.size(); i++) { 3740 ActivityRecord r = activities.get(i); 3741 if (!r.finishing) { 3742 r.task.stack.finishActivityLocked(r, Activity.RESULT_CANCELED, 3743 null, "finish-heavy", true); 3744 } 3745 } 3746 3747 mHandler.sendMessage(mHandler.obtainMessage(CANCEL_HEAVY_NOTIFICATION_MSG, 3748 mHeavyWeightProcess.userId, 0)); 3749 mHeavyWeightProcess = null; 3750 } 3751 } 3752 3753 @Override 3754 public void crashApplication(int uid, int initialPid, String packageName, 3755 String message) { 3756 if (checkCallingPermission(android.Manifest.permission.FORCE_STOP_PACKAGES) 3757 != PackageManager.PERMISSION_GRANTED) { 3758 String msg = "Permission Denial: crashApplication() from pid=" 3759 + Binder.getCallingPid() 3760 + ", uid=" + Binder.getCallingUid() 3761 + " requires " + android.Manifest.permission.FORCE_STOP_PACKAGES; 3762 Slog.w(TAG, msg); 3763 throw new SecurityException(msg); 3764 } 3765 3766 synchronized(this) { 3767 ProcessRecord proc = null; 3768 3769 // Figure out which process to kill. We don't trust that initialPid 3770 // still has any relation to current pids, so must scan through the 3771 // list. 3772 synchronized (mPidsSelfLocked) { 3773 for (int i=0; i<mPidsSelfLocked.size(); i++) { 3774 ProcessRecord p = mPidsSelfLocked.valueAt(i); 3775 if (p.uid != uid) { 3776 continue; 3777 } 3778 if (p.pid == initialPid) { 3779 proc = p; 3780 break; 3781 } 3782 if (p.pkgList.containsKey(packageName)) { 3783 proc = p; 3784 } 3785 } 3786 } 3787 3788 if (proc == null) { 3789 Slog.w(TAG, "crashApplication: nothing for uid=" + uid 3790 + " initialPid=" + initialPid 3791 + " packageName=" + packageName); 3792 return; 3793 } 3794 3795 if (proc.thread != null) { 3796 if (proc.pid == Process.myPid()) { 3797 Log.w(TAG, "crashApplication: trying to crash self!"); 3798 return; 3799 } 3800 long ident = Binder.clearCallingIdentity(); 3801 try { 3802 proc.thread.scheduleCrash(message); 3803 } catch (RemoteException e) { 3804 } 3805 Binder.restoreCallingIdentity(ident); 3806 } 3807 } 3808 } 3809 3810 @Override 3811 public final void finishSubActivity(IBinder token, String resultWho, 3812 int requestCode) { 3813 synchronized(this) { 3814 final long origId = Binder.clearCallingIdentity(); 3815 ActivityRecord r = ActivityRecord.isInStackLocked(token); 3816 if (r != null) { 3817 r.task.stack.finishSubActivityLocked(r, resultWho, requestCode); 3818 } 3819 Binder.restoreCallingIdentity(origId); 3820 } 3821 } 3822 3823 @Override 3824 public boolean finishActivityAffinity(IBinder token) { 3825 synchronized(this) { 3826 final long origId = Binder.clearCallingIdentity(); 3827 try { 3828 ActivityRecord r = ActivityRecord.isInStackLocked(token); 3829 3830 ActivityRecord rootR = r.task.getRootActivity(); 3831 // Do not allow task to finish in Lock Task mode. 3832 if (r.task == mStackSupervisor.mLockTaskModeTask) { 3833 if (rootR == r) { 3834 Binder.restoreCallingIdentity(origId); 3835 return false; 3836 } 3837 } 3838 boolean res = false; 3839 if (r != null) { 3840 res = r.task.stack.finishActivityAffinityLocked(r); 3841 } 3842 return res; 3843 } finally { 3844 Binder.restoreCallingIdentity(origId); 3845 } 3846 } 3847 } 3848 3849 @Override 3850 public boolean willActivityBeVisible(IBinder token) { 3851 synchronized(this) { 3852 ActivityStack stack = ActivityRecord.getStackLocked(token); 3853 if (stack != null) { 3854 return stack.willActivityBeVisibleLocked(token); 3855 } 3856 return false; 3857 } 3858 } 3859 3860 @Override 3861 public void overridePendingTransition(IBinder token, String packageName, 3862 int enterAnim, int exitAnim) { 3863 synchronized(this) { 3864 ActivityRecord self = ActivityRecord.isInStackLocked(token); 3865 if (self == null) { 3866 return; 3867 } 3868 3869 final long origId = Binder.clearCallingIdentity(); 3870 3871 if (self.state == ActivityState.RESUMED 3872 || self.state == ActivityState.PAUSING) { 3873 mWindowManager.overridePendingAppTransition(packageName, 3874 enterAnim, exitAnim, null); 3875 } 3876 3877 Binder.restoreCallingIdentity(origId); 3878 } 3879 } 3880 3881 /** 3882 * Main function for removing an existing process from the activity manager 3883 * as a result of that process going away. Clears out all connections 3884 * to the process. 3885 */ 3886 private final void handleAppDiedLocked(ProcessRecord app, 3887 boolean restarting, boolean allowRestart) { 3888 int pid = app.pid; 3889 cleanUpApplicationRecordLocked(app, restarting, allowRestart, -1); 3890 if (!restarting) { 3891 removeLruProcessLocked(app); 3892 if (pid > 0) { 3893 ProcessList.remove(pid); 3894 } 3895 } 3896 3897 if (mProfileProc == app) { 3898 clearProfilerLocked(); 3899 } 3900 3901 // Remove this application's activities from active lists. 3902 boolean hasVisibleActivities = mStackSupervisor.handleAppDiedLocked(app); 3903 3904 app.activities.clear(); 3905 3906 if (app.instrumentationClass != null) { 3907 Slog.w(TAG, "Crash of app " + app.processName 3908 + " running instrumentation " + app.instrumentationClass); 3909 Bundle info = new Bundle(); 3910 info.putString("shortMsg", "Process crashed."); 3911 finishInstrumentationLocked(app, Activity.RESULT_CANCELED, info); 3912 } 3913 3914 if (!restarting) { 3915 if (!mStackSupervisor.resumeTopActivitiesLocked()) { 3916 // If there was nothing to resume, and we are not already 3917 // restarting this process, but there is a visible activity that 3918 // is hosted by the process... then make sure all visible 3919 // activities are running, taking care of restarting this 3920 // process. 3921 if (hasVisibleActivities) { 3922 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0); 3923 } 3924 } 3925 } 3926 } 3927 3928 private final int getLRURecordIndexForAppLocked(IApplicationThread thread) { 3929 IBinder threadBinder = thread.asBinder(); 3930 // Find the application record. 3931 for (int i=mLruProcesses.size()-1; i>=0; i--) { 3932 ProcessRecord rec = mLruProcesses.get(i); 3933 if (rec.thread != null && rec.thread.asBinder() == threadBinder) { 3934 return i; 3935 } 3936 } 3937 return -1; 3938 } 3939 3940 final ProcessRecord getRecordForAppLocked( 3941 IApplicationThread thread) { 3942 if (thread == null) { 3943 return null; 3944 } 3945 3946 int appIndex = getLRURecordIndexForAppLocked(thread); 3947 return appIndex >= 0 ? mLruProcesses.get(appIndex) : null; 3948 } 3949 3950 final void doLowMemReportIfNeededLocked(ProcessRecord dyingProc) { 3951 // If there are no longer any background processes running, 3952 // and the app that died was not running instrumentation, 3953 // then tell everyone we are now low on memory. 3954 boolean haveBg = false; 3955 for (int i=mLruProcesses.size()-1; i>=0; i--) { 3956 ProcessRecord rec = mLruProcesses.get(i); 3957 if (rec.thread != null 3958 && rec.setProcState >= ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 3959 haveBg = true; 3960 break; 3961 } 3962 } 3963 3964 if (!haveBg) { 3965 boolean doReport = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 3966 if (doReport) { 3967 long now = SystemClock.uptimeMillis(); 3968 if (now < (mLastMemUsageReportTime+5*60*1000)) { 3969 doReport = false; 3970 } else { 3971 mLastMemUsageReportTime = now; 3972 } 3973 } 3974 final ArrayList<ProcessMemInfo> memInfos 3975 = doReport ? new ArrayList<ProcessMemInfo>(mLruProcesses.size()) : null; 3976 EventLog.writeEvent(EventLogTags.AM_LOW_MEMORY, mLruProcesses.size()); 3977 long now = SystemClock.uptimeMillis(); 3978 for (int i=mLruProcesses.size()-1; i>=0; i--) { 3979 ProcessRecord rec = mLruProcesses.get(i); 3980 if (rec == dyingProc || rec.thread == null) { 3981 continue; 3982 } 3983 if (doReport) { 3984 memInfos.add(new ProcessMemInfo(rec.processName, rec.pid, rec.setAdj, 3985 rec.setProcState, rec.adjType, rec.makeAdjReason())); 3986 } 3987 if ((rec.lastLowMemory+GC_MIN_INTERVAL) <= now) { 3988 // The low memory report is overriding any current 3989 // state for a GC request. Make sure to do 3990 // heavy/important/visible/foreground processes first. 3991 if (rec.setAdj <= ProcessList.HEAVY_WEIGHT_APP_ADJ) { 3992 rec.lastRequestedGc = 0; 3993 } else { 3994 rec.lastRequestedGc = rec.lastLowMemory; 3995 } 3996 rec.reportLowMemory = true; 3997 rec.lastLowMemory = now; 3998 mProcessesToGc.remove(rec); 3999 addProcessToGcListLocked(rec); 4000 } 4001 } 4002 if (doReport) { 4003 Message msg = mHandler.obtainMessage(REPORT_MEM_USAGE_MSG, memInfos); 4004 mHandler.sendMessage(msg); 4005 } 4006 scheduleAppGcsLocked(); 4007 } 4008 } 4009 4010 final void appDiedLocked(ProcessRecord app, int pid, 4011 IApplicationThread thread) { 4012 4013 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 4014 synchronized (stats) { 4015 stats.noteProcessDiedLocked(app.info.uid, pid); 4016 } 4017 4018 // Clean up already done if the process has been re-started. 4019 if (app.pid == pid && app.thread != null && 4020 app.thread.asBinder() == thread.asBinder()) { 4021 boolean doLowMem = app.instrumentationClass == null; 4022 boolean doOomAdj = doLowMem; 4023 if (!app.killedByAm) { 4024 Slog.i(TAG, "Process " + app.processName + " (pid " + pid 4025 + ") has died."); 4026 mAllowLowerMemLevel = true; 4027 } else { 4028 // Note that we always want to do oom adj to update our state with the 4029 // new number of procs. 4030 mAllowLowerMemLevel = false; 4031 doLowMem = false; 4032 } 4033 EventLog.writeEvent(EventLogTags.AM_PROC_DIED, app.userId, app.pid, app.processName); 4034 if (DEBUG_CLEANUP) Slog.v( 4035 TAG, "Dying app: " + app + ", pid: " + pid 4036 + ", thread: " + thread.asBinder()); 4037 handleAppDiedLocked(app, false, true); 4038 4039 if (doOomAdj) { 4040 updateOomAdjLocked(); 4041 } 4042 if (doLowMem) { 4043 doLowMemReportIfNeededLocked(app); 4044 } 4045 } else if (app.pid != pid) { 4046 // A new process has already been started. 4047 Slog.i(TAG, "Process " + app.processName + " (pid " + pid 4048 + ") has died and restarted (pid " + app.pid + ")."); 4049 EventLog.writeEvent(EventLogTags.AM_PROC_DIED, app.userId, app.pid, app.processName); 4050 } else if (DEBUG_PROCESSES) { 4051 Slog.d(TAG, "Received spurious death notification for thread " 4052 + thread.asBinder()); 4053 } 4054 } 4055 4056 /** 4057 * If a stack trace dump file is configured, dump process stack traces. 4058 * @param clearTraces causes the dump file to be erased prior to the new 4059 * traces being written, if true; when false, the new traces will be 4060 * appended to any existing file content. 4061 * @param firstPids of dalvik VM processes to dump stack traces for first 4062 * @param lastPids of dalvik VM processes to dump stack traces for last 4063 * @param nativeProcs optional list of native process names to dump stack crawls 4064 * @return file containing stack traces, or null if no dump file is configured 4065 */ 4066 public static File dumpStackTraces(boolean clearTraces, ArrayList<Integer> firstPids, 4067 ProcessCpuTracker processCpuTracker, SparseArray<Boolean> lastPids, String[] nativeProcs) { 4068 String tracesPath = SystemProperties.get("dalvik.vm.stack-trace-file", null); 4069 if (tracesPath == null || tracesPath.length() == 0) { 4070 return null; 4071 } 4072 4073 File tracesFile = new File(tracesPath); 4074 try { 4075 File tracesDir = tracesFile.getParentFile(); 4076 if (!tracesDir.exists()) { 4077 tracesFile.mkdirs(); 4078 if (!SELinux.restorecon(tracesDir)) { 4079 return null; 4080 } 4081 } 4082 FileUtils.setPermissions(tracesDir.getPath(), 0775, -1, -1); // drwxrwxr-x 4083 4084 if (clearTraces && tracesFile.exists()) tracesFile.delete(); 4085 tracesFile.createNewFile(); 4086 FileUtils.setPermissions(tracesFile.getPath(), 0666, -1, -1); // -rw-rw-rw- 4087 } catch (IOException e) { 4088 Slog.w(TAG, "Unable to prepare ANR traces file: " + tracesPath, e); 4089 return null; 4090 } 4091 4092 dumpStackTraces(tracesPath, firstPids, processCpuTracker, lastPids, nativeProcs); 4093 return tracesFile; 4094 } 4095 4096 private static void dumpStackTraces(String tracesPath, ArrayList<Integer> firstPids, 4097 ProcessCpuTracker processCpuTracker, SparseArray<Boolean> lastPids, String[] nativeProcs) { 4098 // Use a FileObserver to detect when traces finish writing. 4099 // The order of traces is considered important to maintain for legibility. 4100 FileObserver observer = new FileObserver(tracesPath, FileObserver.CLOSE_WRITE) { 4101 @Override 4102 public synchronized void onEvent(int event, String path) { notify(); } 4103 }; 4104 4105 try { 4106 observer.startWatching(); 4107 4108 // First collect all of the stacks of the most important pids. 4109 if (firstPids != null) { 4110 try { 4111 int num = firstPids.size(); 4112 for (int i = 0; i < num; i++) { 4113 synchronized (observer) { 4114 Process.sendSignal(firstPids.get(i), Process.SIGNAL_QUIT); 4115 observer.wait(200); // Wait for write-close, give up after 200msec 4116 } 4117 } 4118 } catch (InterruptedException e) { 4119 Log.wtf(TAG, e); 4120 } 4121 } 4122 4123 // Next collect the stacks of the native pids 4124 if (nativeProcs != null) { 4125 int[] pids = Process.getPidsForCommands(nativeProcs); 4126 if (pids != null) { 4127 for (int pid : pids) { 4128 Debug.dumpNativeBacktraceToFile(pid, tracesPath); 4129 } 4130 } 4131 } 4132 4133 // Lastly, measure CPU usage. 4134 if (processCpuTracker != null) { 4135 processCpuTracker.init(); 4136 System.gc(); 4137 processCpuTracker.update(); 4138 try { 4139 synchronized (processCpuTracker) { 4140 processCpuTracker.wait(500); // measure over 1/2 second. 4141 } 4142 } catch (InterruptedException e) { 4143 } 4144 processCpuTracker.update(); 4145 4146 // We'll take the stack crawls of just the top apps using CPU. 4147 final int N = processCpuTracker.countWorkingStats(); 4148 int numProcs = 0; 4149 for (int i=0; i<N && numProcs<5; i++) { 4150 ProcessCpuTracker.Stats stats = processCpuTracker.getWorkingStats(i); 4151 if (lastPids.indexOfKey(stats.pid) >= 0) { 4152 numProcs++; 4153 try { 4154 synchronized (observer) { 4155 Process.sendSignal(stats.pid, Process.SIGNAL_QUIT); 4156 observer.wait(200); // Wait for write-close, give up after 200msec 4157 } 4158 } catch (InterruptedException e) { 4159 Log.wtf(TAG, e); 4160 } 4161 4162 } 4163 } 4164 } 4165 } finally { 4166 observer.stopWatching(); 4167 } 4168 } 4169 4170 final void logAppTooSlow(ProcessRecord app, long startTime, String msg) { 4171 if (true || IS_USER_BUILD) { 4172 return; 4173 } 4174 String tracesPath = SystemProperties.get("dalvik.vm.stack-trace-file", null); 4175 if (tracesPath == null || tracesPath.length() == 0) { 4176 return; 4177 } 4178 4179 StrictMode.ThreadPolicy oldPolicy = StrictMode.allowThreadDiskReads(); 4180 StrictMode.allowThreadDiskWrites(); 4181 try { 4182 final File tracesFile = new File(tracesPath); 4183 final File tracesDir = tracesFile.getParentFile(); 4184 final File tracesTmp = new File(tracesDir, "__tmp__"); 4185 try { 4186 if (!tracesDir.exists()) { 4187 tracesFile.mkdirs(); 4188 if (!SELinux.restorecon(tracesDir.getPath())) { 4189 return; 4190 } 4191 } 4192 FileUtils.setPermissions(tracesDir.getPath(), 0775, -1, -1); // drwxrwxr-x 4193 4194 if (tracesFile.exists()) { 4195 tracesTmp.delete(); 4196 tracesFile.renameTo(tracesTmp); 4197 } 4198 StringBuilder sb = new StringBuilder(); 4199 Time tobj = new Time(); 4200 tobj.set(System.currentTimeMillis()); 4201 sb.append(tobj.format("%Y-%m-%d %H:%M:%S")); 4202 sb.append(": "); 4203 TimeUtils.formatDuration(SystemClock.uptimeMillis()-startTime, sb); 4204 sb.append(" since "); 4205 sb.append(msg); 4206 FileOutputStream fos = new FileOutputStream(tracesFile); 4207 fos.write(sb.toString().getBytes()); 4208 if (app == null) { 4209 fos.write("\n*** No application process!".getBytes()); 4210 } 4211 fos.close(); 4212 FileUtils.setPermissions(tracesFile.getPath(), 0666, -1, -1); // -rw-rw-rw- 4213 } catch (IOException e) { 4214 Slog.w(TAG, "Unable to prepare slow app traces file: " + tracesPath, e); 4215 return; 4216 } 4217 4218 if (app != null) { 4219 ArrayList<Integer> firstPids = new ArrayList<Integer>(); 4220 firstPids.add(app.pid); 4221 dumpStackTraces(tracesPath, firstPids, null, null, null); 4222 } 4223 4224 File lastTracesFile = null; 4225 File curTracesFile = null; 4226 for (int i=9; i>=0; i--) { 4227 String name = String.format(Locale.US, "slow%02d.txt", i); 4228 curTracesFile = new File(tracesDir, name); 4229 if (curTracesFile.exists()) { 4230 if (lastTracesFile != null) { 4231 curTracesFile.renameTo(lastTracesFile); 4232 } else { 4233 curTracesFile.delete(); 4234 } 4235 } 4236 lastTracesFile = curTracesFile; 4237 } 4238 tracesFile.renameTo(curTracesFile); 4239 if (tracesTmp.exists()) { 4240 tracesTmp.renameTo(tracesFile); 4241 } 4242 } finally { 4243 StrictMode.setThreadPolicy(oldPolicy); 4244 } 4245 } 4246 4247 final void appNotResponding(ProcessRecord app, ActivityRecord activity, 4248 ActivityRecord parent, boolean aboveSystem, final String annotation) { 4249 ArrayList<Integer> firstPids = new ArrayList<Integer>(5); 4250 SparseArray<Boolean> lastPids = new SparseArray<Boolean>(20); 4251 4252 if (mController != null) { 4253 try { 4254 // 0 == continue, -1 = kill process immediately 4255 int res = mController.appEarlyNotResponding(app.processName, app.pid, annotation); 4256 if (res < 0 && app.pid != MY_PID) Process.killProcess(app.pid); 4257 } catch (RemoteException e) { 4258 mController = null; 4259 Watchdog.getInstance().setActivityController(null); 4260 } 4261 } 4262 4263 long anrTime = SystemClock.uptimeMillis(); 4264 if (MONITOR_CPU_USAGE) { 4265 updateCpuStatsNow(); 4266 } 4267 4268 synchronized (this) { 4269 // PowerManager.reboot() can block for a long time, so ignore ANRs while shutting down. 4270 if (mShuttingDown) { 4271 Slog.i(TAG, "During shutdown skipping ANR: " + app + " " + annotation); 4272 return; 4273 } else if (app.notResponding) { 4274 Slog.i(TAG, "Skipping duplicate ANR: " + app + " " + annotation); 4275 return; 4276 } else if (app.crashing) { 4277 Slog.i(TAG, "Crashing app skipping ANR: " + app + " " + annotation); 4278 return; 4279 } 4280 4281 // In case we come through here for the same app before completing 4282 // this one, mark as anring now so we will bail out. 4283 app.notResponding = true; 4284 4285 // Log the ANR to the event log. 4286 EventLog.writeEvent(EventLogTags.AM_ANR, app.userId, app.pid, 4287 app.processName, app.info.flags, annotation); 4288 4289 // Dump thread traces as quickly as we can, starting with "interesting" processes. 4290 firstPids.add(app.pid); 4291 4292 int parentPid = app.pid; 4293 if (parent != null && parent.app != null && parent.app.pid > 0) parentPid = parent.app.pid; 4294 if (parentPid != app.pid) firstPids.add(parentPid); 4295 4296 if (MY_PID != app.pid && MY_PID != parentPid) firstPids.add(MY_PID); 4297 4298 for (int i = mLruProcesses.size() - 1; i >= 0; i--) { 4299 ProcessRecord r = mLruProcesses.get(i); 4300 if (r != null && r.thread != null) { 4301 int pid = r.pid; 4302 if (pid > 0 && pid != app.pid && pid != parentPid && pid != MY_PID) { 4303 if (r.persistent) { 4304 firstPids.add(pid); 4305 } else { 4306 lastPids.put(pid, Boolean.TRUE); 4307 } 4308 } 4309 } 4310 } 4311 } 4312 4313 // Log the ANR to the main log. 4314 StringBuilder info = new StringBuilder(); 4315 info.setLength(0); 4316 info.append("ANR in ").append(app.processName); 4317 if (activity != null && activity.shortComponentName != null) { 4318 info.append(" (").append(activity.shortComponentName).append(")"); 4319 } 4320 info.append("\n"); 4321 info.append("PID: ").append(app.pid).append("\n"); 4322 if (annotation != null) { 4323 info.append("Reason: ").append(annotation).append("\n"); 4324 } 4325 if (parent != null && parent != activity) { 4326 info.append("Parent: ").append(parent.shortComponentName).append("\n"); 4327 } 4328 4329 final ProcessCpuTracker processCpuTracker = new ProcessCpuTracker(true); 4330 4331 File tracesFile = dumpStackTraces(true, firstPids, processCpuTracker, lastPids, 4332 NATIVE_STACKS_OF_INTEREST); 4333 4334 String cpuInfo = null; 4335 if (MONITOR_CPU_USAGE) { 4336 updateCpuStatsNow(); 4337 synchronized (mProcessCpuThread) { 4338 cpuInfo = mProcessCpuTracker.printCurrentState(anrTime); 4339 } 4340 info.append(processCpuTracker.printCurrentLoad()); 4341 info.append(cpuInfo); 4342 } 4343 4344 info.append(processCpuTracker.printCurrentState(anrTime)); 4345 4346 Slog.e(TAG, info.toString()); 4347 if (tracesFile == null) { 4348 // There is no trace file, so dump (only) the alleged culprit's threads to the log 4349 Process.sendSignal(app.pid, Process.SIGNAL_QUIT); 4350 } 4351 4352 addErrorToDropBox("anr", app, app.processName, activity, parent, annotation, 4353 cpuInfo, tracesFile, null); 4354 4355 if (mController != null) { 4356 try { 4357 // 0 == show dialog, 1 = keep waiting, -1 = kill process immediately 4358 int res = mController.appNotResponding(app.processName, app.pid, info.toString()); 4359 if (res != 0) { 4360 if (res < 0 && app.pid != MY_PID) { 4361 Process.killProcess(app.pid); 4362 } else { 4363 synchronized (this) { 4364 mServices.scheduleServiceTimeoutLocked(app); 4365 } 4366 } 4367 return; 4368 } 4369 } catch (RemoteException e) { 4370 mController = null; 4371 Watchdog.getInstance().setActivityController(null); 4372 } 4373 } 4374 4375 // Unless configured otherwise, swallow ANRs in background processes & kill the process. 4376 boolean showBackground = Settings.Secure.getInt(mContext.getContentResolver(), 4377 Settings.Secure.ANR_SHOW_BACKGROUND, 0) != 0; 4378 4379 synchronized (this) { 4380 if (!showBackground && !app.isInterestingToUserLocked() && app.pid != MY_PID) { 4381 killUnneededProcessLocked(app, "background ANR"); 4382 return; 4383 } 4384 4385 // Set the app's notResponding state, and look up the errorReportReceiver 4386 makeAppNotRespondingLocked(app, 4387 activity != null ? activity.shortComponentName : null, 4388 annotation != null ? "ANR " + annotation : "ANR", 4389 info.toString()); 4390 4391 // Bring up the infamous App Not Responding dialog 4392 Message msg = Message.obtain(); 4393 HashMap<String, Object> map = new HashMap<String, Object>(); 4394 msg.what = SHOW_NOT_RESPONDING_MSG; 4395 msg.obj = map; 4396 msg.arg1 = aboveSystem ? 1 : 0; 4397 map.put("app", app); 4398 if (activity != null) { 4399 map.put("activity", activity); 4400 } 4401 4402 mHandler.sendMessage(msg); 4403 } 4404 } 4405 4406 final void showLaunchWarningLocked(final ActivityRecord cur, final ActivityRecord next) { 4407 if (!mLaunchWarningShown) { 4408 mLaunchWarningShown = true; 4409 mHandler.post(new Runnable() { 4410 @Override 4411 public void run() { 4412 synchronized (ActivityManagerService.this) { 4413 final Dialog d = new LaunchWarningWindow(mContext, cur, next); 4414 d.show(); 4415 mHandler.postDelayed(new Runnable() { 4416 @Override 4417 public void run() { 4418 synchronized (ActivityManagerService.this) { 4419 d.dismiss(); 4420 mLaunchWarningShown = false; 4421 } 4422 } 4423 }, 4000); 4424 } 4425 } 4426 }); 4427 } 4428 } 4429 4430 @Override 4431 public boolean clearApplicationUserData(final String packageName, 4432 final IPackageDataObserver observer, int userId) { 4433 enforceNotIsolatedCaller("clearApplicationUserData"); 4434 int uid = Binder.getCallingUid(); 4435 int pid = Binder.getCallingPid(); 4436 userId = handleIncomingUser(pid, uid, 4437 userId, false, true, "clearApplicationUserData", null); 4438 long callingId = Binder.clearCallingIdentity(); 4439 try { 4440 IPackageManager pm = AppGlobals.getPackageManager(); 4441 int pkgUid = -1; 4442 synchronized(this) { 4443 try { 4444 pkgUid = pm.getPackageUid(packageName, userId); 4445 } catch (RemoteException e) { 4446 } 4447 if (pkgUid == -1) { 4448 Slog.w(TAG, "Invalid packageName: " + packageName); 4449 if (observer != null) { 4450 try { 4451 observer.onRemoveCompleted(packageName, false); 4452 } catch (RemoteException e) { 4453 Slog.i(TAG, "Observer no longer exists."); 4454 } 4455 } 4456 return false; 4457 } 4458 if (uid == pkgUid || checkComponentPermission( 4459 android.Manifest.permission.CLEAR_APP_USER_DATA, 4460 pid, uid, -1, true) 4461 == PackageManager.PERMISSION_GRANTED) { 4462 forceStopPackageLocked(packageName, pkgUid, "clear data"); 4463 } else { 4464 throw new SecurityException("PID " + pid + " does not have permission " 4465 + android.Manifest.permission.CLEAR_APP_USER_DATA + " to clear data" 4466 + " of package " + packageName); 4467 } 4468 } 4469 4470 try { 4471 // Clear application user data 4472 pm.clearApplicationUserData(packageName, observer, userId); 4473 4474 // Remove all permissions granted from/to this package 4475 removeUriPermissionsForPackageLocked(packageName, userId, true); 4476 4477 Intent intent = new Intent(Intent.ACTION_PACKAGE_DATA_CLEARED, 4478 Uri.fromParts("package", packageName, null)); 4479 intent.putExtra(Intent.EXTRA_UID, pkgUid); 4480 broadcastIntentInPackage("android", Process.SYSTEM_UID, intent, 4481 null, null, 0, null, null, null, false, false, userId); 4482 } catch (RemoteException e) { 4483 } 4484 } finally { 4485 Binder.restoreCallingIdentity(callingId); 4486 } 4487 return true; 4488 } 4489 4490 @Override 4491 public void killBackgroundProcesses(final String packageName, int userId) { 4492 if (checkCallingPermission(android.Manifest.permission.KILL_BACKGROUND_PROCESSES) 4493 != PackageManager.PERMISSION_GRANTED && 4494 checkCallingPermission(android.Manifest.permission.RESTART_PACKAGES) 4495 != PackageManager.PERMISSION_GRANTED) { 4496 String msg = "Permission Denial: killBackgroundProcesses() from pid=" 4497 + Binder.getCallingPid() 4498 + ", uid=" + Binder.getCallingUid() 4499 + " requires " + android.Manifest.permission.KILL_BACKGROUND_PROCESSES; 4500 Slog.w(TAG, msg); 4501 throw new SecurityException(msg); 4502 } 4503 4504 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 4505 userId, true, true, "killBackgroundProcesses", null); 4506 long callingId = Binder.clearCallingIdentity(); 4507 try { 4508 IPackageManager pm = AppGlobals.getPackageManager(); 4509 synchronized(this) { 4510 int appId = -1; 4511 try { 4512 appId = UserHandle.getAppId(pm.getPackageUid(packageName, 0)); 4513 } catch (RemoteException e) { 4514 } 4515 if (appId == -1) { 4516 Slog.w(TAG, "Invalid packageName: " + packageName); 4517 return; 4518 } 4519 killPackageProcessesLocked(packageName, appId, userId, 4520 ProcessList.SERVICE_ADJ, false, true, true, false, "kill background"); 4521 } 4522 } finally { 4523 Binder.restoreCallingIdentity(callingId); 4524 } 4525 } 4526 4527 @Override 4528 public void killAllBackgroundProcesses() { 4529 if (checkCallingPermission(android.Manifest.permission.KILL_BACKGROUND_PROCESSES) 4530 != PackageManager.PERMISSION_GRANTED) { 4531 String msg = "Permission Denial: killAllBackgroundProcesses() from pid=" 4532 + Binder.getCallingPid() 4533 + ", uid=" + Binder.getCallingUid() 4534 + " requires " + android.Manifest.permission.KILL_BACKGROUND_PROCESSES; 4535 Slog.w(TAG, msg); 4536 throw new SecurityException(msg); 4537 } 4538 4539 long callingId = Binder.clearCallingIdentity(); 4540 try { 4541 synchronized(this) { 4542 ArrayList<ProcessRecord> procs = new ArrayList<ProcessRecord>(); 4543 final int NP = mProcessNames.getMap().size(); 4544 for (int ip=0; ip<NP; ip++) { 4545 SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 4546 final int NA = apps.size(); 4547 for (int ia=0; ia<NA; ia++) { 4548 ProcessRecord app = apps.valueAt(ia); 4549 if (app.persistent) { 4550 // we don't kill persistent processes 4551 continue; 4552 } 4553 if (app.removed) { 4554 procs.add(app); 4555 } else if (app.setAdj >= ProcessList.CACHED_APP_MIN_ADJ) { 4556 app.removed = true; 4557 procs.add(app); 4558 } 4559 } 4560 } 4561 4562 int N = procs.size(); 4563 for (int i=0; i<N; i++) { 4564 removeProcessLocked(procs.get(i), false, true, "kill all background"); 4565 } 4566 mAllowLowerMemLevel = true; 4567 updateOomAdjLocked(); 4568 doLowMemReportIfNeededLocked(null); 4569 } 4570 } finally { 4571 Binder.restoreCallingIdentity(callingId); 4572 } 4573 } 4574 4575 @Override 4576 public void forceStopPackage(final String packageName, int userId) { 4577 if (checkCallingPermission(android.Manifest.permission.FORCE_STOP_PACKAGES) 4578 != PackageManager.PERMISSION_GRANTED) { 4579 String msg = "Permission Denial: forceStopPackage() from pid=" 4580 + Binder.getCallingPid() 4581 + ", uid=" + Binder.getCallingUid() 4582 + " requires " + android.Manifest.permission.FORCE_STOP_PACKAGES; 4583 Slog.w(TAG, msg); 4584 throw new SecurityException(msg); 4585 } 4586 final int callingPid = Binder.getCallingPid(); 4587 userId = handleIncomingUser(callingPid, Binder.getCallingUid(), 4588 userId, true, true, "forceStopPackage", null); 4589 long callingId = Binder.clearCallingIdentity(); 4590 try { 4591 IPackageManager pm = AppGlobals.getPackageManager(); 4592 synchronized(this) { 4593 int[] users = userId == UserHandle.USER_ALL 4594 ? getUsersLocked() : new int[] { userId }; 4595 for (int user : users) { 4596 int pkgUid = -1; 4597 try { 4598 pkgUid = pm.getPackageUid(packageName, user); 4599 } catch (RemoteException e) { 4600 } 4601 if (pkgUid == -1) { 4602 Slog.w(TAG, "Invalid packageName: " + packageName); 4603 continue; 4604 } 4605 try { 4606 pm.setPackageStoppedState(packageName, true, user); 4607 } catch (RemoteException e) { 4608 } catch (IllegalArgumentException e) { 4609 Slog.w(TAG, "Failed trying to unstop package " 4610 + packageName + ": " + e); 4611 } 4612 if (isUserRunningLocked(user, false)) { 4613 forceStopPackageLocked(packageName, pkgUid, "from pid " + callingPid); 4614 } 4615 } 4616 } 4617 } finally { 4618 Binder.restoreCallingIdentity(callingId); 4619 } 4620 } 4621 4622 /* 4623 * The pkg name and app id have to be specified. 4624 */ 4625 @Override 4626 public void killApplicationWithAppId(String pkg, int appid, String reason) { 4627 if (pkg == null) { 4628 return; 4629 } 4630 // Make sure the uid is valid. 4631 if (appid < 0) { 4632 Slog.w(TAG, "Invalid appid specified for pkg : " + pkg); 4633 return; 4634 } 4635 int callerUid = Binder.getCallingUid(); 4636 // Only the system server can kill an application 4637 if (callerUid == Process.SYSTEM_UID) { 4638 // Post an aysnc message to kill the application 4639 Message msg = mHandler.obtainMessage(KILL_APPLICATION_MSG); 4640 msg.arg1 = appid; 4641 msg.arg2 = 0; 4642 Bundle bundle = new Bundle(); 4643 bundle.putString("pkg", pkg); 4644 bundle.putString("reason", reason); 4645 msg.obj = bundle; 4646 mHandler.sendMessage(msg); 4647 } else { 4648 throw new SecurityException(callerUid + " cannot kill pkg: " + 4649 pkg); 4650 } 4651 } 4652 4653 @Override 4654 public void closeSystemDialogs(String reason) { 4655 enforceNotIsolatedCaller("closeSystemDialogs"); 4656 4657 final int pid = Binder.getCallingPid(); 4658 final int uid = Binder.getCallingUid(); 4659 final long origId = Binder.clearCallingIdentity(); 4660 try { 4661 synchronized (this) { 4662 // Only allow this from foreground processes, so that background 4663 // applications can't abuse it to prevent system UI from being shown. 4664 if (uid >= Process.FIRST_APPLICATION_UID) { 4665 ProcessRecord proc; 4666 synchronized (mPidsSelfLocked) { 4667 proc = mPidsSelfLocked.get(pid); 4668 } 4669 if (proc.curRawAdj > ProcessList.PERCEPTIBLE_APP_ADJ) { 4670 Slog.w(TAG, "Ignoring closeSystemDialogs " + reason 4671 + " from background process " + proc); 4672 return; 4673 } 4674 } 4675 closeSystemDialogsLocked(reason); 4676 } 4677 } finally { 4678 Binder.restoreCallingIdentity(origId); 4679 } 4680 } 4681 4682 void closeSystemDialogsLocked(String reason) { 4683 Intent intent = new Intent(Intent.ACTION_CLOSE_SYSTEM_DIALOGS); 4684 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 4685 | Intent.FLAG_RECEIVER_FOREGROUND); 4686 if (reason != null) { 4687 intent.putExtra("reason", reason); 4688 } 4689 mWindowManager.closeSystemDialogs(reason); 4690 4691 mStackSupervisor.closeSystemDialogsLocked(); 4692 4693 broadcastIntentLocked(null, null, intent, null, 4694 null, 0, null, null, null, AppOpsManager.OP_NONE, false, false, -1, 4695 Process.SYSTEM_UID, UserHandle.USER_ALL); 4696 } 4697 4698 @Override 4699 public Debug.MemoryInfo[] getProcessMemoryInfo(int[] pids) { 4700 enforceNotIsolatedCaller("getProcessMemoryInfo"); 4701 Debug.MemoryInfo[] infos = new Debug.MemoryInfo[pids.length]; 4702 for (int i=pids.length-1; i>=0; i--) { 4703 ProcessRecord proc; 4704 int oomAdj; 4705 synchronized (this) { 4706 synchronized (mPidsSelfLocked) { 4707 proc = mPidsSelfLocked.get(pids[i]); 4708 oomAdj = proc != null ? proc.setAdj : 0; 4709 } 4710 } 4711 infos[i] = new Debug.MemoryInfo(); 4712 Debug.getMemoryInfo(pids[i], infos[i]); 4713 if (proc != null) { 4714 synchronized (this) { 4715 if (proc.thread != null && proc.setAdj == oomAdj) { 4716 // Record this for posterity if the process has been stable. 4717 proc.baseProcessTracker.addPss(infos[i].getTotalPss(), 4718 infos[i].getTotalUss(), false, proc.pkgList); 4719 } 4720 } 4721 } 4722 } 4723 return infos; 4724 } 4725 4726 @Override 4727 public long[] getProcessPss(int[] pids) { 4728 enforceNotIsolatedCaller("getProcessPss"); 4729 long[] pss = new long[pids.length]; 4730 for (int i=pids.length-1; i>=0; i--) { 4731 ProcessRecord proc; 4732 int oomAdj; 4733 synchronized (this) { 4734 synchronized (mPidsSelfLocked) { 4735 proc = mPidsSelfLocked.get(pids[i]); 4736 oomAdj = proc != null ? proc.setAdj : 0; 4737 } 4738 } 4739 long[] tmpUss = new long[1]; 4740 pss[i] = Debug.getPss(pids[i], tmpUss); 4741 if (proc != null) { 4742 synchronized (this) { 4743 if (proc.thread != null && proc.setAdj == oomAdj) { 4744 // Record this for posterity if the process has been stable. 4745 proc.baseProcessTracker.addPss(pss[i], tmpUss[0], false, proc.pkgList); 4746 } 4747 } 4748 } 4749 } 4750 return pss; 4751 } 4752 4753 @Override 4754 public void killApplicationProcess(String processName, int uid) { 4755 if (processName == null) { 4756 return; 4757 } 4758 4759 int callerUid = Binder.getCallingUid(); 4760 // Only the system server can kill an application 4761 if (callerUid == Process.SYSTEM_UID) { 4762 synchronized (this) { 4763 ProcessRecord app = getProcessRecordLocked(processName, uid, true); 4764 if (app != null && app.thread != null) { 4765 try { 4766 app.thread.scheduleSuicide(); 4767 } catch (RemoteException e) { 4768 // If the other end already died, then our work here is done. 4769 } 4770 } else { 4771 Slog.w(TAG, "Process/uid not found attempting kill of " 4772 + processName + " / " + uid); 4773 } 4774 } 4775 } else { 4776 throw new SecurityException(callerUid + " cannot kill app process: " + 4777 processName); 4778 } 4779 } 4780 4781 private void forceStopPackageLocked(final String packageName, int uid, String reason) { 4782 forceStopPackageLocked(packageName, UserHandle.getAppId(uid), false, 4783 false, true, false, false, UserHandle.getUserId(uid), reason); 4784 Intent intent = new Intent(Intent.ACTION_PACKAGE_RESTARTED, 4785 Uri.fromParts("package", packageName, null)); 4786 if (!mProcessesReady) { 4787 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 4788 | Intent.FLAG_RECEIVER_FOREGROUND); 4789 } 4790 intent.putExtra(Intent.EXTRA_UID, uid); 4791 intent.putExtra(Intent.EXTRA_USER_HANDLE, UserHandle.getUserId(uid)); 4792 broadcastIntentLocked(null, null, intent, 4793 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 4794 false, false, 4795 MY_PID, Process.SYSTEM_UID, UserHandle.getUserId(uid)); 4796 } 4797 4798 private void forceStopUserLocked(int userId, String reason) { 4799 forceStopPackageLocked(null, -1, false, false, true, false, false, userId, reason); 4800 Intent intent = new Intent(Intent.ACTION_USER_STOPPED); 4801 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 4802 | Intent.FLAG_RECEIVER_FOREGROUND); 4803 intent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 4804 broadcastIntentLocked(null, null, intent, 4805 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 4806 false, false, 4807 MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 4808 } 4809 4810 private final boolean killPackageProcessesLocked(String packageName, int appId, 4811 int userId, int minOomAdj, boolean callerWillRestart, boolean allowRestart, 4812 boolean doit, boolean evenPersistent, String reason) { 4813 ArrayList<ProcessRecord> procs = new ArrayList<ProcessRecord>(); 4814 4815 // Remove all processes this package may have touched: all with the 4816 // same UID (except for the system or root user), and all whose name 4817 // matches the package name. 4818 final String procNamePrefix = packageName != null ? (packageName + ":") : null; 4819 final int NP = mProcessNames.getMap().size(); 4820 for (int ip=0; ip<NP; ip++) { 4821 SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 4822 final int NA = apps.size(); 4823 for (int ia=0; ia<NA; ia++) { 4824 ProcessRecord app = apps.valueAt(ia); 4825 if (app.persistent && !evenPersistent) { 4826 // we don't kill persistent processes 4827 continue; 4828 } 4829 if (app.removed) { 4830 if (doit) { 4831 procs.add(app); 4832 } 4833 continue; 4834 } 4835 4836 // Skip process if it doesn't meet our oom adj requirement. 4837 if (app.setAdj < minOomAdj) { 4838 continue; 4839 } 4840 4841 // If no package is specified, we call all processes under the 4842 // give user id. 4843 if (packageName == null) { 4844 if (app.userId != userId) { 4845 continue; 4846 } 4847 if (appId >= 0 && UserHandle.getAppId(app.uid) != appId) { 4848 continue; 4849 } 4850 // Package has been specified, we want to hit all processes 4851 // that match it. We need to qualify this by the processes 4852 // that are running under the specified app and user ID. 4853 } else { 4854 if (UserHandle.getAppId(app.uid) != appId) { 4855 continue; 4856 } 4857 if (userId != UserHandle.USER_ALL && app.userId != userId) { 4858 continue; 4859 } 4860 if (!app.pkgList.containsKey(packageName)) { 4861 continue; 4862 } 4863 } 4864 4865 // Process has passed all conditions, kill it! 4866 if (!doit) { 4867 return true; 4868 } 4869 app.removed = true; 4870 procs.add(app); 4871 } 4872 } 4873 4874 int N = procs.size(); 4875 for (int i=0; i<N; i++) { 4876 removeProcessLocked(procs.get(i), callerWillRestart, allowRestart, reason); 4877 } 4878 updateOomAdjLocked(); 4879 return N > 0; 4880 } 4881 4882 private final boolean forceStopPackageLocked(String name, int appId, 4883 boolean callerWillRestart, boolean purgeCache, boolean doit, 4884 boolean evenPersistent, boolean uninstalling, int userId, String reason) { 4885 int i; 4886 int N; 4887 4888 if (userId == UserHandle.USER_ALL && name == null) { 4889 Slog.w(TAG, "Can't force stop all processes of all users, that is insane!"); 4890 } 4891 4892 if (appId < 0 && name != null) { 4893 try { 4894 appId = UserHandle.getAppId( 4895 AppGlobals.getPackageManager().getPackageUid(name, 0)); 4896 } catch (RemoteException e) { 4897 } 4898 } 4899 4900 if (doit) { 4901 if (name != null) { 4902 Slog.i(TAG, "Force stopping " + name + " appid=" + appId 4903 + " user=" + userId + ": " + reason); 4904 } else { 4905 Slog.i(TAG, "Force stopping u" + userId + ": " + reason); 4906 } 4907 4908 final ArrayMap<String, SparseArray<Long>> pmap = mProcessCrashTimes.getMap(); 4909 for (int ip=pmap.size()-1; ip>=0; ip--) { 4910 SparseArray<Long> ba = pmap.valueAt(ip); 4911 for (i=ba.size()-1; i>=0; i--) { 4912 boolean remove = false; 4913 final int entUid = ba.keyAt(i); 4914 if (name != null) { 4915 if (userId == UserHandle.USER_ALL) { 4916 if (UserHandle.getAppId(entUid) == appId) { 4917 remove = true; 4918 } 4919 } else { 4920 if (entUid == UserHandle.getUid(userId, appId)) { 4921 remove = true; 4922 } 4923 } 4924 } else if (UserHandle.getUserId(entUid) == userId) { 4925 remove = true; 4926 } 4927 if (remove) { 4928 ba.removeAt(i); 4929 } 4930 } 4931 if (ba.size() == 0) { 4932 pmap.removeAt(ip); 4933 } 4934 } 4935 } 4936 4937 boolean didSomething = killPackageProcessesLocked(name, appId, userId, 4938 -100, callerWillRestart, true, doit, evenPersistent, 4939 name == null ? ("stop user " + userId) : ("stop " + name)); 4940 4941 if (mStackSupervisor.forceStopPackageLocked(name, doit, evenPersistent, userId)) { 4942 if (!doit) { 4943 return true; 4944 } 4945 didSomething = true; 4946 } 4947 4948 if (mServices.forceStopLocked(name, userId, evenPersistent, doit)) { 4949 if (!doit) { 4950 return true; 4951 } 4952 didSomething = true; 4953 } 4954 4955 if (name == null) { 4956 // Remove all sticky broadcasts from this user. 4957 mStickyBroadcasts.remove(userId); 4958 } 4959 4960 ArrayList<ContentProviderRecord> providers = new ArrayList<ContentProviderRecord>(); 4961 if (mProviderMap.collectForceStopProviders(name, appId, doit, evenPersistent, 4962 userId, providers)) { 4963 if (!doit) { 4964 return true; 4965 } 4966 didSomething = true; 4967 } 4968 N = providers.size(); 4969 for (i=0; i<N; i++) { 4970 removeDyingProviderLocked(null, providers.get(i), true); 4971 } 4972 4973 // Remove transient permissions granted from/to this package/user 4974 removeUriPermissionsForPackageLocked(name, userId, false); 4975 4976 if (name == null || uninstalling) { 4977 // Remove pending intents. For now we only do this when force 4978 // stopping users, because we have some problems when doing this 4979 // for packages -- app widgets are not currently cleaned up for 4980 // such packages, so they can be left with bad pending intents. 4981 if (mIntentSenderRecords.size() > 0) { 4982 Iterator<WeakReference<PendingIntentRecord>> it 4983 = mIntentSenderRecords.values().iterator(); 4984 while (it.hasNext()) { 4985 WeakReference<PendingIntentRecord> wpir = it.next(); 4986 if (wpir == null) { 4987 it.remove(); 4988 continue; 4989 } 4990 PendingIntentRecord pir = wpir.get(); 4991 if (pir == null) { 4992 it.remove(); 4993 continue; 4994 } 4995 if (name == null) { 4996 // Stopping user, remove all objects for the user. 4997 if (pir.key.userId != userId) { 4998 // Not the same user, skip it. 4999 continue; 5000 } 5001 } else { 5002 if (UserHandle.getAppId(pir.uid) != appId) { 5003 // Different app id, skip it. 5004 continue; 5005 } 5006 if (userId != UserHandle.USER_ALL && pir.key.userId != userId) { 5007 // Different user, skip it. 5008 continue; 5009 } 5010 if (!pir.key.packageName.equals(name)) { 5011 // Different package, skip it. 5012 continue; 5013 } 5014 } 5015 if (!doit) { 5016 return true; 5017 } 5018 didSomething = true; 5019 it.remove(); 5020 pir.canceled = true; 5021 if (pir.key.activity != null) { 5022 pir.key.activity.pendingResults.remove(pir.ref); 5023 } 5024 } 5025 } 5026 } 5027 5028 if (doit) { 5029 if (purgeCache && name != null) { 5030 AttributeCache ac = AttributeCache.instance(); 5031 if (ac != null) { 5032 ac.removePackage(name); 5033 } 5034 } 5035 if (mBooted) { 5036 mStackSupervisor.resumeTopActivitiesLocked(); 5037 mStackSupervisor.scheduleIdleLocked(); 5038 } 5039 } 5040 5041 return didSomething; 5042 } 5043 5044 private final boolean removeProcessLocked(ProcessRecord app, 5045 boolean callerWillRestart, boolean allowRestart, String reason) { 5046 final String name = app.processName; 5047 final int uid = app.uid; 5048 if (DEBUG_PROCESSES) Slog.d( 5049 TAG, "Force removing proc " + app.toShortString() + " (" + name 5050 + "/" + uid + ")"); 5051 5052 mProcessNames.remove(name, uid); 5053 mIsolatedProcesses.remove(app.uid); 5054 if (mHeavyWeightProcess == app) { 5055 mHandler.sendMessage(mHandler.obtainMessage(CANCEL_HEAVY_NOTIFICATION_MSG, 5056 mHeavyWeightProcess.userId, 0)); 5057 mHeavyWeightProcess = null; 5058 } 5059 boolean needRestart = false; 5060 if (app.pid > 0 && app.pid != MY_PID) { 5061 int pid = app.pid; 5062 synchronized (mPidsSelfLocked) { 5063 mPidsSelfLocked.remove(pid); 5064 mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app); 5065 } 5066 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_PROC_FINISH, 5067 app.processName, app.info.uid); 5068 if (app.isolated) { 5069 mBatteryStatsService.removeIsolatedUid(app.uid, app.info.uid); 5070 } 5071 killUnneededProcessLocked(app, reason); 5072 handleAppDiedLocked(app, true, allowRestart); 5073 removeLruProcessLocked(app); 5074 5075 if (app.persistent && !app.isolated) { 5076 if (!callerWillRestart) { 5077 addAppLocked(app.info, false, null /* ABI override */); 5078 } else { 5079 needRestart = true; 5080 } 5081 } 5082 } else { 5083 mRemovedProcesses.add(app); 5084 } 5085 5086 return needRestart; 5087 } 5088 5089 private final void processStartTimedOutLocked(ProcessRecord app) { 5090 final int pid = app.pid; 5091 boolean gone = false; 5092 synchronized (mPidsSelfLocked) { 5093 ProcessRecord knownApp = mPidsSelfLocked.get(pid); 5094 if (knownApp != null && knownApp.thread == null) { 5095 mPidsSelfLocked.remove(pid); 5096 gone = true; 5097 } 5098 } 5099 5100 if (gone) { 5101 Slog.w(TAG, "Process " + app + " failed to attach"); 5102 EventLog.writeEvent(EventLogTags.AM_PROCESS_START_TIMEOUT, app.userId, 5103 pid, app.uid, app.processName); 5104 mProcessNames.remove(app.processName, app.uid); 5105 mIsolatedProcesses.remove(app.uid); 5106 if (mHeavyWeightProcess == app) { 5107 mHandler.sendMessage(mHandler.obtainMessage(CANCEL_HEAVY_NOTIFICATION_MSG, 5108 mHeavyWeightProcess.userId, 0)); 5109 mHeavyWeightProcess = null; 5110 } 5111 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_PROC_FINISH, 5112 app.processName, app.info.uid); 5113 if (app.isolated) { 5114 mBatteryStatsService.removeIsolatedUid(app.uid, app.info.uid); 5115 } 5116 // Take care of any launching providers waiting for this process. 5117 checkAppInLaunchingProvidersLocked(app, true); 5118 // Take care of any services that are waiting for the process. 5119 mServices.processStartTimedOutLocked(app); 5120 killUnneededProcessLocked(app, "start timeout"); 5121 if (mBackupTarget != null && mBackupTarget.app.pid == pid) { 5122 Slog.w(TAG, "Unattached app died before backup, skipping"); 5123 try { 5124 IBackupManager bm = IBackupManager.Stub.asInterface( 5125 ServiceManager.getService(Context.BACKUP_SERVICE)); 5126 bm.agentDisconnected(app.info.packageName); 5127 } catch (RemoteException e) { 5128 // Can't happen; the backup manager is local 5129 } 5130 } 5131 if (isPendingBroadcastProcessLocked(pid)) { 5132 Slog.w(TAG, "Unattached app died before broadcast acknowledged, skipping"); 5133 skipPendingBroadcastLocked(pid); 5134 } 5135 } else { 5136 Slog.w(TAG, "Spurious process start timeout - pid not known for " + app); 5137 } 5138 } 5139 5140 private final boolean attachApplicationLocked(IApplicationThread thread, 5141 int pid) { 5142 5143 // Find the application record that is being attached... either via 5144 // the pid if we are running in multiple processes, or just pull the 5145 // next app record if we are emulating process with anonymous threads. 5146 ProcessRecord app; 5147 if (pid != MY_PID && pid >= 0) { 5148 synchronized (mPidsSelfLocked) { 5149 app = mPidsSelfLocked.get(pid); 5150 } 5151 } else { 5152 app = null; 5153 } 5154 5155 if (app == null) { 5156 Slog.w(TAG, "No pending application record for pid " + pid 5157 + " (IApplicationThread " + thread + "); dropping process"); 5158 EventLog.writeEvent(EventLogTags.AM_DROP_PROCESS, pid); 5159 if (pid > 0 && pid != MY_PID) { 5160 Process.killProcessQuiet(pid); 5161 } else { 5162 try { 5163 thread.scheduleExit(); 5164 } catch (Exception e) { 5165 // Ignore exceptions. 5166 } 5167 } 5168 return false; 5169 } 5170 5171 // If this application record is still attached to a previous 5172 // process, clean it up now. 5173 if (app.thread != null) { 5174 handleAppDiedLocked(app, true, true); 5175 } 5176 5177 // Tell the process all about itself. 5178 5179 if (localLOGV) Slog.v( 5180 TAG, "Binding process pid " + pid + " to record " + app); 5181 5182 final String processName = app.processName; 5183 try { 5184 AppDeathRecipient adr = new AppDeathRecipient( 5185 app, pid, thread); 5186 thread.asBinder().linkToDeath(adr, 0); 5187 app.deathRecipient = adr; 5188 } catch (RemoteException e) { 5189 app.resetPackageList(mProcessStats); 5190 startProcessLocked(app, "link fail", processName, null /* ABI override */); 5191 return false; 5192 } 5193 5194 EventLog.writeEvent(EventLogTags.AM_PROC_BOUND, app.userId, app.pid, app.processName); 5195 5196 app.makeActive(thread, mProcessStats); 5197 app.curAdj = app.setAdj = -100; 5198 app.curSchedGroup = app.setSchedGroup = Process.THREAD_GROUP_DEFAULT; 5199 app.forcingToForeground = null; 5200 updateProcessForegroundLocked(app, false, false); 5201 app.hasShownUi = false; 5202 app.debugging = false; 5203 app.cached = false; 5204 5205 mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app); 5206 5207 boolean normalMode = mProcessesReady || isAllowedWhileBooting(app.info); 5208 List<ProviderInfo> providers = normalMode ? generateApplicationProvidersLocked(app) : null; 5209 5210 if (!normalMode) { 5211 Slog.i(TAG, "Launching preboot mode app: " + app); 5212 } 5213 5214 if (localLOGV) Slog.v( 5215 TAG, "New app record " + app 5216 + " thread=" + thread.asBinder() + " pid=" + pid); 5217 try { 5218 int testMode = IApplicationThread.DEBUG_OFF; 5219 if (mDebugApp != null && mDebugApp.equals(processName)) { 5220 testMode = mWaitForDebugger 5221 ? IApplicationThread.DEBUG_WAIT 5222 : IApplicationThread.DEBUG_ON; 5223 app.debugging = true; 5224 if (mDebugTransient) { 5225 mDebugApp = mOrigDebugApp; 5226 mWaitForDebugger = mOrigWaitForDebugger; 5227 } 5228 } 5229 String profileFile = app.instrumentationProfileFile; 5230 ParcelFileDescriptor profileFd = null; 5231 boolean profileAutoStop = false; 5232 if (mProfileApp != null && mProfileApp.equals(processName)) { 5233 mProfileProc = app; 5234 profileFile = mProfileFile; 5235 profileFd = mProfileFd; 5236 profileAutoStop = mAutoStopProfiler; 5237 } 5238 boolean enableOpenGlTrace = false; 5239 if (mOpenGlTraceApp != null && mOpenGlTraceApp.equals(processName)) { 5240 enableOpenGlTrace = true; 5241 mOpenGlTraceApp = null; 5242 } 5243 5244 // If the app is being launched for restore or full backup, set it up specially 5245 boolean isRestrictedBackupMode = false; 5246 if (mBackupTarget != null && mBackupAppName.equals(processName)) { 5247 isRestrictedBackupMode = (mBackupTarget.backupMode == BackupRecord.RESTORE) 5248 || (mBackupTarget.backupMode == BackupRecord.RESTORE_FULL) 5249 || (mBackupTarget.backupMode == BackupRecord.BACKUP_FULL); 5250 } 5251 5252 ensurePackageDexOpt(app.instrumentationInfo != null 5253 ? app.instrumentationInfo.packageName 5254 : app.info.packageName); 5255 if (app.instrumentationClass != null) { 5256 ensurePackageDexOpt(app.instrumentationClass.getPackageName()); 5257 } 5258 if (DEBUG_CONFIGURATION) Slog.v(TAG, "Binding proc " 5259 + processName + " with config " + mConfiguration); 5260 ApplicationInfo appInfo = app.instrumentationInfo != null 5261 ? app.instrumentationInfo : app.info; 5262 app.compat = compatibilityInfoForPackageLocked(appInfo); 5263 if (profileFd != null) { 5264 profileFd = profileFd.dup(); 5265 } 5266 thread.bindApplication(processName, appInfo, providers, 5267 app.instrumentationClass, profileFile, profileFd, profileAutoStop, 5268 app.instrumentationArguments, app.instrumentationWatcher, 5269 app.instrumentationUiAutomationConnection, testMode, enableOpenGlTrace, 5270 isRestrictedBackupMode || !normalMode, app.persistent, 5271 new Configuration(mConfiguration), app.compat, getCommonServicesLocked(), 5272 mCoreSettingsObserver.getCoreSettingsLocked()); 5273 updateLruProcessLocked(app, false, null); 5274 app.lastRequestedGc = app.lastLowMemory = SystemClock.uptimeMillis(); 5275 } catch (Exception e) { 5276 // todo: Yikes! What should we do? For now we will try to 5277 // start another process, but that could easily get us in 5278 // an infinite loop of restarting processes... 5279 Slog.w(TAG, "Exception thrown during bind!", e); 5280 5281 app.resetPackageList(mProcessStats); 5282 app.unlinkDeathRecipient(); 5283 startProcessLocked(app, "bind fail", processName, null /* ABI override */); 5284 return false; 5285 } 5286 5287 // Remove this record from the list of starting applications. 5288 mPersistentStartingProcesses.remove(app); 5289 if (DEBUG_PROCESSES && mProcessesOnHold.contains(app)) Slog.v(TAG, 5290 "Attach application locked removing on hold: " + app); 5291 mProcessesOnHold.remove(app); 5292 5293 boolean badApp = false; 5294 boolean didSomething = false; 5295 5296 // See if the top visible activity is waiting to run in this process... 5297 if (normalMode) { 5298 try { 5299 if (mStackSupervisor.attachApplicationLocked(app)) { 5300 didSomething = true; 5301 } 5302 } catch (Exception e) { 5303 badApp = true; 5304 } 5305 } 5306 5307 // Find any services that should be running in this process... 5308 if (!badApp) { 5309 try { 5310 didSomething |= mServices.attachApplicationLocked(app, processName); 5311 } catch (Exception e) { 5312 badApp = true; 5313 } 5314 } 5315 5316 // Check if a next-broadcast receiver is in this process... 5317 if (!badApp && isPendingBroadcastProcessLocked(pid)) { 5318 try { 5319 didSomething |= sendPendingBroadcastsLocked(app); 5320 } catch (Exception e) { 5321 // If the app died trying to launch the receiver we declare it 'bad' 5322 badApp = true; 5323 } 5324 } 5325 5326 // Check whether the next backup agent is in this process... 5327 if (!badApp && mBackupTarget != null && mBackupTarget.appInfo.uid == app.uid) { 5328 if (DEBUG_BACKUP) Slog.v(TAG, "New app is backup target, launching agent for " + app); 5329 ensurePackageDexOpt(mBackupTarget.appInfo.packageName); 5330 try { 5331 thread.scheduleCreateBackupAgent(mBackupTarget.appInfo, 5332 compatibilityInfoForPackageLocked(mBackupTarget.appInfo), 5333 mBackupTarget.backupMode); 5334 } catch (Exception e) { 5335 Slog.w(TAG, "Exception scheduling backup agent creation: "); 5336 e.printStackTrace(); 5337 } 5338 } 5339 5340 if (badApp) { 5341 // todo: Also need to kill application to deal with all 5342 // kinds of exceptions. 5343 handleAppDiedLocked(app, false, true); 5344 return false; 5345 } 5346 5347 if (!didSomething) { 5348 updateOomAdjLocked(); 5349 } 5350 5351 return true; 5352 } 5353 5354 @Override 5355 public final void attachApplication(IApplicationThread thread) { 5356 synchronized (this) { 5357 int callingPid = Binder.getCallingPid(); 5358 final long origId = Binder.clearCallingIdentity(); 5359 attachApplicationLocked(thread, callingPid); 5360 Binder.restoreCallingIdentity(origId); 5361 } 5362 } 5363 5364 @Override 5365 public final void activityIdle(IBinder token, Configuration config, boolean stopProfiling) { 5366 final long origId = Binder.clearCallingIdentity(); 5367 synchronized (this) { 5368 ActivityStack stack = ActivityRecord.getStackLocked(token); 5369 if (stack != null) { 5370 ActivityRecord r = 5371 mStackSupervisor.activityIdleInternalLocked(token, false, config); 5372 if (stopProfiling) { 5373 if ((mProfileProc == r.app) && (mProfileFd != null)) { 5374 try { 5375 mProfileFd.close(); 5376 } catch (IOException e) { 5377 } 5378 clearProfilerLocked(); 5379 } 5380 } 5381 } 5382 } 5383 Binder.restoreCallingIdentity(origId); 5384 } 5385 5386 void enableScreenAfterBoot() { 5387 EventLog.writeEvent(EventLogTags.BOOT_PROGRESS_ENABLE_SCREEN, 5388 SystemClock.uptimeMillis()); 5389 mWindowManager.enableScreenAfterBoot(); 5390 5391 synchronized (this) { 5392 updateEventDispatchingLocked(); 5393 } 5394 } 5395 5396 @Override 5397 public void showBootMessage(final CharSequence msg, final boolean always) { 5398 enforceNotIsolatedCaller("showBootMessage"); 5399 mWindowManager.showBootMessage(msg, always); 5400 } 5401 5402 @Override 5403 public void dismissKeyguardOnNextActivity() { 5404 enforceNotIsolatedCaller("dismissKeyguardOnNextActivity"); 5405 final long token = Binder.clearCallingIdentity(); 5406 try { 5407 synchronized (this) { 5408 if (DEBUG_LOCKSCREEN) logLockScreen(""); 5409 if (mLockScreenShown) { 5410 mLockScreenShown = false; 5411 comeOutOfSleepIfNeededLocked(); 5412 } 5413 mStackSupervisor.setDismissKeyguard(true); 5414 } 5415 } finally { 5416 Binder.restoreCallingIdentity(token); 5417 } 5418 } 5419 5420 final void finishBooting() { 5421 // Register receivers to handle package update events 5422 mPackageMonitor.register(mContext, Looper.getMainLooper(), false); 5423 5424 synchronized (this) { 5425 // Ensure that any processes we had put on hold are now started 5426 // up. 5427 final int NP = mProcessesOnHold.size(); 5428 if (NP > 0) { 5429 ArrayList<ProcessRecord> procs = 5430 new ArrayList<ProcessRecord>(mProcessesOnHold); 5431 for (int ip=0; ip<NP; ip++) { 5432 if (DEBUG_PROCESSES) Slog.v(TAG, "Starting process on hold: " 5433 + procs.get(ip)); 5434 startProcessLocked(procs.get(ip), "on-hold", null, null /* ABI override */); 5435 } 5436 } 5437 5438 if (mFactoryTest != FactoryTest.FACTORY_TEST_LOW_LEVEL) { 5439 // Start looking for apps that are abusing wake locks. 5440 Message nmsg = mHandler.obtainMessage(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 5441 mHandler.sendMessageDelayed(nmsg, POWER_CHECK_DELAY); 5442 // Tell anyone interested that we are done booting! 5443 SystemProperties.set("sys.boot_completed", "1"); 5444 SystemProperties.set("dev.bootcomplete", "1"); 5445 for (int i=0; i<mStartedUsers.size(); i++) { 5446 UserStartedState uss = mStartedUsers.valueAt(i); 5447 if (uss.mState == UserStartedState.STATE_BOOTING) { 5448 uss.mState = UserStartedState.STATE_RUNNING; 5449 final int userId = mStartedUsers.keyAt(i); 5450 Intent intent = new Intent(Intent.ACTION_BOOT_COMPLETED, null); 5451 intent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 5452 intent.addFlags(Intent.FLAG_RECEIVER_NO_ABORT); 5453 broadcastIntentLocked(null, null, intent, null, 5454 new IIntentReceiver.Stub() { 5455 @Override 5456 public void performReceive(Intent intent, int resultCode, 5457 String data, Bundle extras, boolean ordered, 5458 boolean sticky, int sendingUser) { 5459 synchronized (ActivityManagerService.this) { 5460 requestPssAllProcsLocked(SystemClock.uptimeMillis(), 5461 true, false); 5462 } 5463 } 5464 }, 5465 0, null, null, 5466 android.Manifest.permission.RECEIVE_BOOT_COMPLETED, 5467 AppOpsManager.OP_NONE, true, false, MY_PID, Process.SYSTEM_UID, 5468 userId); 5469 } 5470 } 5471 scheduleStartProfilesLocked(); 5472 } 5473 } 5474 } 5475 5476 final void ensureBootCompleted() { 5477 boolean booting; 5478 boolean enableScreen; 5479 synchronized (this) { 5480 booting = mBooting; 5481 mBooting = false; 5482 enableScreen = !mBooted; 5483 mBooted = true; 5484 } 5485 5486 if (booting) { 5487 finishBooting(); 5488 } 5489 5490 if (enableScreen) { 5491 enableScreenAfterBoot(); 5492 } 5493 } 5494 5495 @Override 5496 public final void activityResumed(IBinder token) { 5497 final long origId = Binder.clearCallingIdentity(); 5498 synchronized(this) { 5499 ActivityStack stack = ActivityRecord.getStackLocked(token); 5500 if (stack != null) { 5501 ActivityRecord.activityResumedLocked(token); 5502 } 5503 } 5504 Binder.restoreCallingIdentity(origId); 5505 } 5506 5507 @Override 5508 public final void activityPaused(IBinder token, PersistableBundle persistentState) { 5509 final long origId = Binder.clearCallingIdentity(); 5510 synchronized(this) { 5511 ActivityStack stack = ActivityRecord.getStackLocked(token); 5512 if (stack != null) { 5513 stack.activityPausedLocked(token, false, persistentState); 5514 } 5515 } 5516 Binder.restoreCallingIdentity(origId); 5517 } 5518 5519 @Override 5520 public final void activityStopped(IBinder token, Bundle icicle, 5521 PersistableBundle persistentState, CharSequence description) { 5522 if (localLOGV) Slog.v(TAG, "Activity stopped: token=" + token); 5523 5524 // Refuse possible leaked file descriptors 5525 if (icicle != null && icicle.hasFileDescriptors()) { 5526 throw new IllegalArgumentException("File descriptors passed in Bundle"); 5527 } 5528 5529 final long origId = Binder.clearCallingIdentity(); 5530 5531 synchronized (this) { 5532 ActivityRecord r = ActivityRecord.isInStackLocked(token); 5533 if (r != null) { 5534 r.task.stack.activityStoppedLocked(r, icicle, persistentState, description); 5535 } 5536 } 5537 5538 trimApplications(); 5539 5540 Binder.restoreCallingIdentity(origId); 5541 } 5542 5543 @Override 5544 public final void activityDestroyed(IBinder token) { 5545 if (DEBUG_SWITCH) Slog.v(TAG, "ACTIVITY DESTROYED: " + token); 5546 synchronized (this) { 5547 ActivityStack stack = ActivityRecord.getStackLocked(token); 5548 if (stack != null) { 5549 stack.activityDestroyedLocked(token); 5550 } 5551 } 5552 } 5553 5554 @Override 5555 public String getCallingPackage(IBinder token) { 5556 synchronized (this) { 5557 ActivityRecord r = getCallingRecordLocked(token); 5558 return r != null ? r.info.packageName : null; 5559 } 5560 } 5561 5562 @Override 5563 public ComponentName getCallingActivity(IBinder token) { 5564 synchronized (this) { 5565 ActivityRecord r = getCallingRecordLocked(token); 5566 return r != null ? r.intent.getComponent() : null; 5567 } 5568 } 5569 5570 private ActivityRecord getCallingRecordLocked(IBinder token) { 5571 ActivityRecord r = ActivityRecord.isInStackLocked(token); 5572 if (r == null) { 5573 return null; 5574 } 5575 return r.resultTo; 5576 } 5577 5578 @Override 5579 public ComponentName getActivityClassForToken(IBinder token) { 5580 synchronized(this) { 5581 ActivityRecord r = ActivityRecord.isInStackLocked(token); 5582 if (r == null) { 5583 return null; 5584 } 5585 return r.intent.getComponent(); 5586 } 5587 } 5588 5589 @Override 5590 public String getPackageForToken(IBinder token) { 5591 synchronized(this) { 5592 ActivityRecord r = ActivityRecord.isInStackLocked(token); 5593 if (r == null) { 5594 return null; 5595 } 5596 return r.packageName; 5597 } 5598 } 5599 5600 @Override 5601 public IIntentSender getIntentSender(int type, 5602 String packageName, IBinder token, String resultWho, 5603 int requestCode, Intent[] intents, String[] resolvedTypes, 5604 int flags, Bundle options, int userId) { 5605 enforceNotIsolatedCaller("getIntentSender"); 5606 // Refuse possible leaked file descriptors 5607 if (intents != null) { 5608 if (intents.length < 1) { 5609 throw new IllegalArgumentException("Intents array length must be >= 1"); 5610 } 5611 for (int i=0; i<intents.length; i++) { 5612 Intent intent = intents[i]; 5613 if (intent != null) { 5614 if (intent.hasFileDescriptors()) { 5615 throw new IllegalArgumentException("File descriptors passed in Intent"); 5616 } 5617 if (type == ActivityManager.INTENT_SENDER_BROADCAST && 5618 (intent.getFlags()&Intent.FLAG_RECEIVER_BOOT_UPGRADE) != 0) { 5619 throw new IllegalArgumentException( 5620 "Can't use FLAG_RECEIVER_BOOT_UPGRADE here"); 5621 } 5622 intents[i] = new Intent(intent); 5623 } 5624 } 5625 if (resolvedTypes != null && resolvedTypes.length != intents.length) { 5626 throw new IllegalArgumentException( 5627 "Intent array length does not match resolvedTypes length"); 5628 } 5629 } 5630 if (options != null) { 5631 if (options.hasFileDescriptors()) { 5632 throw new IllegalArgumentException("File descriptors passed in options"); 5633 } 5634 } 5635 5636 synchronized(this) { 5637 int callingUid = Binder.getCallingUid(); 5638 int origUserId = userId; 5639 userId = handleIncomingUser(Binder.getCallingPid(), callingUid, userId, 5640 type == ActivityManager.INTENT_SENDER_BROADCAST, false, 5641 "getIntentSender", null); 5642 if (origUserId == UserHandle.USER_CURRENT) { 5643 // We don't want to evaluate this until the pending intent is 5644 // actually executed. However, we do want to always do the 5645 // security checking for it above. 5646 userId = UserHandle.USER_CURRENT; 5647 } 5648 try { 5649 if (callingUid != 0 && callingUid != Process.SYSTEM_UID) { 5650 int uid = AppGlobals.getPackageManager() 5651 .getPackageUid(packageName, UserHandle.getUserId(callingUid)); 5652 if (!UserHandle.isSameApp(callingUid, uid)) { 5653 String msg = "Permission Denial: getIntentSender() from pid=" 5654 + Binder.getCallingPid() 5655 + ", uid=" + Binder.getCallingUid() 5656 + ", (need uid=" + uid + ")" 5657 + " is not allowed to send as package " + packageName; 5658 Slog.w(TAG, msg); 5659 throw new SecurityException(msg); 5660 } 5661 } 5662 5663 return getIntentSenderLocked(type, packageName, callingUid, userId, 5664 token, resultWho, requestCode, intents, resolvedTypes, flags, options); 5665 5666 } catch (RemoteException e) { 5667 throw new SecurityException(e); 5668 } 5669 } 5670 } 5671 5672 IIntentSender getIntentSenderLocked(int type, String packageName, 5673 int callingUid, int userId, IBinder token, String resultWho, 5674 int requestCode, Intent[] intents, String[] resolvedTypes, int flags, 5675 Bundle options) { 5676 if (DEBUG_MU) 5677 Slog.v(TAG_MU, "getIntentSenderLocked(): uid=" + callingUid); 5678 ActivityRecord activity = null; 5679 if (type == ActivityManager.INTENT_SENDER_ACTIVITY_RESULT) { 5680 activity = ActivityRecord.isInStackLocked(token); 5681 if (activity == null) { 5682 return null; 5683 } 5684 if (activity.finishing) { 5685 return null; 5686 } 5687 } 5688 5689 final boolean noCreate = (flags&PendingIntent.FLAG_NO_CREATE) != 0; 5690 final boolean cancelCurrent = (flags&PendingIntent.FLAG_CANCEL_CURRENT) != 0; 5691 final boolean updateCurrent = (flags&PendingIntent.FLAG_UPDATE_CURRENT) != 0; 5692 flags &= ~(PendingIntent.FLAG_NO_CREATE|PendingIntent.FLAG_CANCEL_CURRENT 5693 |PendingIntent.FLAG_UPDATE_CURRENT); 5694 5695 PendingIntentRecord.Key key = new PendingIntentRecord.Key( 5696 type, packageName, activity, resultWho, 5697 requestCode, intents, resolvedTypes, flags, options, userId); 5698 WeakReference<PendingIntentRecord> ref; 5699 ref = mIntentSenderRecords.get(key); 5700 PendingIntentRecord rec = ref != null ? ref.get() : null; 5701 if (rec != null) { 5702 if (!cancelCurrent) { 5703 if (updateCurrent) { 5704 if (rec.key.requestIntent != null) { 5705 rec.key.requestIntent.replaceExtras(intents != null ? 5706 intents[intents.length - 1] : null); 5707 } 5708 if (intents != null) { 5709 intents[intents.length-1] = rec.key.requestIntent; 5710 rec.key.allIntents = intents; 5711 rec.key.allResolvedTypes = resolvedTypes; 5712 } else { 5713 rec.key.allIntents = null; 5714 rec.key.allResolvedTypes = null; 5715 } 5716 } 5717 return rec; 5718 } 5719 rec.canceled = true; 5720 mIntentSenderRecords.remove(key); 5721 } 5722 if (noCreate) { 5723 return rec; 5724 } 5725 rec = new PendingIntentRecord(this, key, callingUid); 5726 mIntentSenderRecords.put(key, rec.ref); 5727 if (type == ActivityManager.INTENT_SENDER_ACTIVITY_RESULT) { 5728 if (activity.pendingResults == null) { 5729 activity.pendingResults 5730 = new HashSet<WeakReference<PendingIntentRecord>>(); 5731 } 5732 activity.pendingResults.add(rec.ref); 5733 } 5734 return rec; 5735 } 5736 5737 @Override 5738 public void cancelIntentSender(IIntentSender sender) { 5739 if (!(sender instanceof PendingIntentRecord)) { 5740 return; 5741 } 5742 synchronized(this) { 5743 PendingIntentRecord rec = (PendingIntentRecord)sender; 5744 try { 5745 int uid = AppGlobals.getPackageManager() 5746 .getPackageUid(rec.key.packageName, UserHandle.getCallingUserId()); 5747 if (!UserHandle.isSameApp(uid, Binder.getCallingUid())) { 5748 String msg = "Permission Denial: cancelIntentSender() from pid=" 5749 + Binder.getCallingPid() 5750 + ", uid=" + Binder.getCallingUid() 5751 + " is not allowed to cancel packges " 5752 + rec.key.packageName; 5753 Slog.w(TAG, msg); 5754 throw new SecurityException(msg); 5755 } 5756 } catch (RemoteException e) { 5757 throw new SecurityException(e); 5758 } 5759 cancelIntentSenderLocked(rec, true); 5760 } 5761 } 5762 5763 void cancelIntentSenderLocked(PendingIntentRecord rec, boolean cleanActivity) { 5764 rec.canceled = true; 5765 mIntentSenderRecords.remove(rec.key); 5766 if (cleanActivity && rec.key.activity != null) { 5767 rec.key.activity.pendingResults.remove(rec.ref); 5768 } 5769 } 5770 5771 @Override 5772 public String getPackageForIntentSender(IIntentSender pendingResult) { 5773 if (!(pendingResult instanceof PendingIntentRecord)) { 5774 return null; 5775 } 5776 try { 5777 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 5778 return res.key.packageName; 5779 } catch (ClassCastException e) { 5780 } 5781 return null; 5782 } 5783 5784 @Override 5785 public int getUidForIntentSender(IIntentSender sender) { 5786 if (sender instanceof PendingIntentRecord) { 5787 try { 5788 PendingIntentRecord res = (PendingIntentRecord)sender; 5789 return res.uid; 5790 } catch (ClassCastException e) { 5791 } 5792 } 5793 return -1; 5794 } 5795 5796 @Override 5797 public boolean isIntentSenderTargetedToPackage(IIntentSender pendingResult) { 5798 if (!(pendingResult instanceof PendingIntentRecord)) { 5799 return false; 5800 } 5801 try { 5802 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 5803 if (res.key.allIntents == null) { 5804 return false; 5805 } 5806 for (int i=0; i<res.key.allIntents.length; i++) { 5807 Intent intent = res.key.allIntents[i]; 5808 if (intent.getPackage() != null && intent.getComponent() != null) { 5809 return false; 5810 } 5811 } 5812 return true; 5813 } catch (ClassCastException e) { 5814 } 5815 return false; 5816 } 5817 5818 @Override 5819 public boolean isIntentSenderAnActivity(IIntentSender pendingResult) { 5820 if (!(pendingResult instanceof PendingIntentRecord)) { 5821 return false; 5822 } 5823 try { 5824 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 5825 if (res.key.type == ActivityManager.INTENT_SENDER_ACTIVITY) { 5826 return true; 5827 } 5828 return false; 5829 } catch (ClassCastException e) { 5830 } 5831 return false; 5832 } 5833 5834 @Override 5835 public Intent getIntentForIntentSender(IIntentSender pendingResult) { 5836 if (!(pendingResult instanceof PendingIntentRecord)) { 5837 return null; 5838 } 5839 try { 5840 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 5841 return res.key.requestIntent != null ? new Intent(res.key.requestIntent) : null; 5842 } catch (ClassCastException e) { 5843 } 5844 return null; 5845 } 5846 5847 @Override 5848 public String getTagForIntentSender(IIntentSender pendingResult, String prefix) { 5849 if (!(pendingResult instanceof PendingIntentRecord)) { 5850 return null; 5851 } 5852 try { 5853 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 5854 Intent intent = res.key.requestIntent; 5855 if (intent != null) { 5856 if (res.lastTag != null && res.lastTagPrefix == prefix && (res.lastTagPrefix == null 5857 || res.lastTagPrefix.equals(prefix))) { 5858 return res.lastTag; 5859 } 5860 res.lastTagPrefix = prefix; 5861 StringBuilder sb = new StringBuilder(128); 5862 if (prefix != null) { 5863 sb.append(prefix); 5864 } 5865 if (intent.getAction() != null) { 5866 sb.append(intent.getAction()); 5867 } else if (intent.getComponent() != null) { 5868 intent.getComponent().appendShortString(sb); 5869 } else { 5870 sb.append("?"); 5871 } 5872 return res.lastTag = sb.toString(); 5873 } 5874 } catch (ClassCastException e) { 5875 } 5876 return null; 5877 } 5878 5879 @Override 5880 public void setProcessLimit(int max) { 5881 enforceCallingPermission(android.Manifest.permission.SET_PROCESS_LIMIT, 5882 "setProcessLimit()"); 5883 synchronized (this) { 5884 mProcessLimit = max < 0 ? ProcessList.MAX_CACHED_APPS : max; 5885 mProcessLimitOverride = max; 5886 } 5887 trimApplications(); 5888 } 5889 5890 @Override 5891 public int getProcessLimit() { 5892 synchronized (this) { 5893 return mProcessLimitOverride; 5894 } 5895 } 5896 5897 void foregroundTokenDied(ForegroundToken token) { 5898 synchronized (ActivityManagerService.this) { 5899 synchronized (mPidsSelfLocked) { 5900 ForegroundToken cur 5901 = mForegroundProcesses.get(token.pid); 5902 if (cur != token) { 5903 return; 5904 } 5905 mForegroundProcesses.remove(token.pid); 5906 ProcessRecord pr = mPidsSelfLocked.get(token.pid); 5907 if (pr == null) { 5908 return; 5909 } 5910 pr.forcingToForeground = null; 5911 updateProcessForegroundLocked(pr, false, false); 5912 } 5913 updateOomAdjLocked(); 5914 } 5915 } 5916 5917 @Override 5918 public void setProcessForeground(IBinder token, int pid, boolean isForeground) { 5919 enforceCallingPermission(android.Manifest.permission.SET_PROCESS_LIMIT, 5920 "setProcessForeground()"); 5921 synchronized(this) { 5922 boolean changed = false; 5923 5924 synchronized (mPidsSelfLocked) { 5925 ProcessRecord pr = mPidsSelfLocked.get(pid); 5926 if (pr == null && isForeground) { 5927 Slog.w(TAG, "setProcessForeground called on unknown pid: " + pid); 5928 return; 5929 } 5930 ForegroundToken oldToken = mForegroundProcesses.get(pid); 5931 if (oldToken != null) { 5932 oldToken.token.unlinkToDeath(oldToken, 0); 5933 mForegroundProcesses.remove(pid); 5934 if (pr != null) { 5935 pr.forcingToForeground = null; 5936 } 5937 changed = true; 5938 } 5939 if (isForeground && token != null) { 5940 ForegroundToken newToken = new ForegroundToken() { 5941 @Override 5942 public void binderDied() { 5943 foregroundTokenDied(this); 5944 } 5945 }; 5946 newToken.pid = pid; 5947 newToken.token = token; 5948 try { 5949 token.linkToDeath(newToken, 0); 5950 mForegroundProcesses.put(pid, newToken); 5951 pr.forcingToForeground = token; 5952 changed = true; 5953 } catch (RemoteException e) { 5954 // If the process died while doing this, we will later 5955 // do the cleanup with the process death link. 5956 } 5957 } 5958 } 5959 5960 if (changed) { 5961 updateOomAdjLocked(); 5962 } 5963 } 5964 } 5965 5966 // ========================================================= 5967 // PERMISSIONS 5968 // ========================================================= 5969 5970 static class PermissionController extends IPermissionController.Stub { 5971 ActivityManagerService mActivityManagerService; 5972 PermissionController(ActivityManagerService activityManagerService) { 5973 mActivityManagerService = activityManagerService; 5974 } 5975 5976 @Override 5977 public boolean checkPermission(String permission, int pid, int uid) { 5978 return mActivityManagerService.checkPermission(permission, pid, 5979 uid) == PackageManager.PERMISSION_GRANTED; 5980 } 5981 } 5982 5983 class IntentFirewallInterface implements IntentFirewall.AMSInterface { 5984 @Override 5985 public int checkComponentPermission(String permission, int pid, int uid, 5986 int owningUid, boolean exported) { 5987 return ActivityManagerService.this.checkComponentPermission(permission, pid, uid, 5988 owningUid, exported); 5989 } 5990 5991 @Override 5992 public Object getAMSLock() { 5993 return ActivityManagerService.this; 5994 } 5995 } 5996 5997 /** 5998 * This can be called with or without the global lock held. 5999 */ 6000 int checkComponentPermission(String permission, int pid, int uid, 6001 int owningUid, boolean exported) { 6002 // We might be performing an operation on behalf of an indirect binder 6003 // invocation, e.g. via {@link #openContentUri}. Check and adjust the 6004 // client identity accordingly before proceeding. 6005 Identity tlsIdentity = sCallerIdentity.get(); 6006 if (tlsIdentity != null) { 6007 Slog.d(TAG, "checkComponentPermission() adjusting {pid,uid} to {" 6008 + tlsIdentity.pid + "," + tlsIdentity.uid + "}"); 6009 uid = tlsIdentity.uid; 6010 pid = tlsIdentity.pid; 6011 } 6012 6013 if (pid == MY_PID) { 6014 return PackageManager.PERMISSION_GRANTED; 6015 } 6016 6017 return ActivityManager.checkComponentPermission(permission, uid, 6018 owningUid, exported); 6019 } 6020 6021 /** 6022 * As the only public entry point for permissions checking, this method 6023 * can enforce the semantic that requesting a check on a null global 6024 * permission is automatically denied. (Internally a null permission 6025 * string is used when calling {@link #checkComponentPermission} in cases 6026 * when only uid-based security is needed.) 6027 * 6028 * This can be called with or without the global lock held. 6029 */ 6030 @Override 6031 public int checkPermission(String permission, int pid, int uid) { 6032 if (permission == null) { 6033 return PackageManager.PERMISSION_DENIED; 6034 } 6035 return checkComponentPermission(permission, pid, UserHandle.getAppId(uid), -1, true); 6036 } 6037 6038 /** 6039 * Binder IPC calls go through the public entry point. 6040 * This can be called with or without the global lock held. 6041 */ 6042 int checkCallingPermission(String permission) { 6043 return checkPermission(permission, 6044 Binder.getCallingPid(), 6045 UserHandle.getAppId(Binder.getCallingUid())); 6046 } 6047 6048 /** 6049 * This can be called with or without the global lock held. 6050 */ 6051 void enforceCallingPermission(String permission, String func) { 6052 if (checkCallingPermission(permission) 6053 == PackageManager.PERMISSION_GRANTED) { 6054 return; 6055 } 6056 6057 String msg = "Permission Denial: " + func + " from pid=" 6058 + Binder.getCallingPid() 6059 + ", uid=" + Binder.getCallingUid() 6060 + " requires " + permission; 6061 Slog.w(TAG, msg); 6062 throw new SecurityException(msg); 6063 } 6064 6065 /** 6066 * Determine if UID is holding permissions required to access {@link Uri} in 6067 * the given {@link ProviderInfo}. Final permission checking is always done 6068 * in {@link ContentProvider}. 6069 */ 6070 private final boolean checkHoldingPermissionsLocked( 6071 IPackageManager pm, ProviderInfo pi, GrantUri grantUri, int uid, final int modeFlags) { 6072 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6073 "checkHoldingPermissionsLocked: uri=" + grantUri + " uid=" + uid); 6074 if (UserHandle.getUserId(uid) != grantUri.sourceUserId) { 6075 return false; 6076 } 6077 6078 if (pi.applicationInfo.uid == uid) { 6079 return true; 6080 } else if (!pi.exported) { 6081 return false; 6082 } 6083 6084 boolean readMet = (modeFlags & Intent.FLAG_GRANT_READ_URI_PERMISSION) == 0; 6085 boolean writeMet = (modeFlags & Intent.FLAG_GRANT_WRITE_URI_PERMISSION) == 0; 6086 try { 6087 // check if target holds top-level <provider> permissions 6088 if (!readMet && pi.readPermission != null 6089 && (pm.checkUidPermission(pi.readPermission, uid) == PERMISSION_GRANTED)) { 6090 readMet = true; 6091 } 6092 if (!writeMet && pi.writePermission != null 6093 && (pm.checkUidPermission(pi.writePermission, uid) == PERMISSION_GRANTED)) { 6094 writeMet = true; 6095 } 6096 6097 // track if unprotected read/write is allowed; any denied 6098 // <path-permission> below removes this ability 6099 boolean allowDefaultRead = pi.readPermission == null; 6100 boolean allowDefaultWrite = pi.writePermission == null; 6101 6102 // check if target holds any <path-permission> that match uri 6103 final PathPermission[] pps = pi.pathPermissions; 6104 if (pps != null) { 6105 final String path = grantUri.uri.getPath(); 6106 int i = pps.length; 6107 while (i > 0 && (!readMet || !writeMet)) { 6108 i--; 6109 PathPermission pp = pps[i]; 6110 if (pp.match(path)) { 6111 if (!readMet) { 6112 final String pprperm = pp.getReadPermission(); 6113 if (DEBUG_URI_PERMISSION) Slog.v(TAG, "Checking read perm for " 6114 + pprperm + " for " + pp.getPath() 6115 + ": match=" + pp.match(path) 6116 + " check=" + pm.checkUidPermission(pprperm, uid)); 6117 if (pprperm != null) { 6118 if (pm.checkUidPermission(pprperm, uid) == PERMISSION_GRANTED) { 6119 readMet = true; 6120 } else { 6121 allowDefaultRead = false; 6122 } 6123 } 6124 } 6125 if (!writeMet) { 6126 final String ppwperm = pp.getWritePermission(); 6127 if (DEBUG_URI_PERMISSION) Slog.v(TAG, "Checking write perm " 6128 + ppwperm + " for " + pp.getPath() 6129 + ": match=" + pp.match(path) 6130 + " check=" + pm.checkUidPermission(ppwperm, uid)); 6131 if (ppwperm != null) { 6132 if (pm.checkUidPermission(ppwperm, uid) == PERMISSION_GRANTED) { 6133 writeMet = true; 6134 } else { 6135 allowDefaultWrite = false; 6136 } 6137 } 6138 } 6139 } 6140 } 6141 } 6142 6143 // grant unprotected <provider> read/write, if not blocked by 6144 // <path-permission> above 6145 if (allowDefaultRead) readMet = true; 6146 if (allowDefaultWrite) writeMet = true; 6147 6148 } catch (RemoteException e) { 6149 return false; 6150 } 6151 6152 return readMet && writeMet; 6153 } 6154 6155 private ProviderInfo getProviderInfoLocked(String authority, int userHandle) { 6156 ProviderInfo pi = null; 6157 ContentProviderRecord cpr = mProviderMap.getProviderByName(authority, userHandle); 6158 if (cpr != null) { 6159 pi = cpr.info; 6160 } else { 6161 try { 6162 pi = AppGlobals.getPackageManager().resolveContentProvider( 6163 authority, PackageManager.GET_URI_PERMISSION_PATTERNS, userHandle); 6164 } catch (RemoteException ex) { 6165 } 6166 } 6167 return pi; 6168 } 6169 6170 private UriPermission findUriPermissionLocked(int targetUid, GrantUri grantUri) { 6171 final ArrayMap<GrantUri, UriPermission> targetUris = mGrantedUriPermissions.get(targetUid); 6172 if (targetUris != null) { 6173 return targetUris.get(grantUri); 6174 } 6175 return null; 6176 } 6177 6178 private UriPermission findOrCreateUriPermissionLocked(String sourcePkg, 6179 String targetPkg, int targetUid, GrantUri grantUri) { 6180 ArrayMap<GrantUri, UriPermission> targetUris = mGrantedUriPermissions.get(targetUid); 6181 if (targetUris == null) { 6182 targetUris = Maps.newArrayMap(); 6183 mGrantedUriPermissions.put(targetUid, targetUris); 6184 } 6185 6186 UriPermission perm = targetUris.get(grantUri); 6187 if (perm == null) { 6188 perm = new UriPermission(sourcePkg, targetPkg, targetUid, grantUri); 6189 targetUris.put(grantUri, perm); 6190 } 6191 6192 return perm; 6193 } 6194 6195 private final boolean checkUriPermissionLocked(GrantUri grantUri, int uid, 6196 final int modeFlags) { 6197 final boolean persistable = (modeFlags & Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION) != 0; 6198 final int minStrength = persistable ? UriPermission.STRENGTH_PERSISTABLE 6199 : UriPermission.STRENGTH_OWNED; 6200 6201 // Root gets to do everything. 6202 if (uid == 0) { 6203 return true; 6204 } 6205 6206 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get(uid); 6207 if (perms == null) return false; 6208 6209 // First look for exact match 6210 final UriPermission exactPerm = perms.get(grantUri); 6211 if (exactPerm != null && exactPerm.getStrength(modeFlags) >= minStrength) { 6212 return true; 6213 } 6214 6215 // No exact match, look for prefixes 6216 final int N = perms.size(); 6217 for (int i = 0; i < N; i++) { 6218 final UriPermission perm = perms.valueAt(i); 6219 if (perm.uri.prefix && grantUri.uri.isPathPrefixMatch(perm.uri.uri) 6220 && perm.getStrength(modeFlags) >= minStrength) { 6221 return true; 6222 } 6223 } 6224 6225 return false; 6226 } 6227 6228 @Override 6229 public int checkUriPermission(Uri uri, int pid, int uid, 6230 final int modeFlags, int userId) { 6231 enforceNotIsolatedCaller("checkUriPermission"); 6232 6233 // Another redirected-binder-call permissions check as in 6234 // {@link checkComponentPermission}. 6235 Identity tlsIdentity = sCallerIdentity.get(); 6236 if (tlsIdentity != null) { 6237 uid = tlsIdentity.uid; 6238 pid = tlsIdentity.pid; 6239 } 6240 6241 // Our own process gets to do everything. 6242 if (pid == MY_PID) { 6243 return PackageManager.PERMISSION_GRANTED; 6244 } 6245 synchronized (this) { 6246 return checkUriPermissionLocked(new GrantUri(userId, uri, false), uid, modeFlags) 6247 ? PackageManager.PERMISSION_GRANTED 6248 : PackageManager.PERMISSION_DENIED; 6249 } 6250 } 6251 6252 /** 6253 * Check if the targetPkg can be granted permission to access uri by 6254 * the callingUid using the given modeFlags. Throws a security exception 6255 * if callingUid is not allowed to do this. Returns the uid of the target 6256 * if the URI permission grant should be performed; returns -1 if it is not 6257 * needed (for example targetPkg already has permission to access the URI). 6258 * If you already know the uid of the target, you can supply it in 6259 * lastTargetUid else set that to -1. 6260 */ 6261 int checkGrantUriPermissionLocked(int callingUid, String targetPkg, GrantUri grantUri, 6262 final int modeFlags, int lastTargetUid) { 6263 if (!Intent.isAccessUriMode(modeFlags)) { 6264 return -1; 6265 } 6266 6267 if (targetPkg != null) { 6268 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6269 "Checking grant " + targetPkg + " permission to " + grantUri); 6270 } 6271 6272 final IPackageManager pm = AppGlobals.getPackageManager(); 6273 6274 // If this is not a content: uri, we can't do anything with it. 6275 if (!ContentResolver.SCHEME_CONTENT.equals(grantUri.uri.getScheme())) { 6276 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6277 "Can't grant URI permission for non-content URI: " + grantUri); 6278 return -1; 6279 } 6280 6281 final String authority = grantUri.uri.getAuthority(); 6282 final ProviderInfo pi = getProviderInfoLocked(authority, grantUri.sourceUserId); 6283 if (pi == null) { 6284 Slog.w(TAG, "No content provider found for permission check: " + 6285 grantUri.uri.toSafeString()); 6286 return -1; 6287 } 6288 6289 int targetUid = lastTargetUid; 6290 if (targetUid < 0 && targetPkg != null) { 6291 try { 6292 targetUid = pm.getPackageUid(targetPkg, UserHandle.getUserId(callingUid)); 6293 if (targetUid < 0) { 6294 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6295 "Can't grant URI permission no uid for: " + targetPkg); 6296 return -1; 6297 } 6298 } catch (RemoteException ex) { 6299 return -1; 6300 } 6301 } 6302 6303 if (targetUid >= 0) { 6304 // First... does the target actually need this permission? 6305 if (checkHoldingPermissionsLocked(pm, pi, grantUri, targetUid, modeFlags)) { 6306 // No need to grant the target this permission. 6307 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6308 "Target " + targetPkg + " already has full permission to " + grantUri); 6309 return -1; 6310 } 6311 } else { 6312 // First... there is no target package, so can anyone access it? 6313 boolean allowed = pi.exported; 6314 if ((modeFlags&Intent.FLAG_GRANT_READ_URI_PERMISSION) != 0) { 6315 if (pi.readPermission != null) { 6316 allowed = false; 6317 } 6318 } 6319 if ((modeFlags&Intent.FLAG_GRANT_WRITE_URI_PERMISSION) != 0) { 6320 if (pi.writePermission != null) { 6321 allowed = false; 6322 } 6323 } 6324 if (allowed) { 6325 return -1; 6326 } 6327 } 6328 6329 // Second... is the provider allowing granting of URI permissions? 6330 if (!pi.grantUriPermissions) { 6331 throw new SecurityException("Provider " + pi.packageName 6332 + "/" + pi.name 6333 + " does not allow granting of Uri permissions (uri " 6334 + grantUri + ")"); 6335 } 6336 if (pi.uriPermissionPatterns != null) { 6337 final int N = pi.uriPermissionPatterns.length; 6338 boolean allowed = false; 6339 for (int i=0; i<N; i++) { 6340 if (pi.uriPermissionPatterns[i] != null 6341 && pi.uriPermissionPatterns[i].match(grantUri.uri.getPath())) { 6342 allowed = true; 6343 break; 6344 } 6345 } 6346 if (!allowed) { 6347 throw new SecurityException("Provider " + pi.packageName 6348 + "/" + pi.name 6349 + " does not allow granting of permission to path of Uri " 6350 + grantUri); 6351 } 6352 } 6353 6354 // Third... does the caller itself have permission to access 6355 // this uri? 6356 if (UserHandle.getAppId(callingUid) != Process.SYSTEM_UID) { 6357 if (!checkHoldingPermissionsLocked(pm, pi, grantUri, callingUid, modeFlags)) { 6358 // Require they hold a strong enough Uri permission 6359 if (!checkUriPermissionLocked(grantUri, callingUid, modeFlags)) { 6360 throw new SecurityException("Uid " + callingUid 6361 + " does not have permission to uri " + grantUri); 6362 } 6363 } 6364 } 6365 return targetUid; 6366 } 6367 6368 @Override 6369 public int checkGrantUriPermission(int callingUid, String targetPkg, Uri uri, 6370 final int modeFlags, int userId) { 6371 enforceNotIsolatedCaller("checkGrantUriPermission"); 6372 synchronized(this) { 6373 return checkGrantUriPermissionLocked(callingUid, targetPkg, 6374 new GrantUri(userId, uri, false), modeFlags, -1); 6375 } 6376 } 6377 6378 void grantUriPermissionUncheckedLocked(int targetUid, String targetPkg, GrantUri grantUri, 6379 final int modeFlags, UriPermissionOwner owner) { 6380 if (!Intent.isAccessUriMode(modeFlags)) { 6381 return; 6382 } 6383 6384 // So here we are: the caller has the assumed permission 6385 // to the uri, and the target doesn't. Let's now give this to 6386 // the target. 6387 6388 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6389 "Granting " + targetPkg + "/" + targetUid + " permission to " + grantUri); 6390 6391 final String authority = grantUri.uri.getAuthority(); 6392 final ProviderInfo pi = getProviderInfoLocked(authority, grantUri.sourceUserId); 6393 if (pi == null) { 6394 Slog.w(TAG, "No content provider found for grant: " + grantUri.toSafeString()); 6395 return; 6396 } 6397 6398 if ((modeFlags & Intent.FLAG_GRANT_PREFIX_URI_PERMISSION) != 0) { 6399 grantUri.prefix = true; 6400 } 6401 final UriPermission perm = findOrCreateUriPermissionLocked( 6402 pi.packageName, targetPkg, targetUid, grantUri); 6403 perm.grantModes(modeFlags, owner); 6404 } 6405 6406 void grantUriPermissionLocked(int callingUid, String targetPkg, GrantUri grantUri, 6407 final int modeFlags, UriPermissionOwner owner) { 6408 if (targetPkg == null) { 6409 throw new NullPointerException("targetPkg"); 6410 } 6411 6412 int targetUid = checkGrantUriPermissionLocked(callingUid, targetPkg, grantUri, modeFlags, 6413 -1); 6414 if (targetUid < 0) { 6415 return; 6416 } 6417 6418 grantUriPermissionUncheckedLocked(targetUid, targetPkg, grantUri, modeFlags, 6419 owner); 6420 } 6421 6422 static class NeededUriGrants extends ArrayList<GrantUri> { 6423 final String targetPkg; 6424 final int targetUid; 6425 final int flags; 6426 6427 NeededUriGrants(String targetPkg, int targetUid, int flags) { 6428 this.targetPkg = targetPkg; 6429 this.targetUid = targetUid; 6430 this.flags = flags; 6431 } 6432 } 6433 6434 /** 6435 * Like checkGrantUriPermissionLocked, but takes an Intent. 6436 */ 6437 NeededUriGrants checkGrantUriPermissionFromIntentLocked(int callingUid, 6438 String targetPkg, Intent intent, int mode, NeededUriGrants needed, int targetUserId) { 6439 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6440 "Checking URI perm to data=" + (intent != null ? intent.getData() : null) 6441 + " clip=" + (intent != null ? intent.getClipData() : null) 6442 + " from " + intent + "; flags=0x" 6443 + Integer.toHexString(intent != null ? intent.getFlags() : 0)); 6444 6445 if (targetPkg == null) { 6446 throw new NullPointerException("targetPkg"); 6447 } 6448 6449 if (intent == null) { 6450 return null; 6451 } 6452 Uri data = intent.getData(); 6453 ClipData clip = intent.getClipData(); 6454 if (data == null && clip == null) { 6455 return null; 6456 } 6457 final IPackageManager pm = AppGlobals.getPackageManager(); 6458 int targetUid; 6459 if (needed != null) { 6460 targetUid = needed.targetUid; 6461 } else { 6462 try { 6463 targetUid = pm.getPackageUid(targetPkg, targetUserId); 6464 } catch (RemoteException ex) { 6465 return null; 6466 } 6467 if (targetUid < 0) { 6468 if (DEBUG_URI_PERMISSION) { 6469 Slog.v(TAG, "Can't grant URI permission no uid for: " + targetPkg 6470 + " on user " + targetUserId); 6471 } 6472 return null; 6473 } 6474 } 6475 if (data != null) { 6476 GrantUri grantUri = GrantUri.resolve(UserHandle.getUserId(callingUid), data); 6477 targetUid = checkGrantUriPermissionLocked(callingUid, targetPkg, grantUri, mode, 6478 targetUid); 6479 if (targetUid > 0) { 6480 if (needed == null) { 6481 needed = new NeededUriGrants(targetPkg, targetUid, mode); 6482 } 6483 needed.add(grantUri); 6484 } 6485 } 6486 if (clip != null) { 6487 for (int i=0; i<clip.getItemCount(); i++) { 6488 Uri uri = clip.getItemAt(i).getUri(); 6489 if (uri != null) { 6490 GrantUri grantUri = GrantUri.resolve(UserHandle.getUserId(callingUid), uri); 6491 targetUid = checkGrantUriPermissionLocked(callingUid, targetPkg, grantUri, mode, 6492 targetUid); 6493 if (targetUid > 0) { 6494 if (needed == null) { 6495 needed = new NeededUriGrants(targetPkg, targetUid, mode); 6496 } 6497 needed.add(grantUri); 6498 } 6499 } else { 6500 Intent clipIntent = clip.getItemAt(i).getIntent(); 6501 if (clipIntent != null) { 6502 NeededUriGrants newNeeded = checkGrantUriPermissionFromIntentLocked( 6503 callingUid, targetPkg, clipIntent, mode, needed, targetUserId); 6504 if (newNeeded != null) { 6505 needed = newNeeded; 6506 } 6507 } 6508 } 6509 } 6510 } 6511 6512 return needed; 6513 } 6514 6515 /** 6516 * Like grantUriPermissionUncheckedLocked, but takes an Intent. 6517 */ 6518 void grantUriPermissionUncheckedFromIntentLocked(NeededUriGrants needed, 6519 UriPermissionOwner owner) { 6520 if (needed != null) { 6521 for (int i=0; i<needed.size(); i++) { 6522 GrantUri grantUri = needed.get(i); 6523 grantUriPermissionUncheckedLocked(needed.targetUid, needed.targetPkg, 6524 grantUri, needed.flags, owner); 6525 } 6526 } 6527 } 6528 6529 void grantUriPermissionFromIntentLocked(int callingUid, 6530 String targetPkg, Intent intent, UriPermissionOwner owner, int targetUserId) { 6531 NeededUriGrants needed = checkGrantUriPermissionFromIntentLocked(callingUid, targetPkg, 6532 intent, intent != null ? intent.getFlags() : 0, null, targetUserId); 6533 if (needed == null) { 6534 return; 6535 } 6536 6537 grantUriPermissionUncheckedFromIntentLocked(needed, owner); 6538 } 6539 6540 @Override 6541 public void grantUriPermission(IApplicationThread caller, String targetPkg, Uri uri, 6542 final int modeFlags, int userId) { 6543 enforceNotIsolatedCaller("grantUriPermission"); 6544 GrantUri grantUri = new GrantUri(userId, uri, false); 6545 synchronized(this) { 6546 final ProcessRecord r = getRecordForAppLocked(caller); 6547 if (r == null) { 6548 throw new SecurityException("Unable to find app for caller " 6549 + caller 6550 + " when granting permission to uri " + grantUri); 6551 } 6552 if (targetPkg == null) { 6553 throw new IllegalArgumentException("null target"); 6554 } 6555 if (grantUri == null) { 6556 throw new IllegalArgumentException("null uri"); 6557 } 6558 6559 Preconditions.checkFlagsArgument(modeFlags, Intent.FLAG_GRANT_READ_URI_PERMISSION 6560 | Intent.FLAG_GRANT_WRITE_URI_PERMISSION 6561 | Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION 6562 | Intent.FLAG_GRANT_PREFIX_URI_PERMISSION); 6563 6564 grantUriPermissionLocked(r.uid, targetPkg, grantUri, modeFlags, null); 6565 } 6566 } 6567 6568 void removeUriPermissionIfNeededLocked(UriPermission perm) { 6569 if (perm.modeFlags == 0) { 6570 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get( 6571 perm.targetUid); 6572 if (perms != null) { 6573 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6574 "Removing " + perm.targetUid + " permission to " + perm.uri); 6575 6576 perms.remove(perm.uri); 6577 if (perms.isEmpty()) { 6578 mGrantedUriPermissions.remove(perm.targetUid); 6579 } 6580 } 6581 } 6582 } 6583 6584 private void revokeUriPermissionLocked(int callingUid, GrantUri grantUri, final int modeFlags) { 6585 if (DEBUG_URI_PERMISSION) Slog.v(TAG, "Revoking all granted permissions to " + grantUri); 6586 6587 final IPackageManager pm = AppGlobals.getPackageManager(); 6588 final String authority = grantUri.uri.getAuthority(); 6589 final ProviderInfo pi = getProviderInfoLocked(authority, grantUri.sourceUserId); 6590 if (pi == null) { 6591 Slog.w(TAG, "No content provider found for permission revoke: " 6592 + grantUri.toSafeString()); 6593 return; 6594 } 6595 6596 // Does the caller have this permission on the URI? 6597 if (!checkHoldingPermissionsLocked(pm, pi, grantUri, callingUid, modeFlags)) { 6598 // Right now, if you are not the original owner of the permission, 6599 // you are not allowed to revoke it. 6600 //if (!checkUriPermissionLocked(uri, callingUid, modeFlags)) { 6601 throw new SecurityException("Uid " + callingUid 6602 + " does not have permission to uri " + grantUri); 6603 //} 6604 } 6605 6606 boolean persistChanged = false; 6607 6608 // Go through all of the permissions and remove any that match. 6609 int N = mGrantedUriPermissions.size(); 6610 for (int i = 0; i < N; i++) { 6611 final int targetUid = mGrantedUriPermissions.keyAt(i); 6612 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i); 6613 6614 for (Iterator<UriPermission> it = perms.values().iterator(); it.hasNext();) { 6615 final UriPermission perm = it.next(); 6616 if (perm.uri.sourceUserId == grantUri.sourceUserId 6617 && perm.uri.uri.isPathPrefixMatch(grantUri.uri)) { 6618 if (DEBUG_URI_PERMISSION) 6619 Slog.v(TAG, 6620 "Revoking " + perm.targetUid + " permission to " + perm.uri); 6621 persistChanged |= perm.revokeModes( 6622 modeFlags | Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION); 6623 if (perm.modeFlags == 0) { 6624 it.remove(); 6625 } 6626 } 6627 } 6628 6629 if (perms.isEmpty()) { 6630 mGrantedUriPermissions.remove(targetUid); 6631 N--; 6632 i--; 6633 } 6634 } 6635 6636 if (persistChanged) { 6637 schedulePersistUriGrants(); 6638 } 6639 } 6640 6641 @Override 6642 public void revokeUriPermission(IApplicationThread caller, Uri uri, final int modeFlags, 6643 int userId) { 6644 enforceNotIsolatedCaller("revokeUriPermission"); 6645 synchronized(this) { 6646 final ProcessRecord r = getRecordForAppLocked(caller); 6647 if (r == null) { 6648 throw new SecurityException("Unable to find app for caller " 6649 + caller 6650 + " when revoking permission to uri " + uri); 6651 } 6652 if (uri == null) { 6653 Slog.w(TAG, "revokeUriPermission: null uri"); 6654 return; 6655 } 6656 6657 if (!Intent.isAccessUriMode(modeFlags)) { 6658 return; 6659 } 6660 6661 final IPackageManager pm = AppGlobals.getPackageManager(); 6662 final String authority = uri.getAuthority(); 6663 final ProviderInfo pi = getProviderInfoLocked(authority, userId); 6664 if (pi == null) { 6665 Slog.w(TAG, "No content provider found for permission revoke: " 6666 + uri.toSafeString()); 6667 return; 6668 } 6669 6670 revokeUriPermissionLocked(r.uid, new GrantUri(userId, uri, false), modeFlags); 6671 } 6672 } 6673 6674 /** 6675 * Remove any {@link UriPermission} granted <em>from</em> or <em>to</em> the 6676 * given package. 6677 * 6678 * @param packageName Package name to match, or {@code null} to apply to all 6679 * packages. 6680 * @param userHandle User to match, or {@link UserHandle#USER_ALL} to apply 6681 * to all users. 6682 * @param persistable If persistable grants should be removed. 6683 */ 6684 private void removeUriPermissionsForPackageLocked( 6685 String packageName, int userHandle, boolean persistable) { 6686 if (userHandle == UserHandle.USER_ALL && packageName == null) { 6687 throw new IllegalArgumentException("Must narrow by either package or user"); 6688 } 6689 6690 boolean persistChanged = false; 6691 6692 int N = mGrantedUriPermissions.size(); 6693 for (int i = 0; i < N; i++) { 6694 final int targetUid = mGrantedUriPermissions.keyAt(i); 6695 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i); 6696 6697 // Only inspect grants matching user 6698 if (userHandle == UserHandle.USER_ALL 6699 || userHandle == UserHandle.getUserId(targetUid)) { 6700 for (Iterator<UriPermission> it = perms.values().iterator(); it.hasNext();) { 6701 final UriPermission perm = it.next(); 6702 6703 // Only inspect grants matching package 6704 if (packageName == null || perm.sourcePkg.equals(packageName) 6705 || perm.targetPkg.equals(packageName)) { 6706 persistChanged |= perm.revokeModes( 6707 persistable ? ~0 : ~Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION); 6708 6709 // Only remove when no modes remain; any persisted grants 6710 // will keep this alive. 6711 if (perm.modeFlags == 0) { 6712 it.remove(); 6713 } 6714 } 6715 } 6716 6717 if (perms.isEmpty()) { 6718 mGrantedUriPermissions.remove(targetUid); 6719 N--; 6720 i--; 6721 } 6722 } 6723 } 6724 6725 if (persistChanged) { 6726 schedulePersistUriGrants(); 6727 } 6728 } 6729 6730 @Override 6731 public IBinder newUriPermissionOwner(String name) { 6732 enforceNotIsolatedCaller("newUriPermissionOwner"); 6733 synchronized(this) { 6734 UriPermissionOwner owner = new UriPermissionOwner(this, name); 6735 return owner.getExternalTokenLocked(); 6736 } 6737 } 6738 6739 @Override 6740 public void grantUriPermissionFromOwner(IBinder token, int fromUid, String targetPkg, Uri uri, 6741 final int modeFlags, int userId) { 6742 synchronized(this) { 6743 UriPermissionOwner owner = UriPermissionOwner.fromExternalToken(token); 6744 if (owner == null) { 6745 throw new IllegalArgumentException("Unknown owner: " + token); 6746 } 6747 if (fromUid != Binder.getCallingUid()) { 6748 if (Binder.getCallingUid() != Process.myUid()) { 6749 // Only system code can grant URI permissions on behalf 6750 // of other users. 6751 throw new SecurityException("nice try"); 6752 } 6753 } 6754 if (targetPkg == null) { 6755 throw new IllegalArgumentException("null target"); 6756 } 6757 if (uri == null) { 6758 throw new IllegalArgumentException("null uri"); 6759 } 6760 6761 grantUriPermissionLocked(fromUid, targetPkg, new GrantUri(userId, uri, false), 6762 modeFlags, owner); 6763 } 6764 } 6765 6766 @Override 6767 public void revokeUriPermissionFromOwner(IBinder token, Uri uri, int mode, int userId) { 6768 synchronized(this) { 6769 UriPermissionOwner owner = UriPermissionOwner.fromExternalToken(token); 6770 if (owner == null) { 6771 throw new IllegalArgumentException("Unknown owner: " + token); 6772 } 6773 6774 if (uri == null) { 6775 owner.removeUriPermissionsLocked(mode); 6776 } else { 6777 owner.removeUriPermissionLocked(new GrantUri(userId, uri, false), mode); 6778 } 6779 } 6780 } 6781 6782 private void schedulePersistUriGrants() { 6783 if (!mHandler.hasMessages(PERSIST_URI_GRANTS_MSG)) { 6784 mHandler.sendMessageDelayed(mHandler.obtainMessage(PERSIST_URI_GRANTS_MSG), 6785 10 * DateUtils.SECOND_IN_MILLIS); 6786 } 6787 } 6788 6789 private void writeGrantedUriPermissions() { 6790 if (DEBUG_URI_PERMISSION) Slog.v(TAG, "writeGrantedUriPermissions()"); 6791 6792 // Snapshot permissions so we can persist without lock 6793 ArrayList<UriPermission.Snapshot> persist = Lists.newArrayList(); 6794 synchronized (this) { 6795 final int size = mGrantedUriPermissions.size(); 6796 for (int i = 0; i < size; i++) { 6797 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i); 6798 for (UriPermission perm : perms.values()) { 6799 if (perm.persistedModeFlags != 0) { 6800 persist.add(perm.snapshot()); 6801 } 6802 } 6803 } 6804 } 6805 6806 FileOutputStream fos = null; 6807 try { 6808 fos = mGrantFile.startWrite(); 6809 6810 XmlSerializer out = new FastXmlSerializer(); 6811 out.setOutput(fos, "utf-8"); 6812 out.startDocument(null, true); 6813 out.startTag(null, TAG_URI_GRANTS); 6814 for (UriPermission.Snapshot perm : persist) { 6815 out.startTag(null, TAG_URI_GRANT); 6816 writeIntAttribute(out, ATTR_SOURCE_USER_ID, perm.uri.sourceUserId); 6817 writeIntAttribute(out, ATTR_TARGET_USER_ID, perm.targetUserId); 6818 out.attribute(null, ATTR_SOURCE_PKG, perm.sourcePkg); 6819 out.attribute(null, ATTR_TARGET_PKG, perm.targetPkg); 6820 out.attribute(null, ATTR_URI, String.valueOf(perm.uri.uri)); 6821 writeBooleanAttribute(out, ATTR_PREFIX, perm.uri.prefix); 6822 writeIntAttribute(out, ATTR_MODE_FLAGS, perm.persistedModeFlags); 6823 writeLongAttribute(out, ATTR_CREATED_TIME, perm.persistedCreateTime); 6824 out.endTag(null, TAG_URI_GRANT); 6825 } 6826 out.endTag(null, TAG_URI_GRANTS); 6827 out.endDocument(); 6828 6829 mGrantFile.finishWrite(fos); 6830 } catch (IOException e) { 6831 if (fos != null) { 6832 mGrantFile.failWrite(fos); 6833 } 6834 } 6835 } 6836 6837 private void readGrantedUriPermissionsLocked() { 6838 if (DEBUG_URI_PERMISSION) Slog.v(TAG, "readGrantedUriPermissions()"); 6839 6840 final long now = System.currentTimeMillis(); 6841 6842 FileInputStream fis = null; 6843 try { 6844 fis = mGrantFile.openRead(); 6845 final XmlPullParser in = Xml.newPullParser(); 6846 in.setInput(fis, null); 6847 6848 int type; 6849 while ((type = in.next()) != END_DOCUMENT) { 6850 final String tag = in.getName(); 6851 if (type == START_TAG) { 6852 if (TAG_URI_GRANT.equals(tag)) { 6853 final int sourceUserId; 6854 final int targetUserId; 6855 final int userHandle = readIntAttribute(in, 6856 ATTR_USER_HANDLE, UserHandle.USER_NULL); 6857 if (userHandle != UserHandle.USER_NULL) { 6858 // For backwards compatibility. 6859 sourceUserId = userHandle; 6860 targetUserId = userHandle; 6861 } else { 6862 sourceUserId = readIntAttribute(in, ATTR_SOURCE_USER_ID); 6863 targetUserId = readIntAttribute(in, ATTR_TARGET_USER_ID); 6864 } 6865 final String sourcePkg = in.getAttributeValue(null, ATTR_SOURCE_PKG); 6866 final String targetPkg = in.getAttributeValue(null, ATTR_TARGET_PKG); 6867 final Uri uri = Uri.parse(in.getAttributeValue(null, ATTR_URI)); 6868 final boolean prefix = readBooleanAttribute(in, ATTR_PREFIX); 6869 final int modeFlags = readIntAttribute(in, ATTR_MODE_FLAGS); 6870 final long createdTime = readLongAttribute(in, ATTR_CREATED_TIME, now); 6871 6872 // Sanity check that provider still belongs to source package 6873 final ProviderInfo pi = getProviderInfoLocked( 6874 uri.getAuthority(), sourceUserId); 6875 if (pi != null && sourcePkg.equals(pi.packageName)) { 6876 int targetUid = -1; 6877 try { 6878 targetUid = AppGlobals.getPackageManager() 6879 .getPackageUid(targetPkg, targetUserId); 6880 } catch (RemoteException e) { 6881 } 6882 if (targetUid != -1) { 6883 final UriPermission perm = findOrCreateUriPermissionLocked( 6884 sourcePkg, targetPkg, targetUid, 6885 new GrantUri(sourceUserId, uri, prefix)); 6886 perm.initPersistedModes(modeFlags, createdTime); 6887 } 6888 } else { 6889 Slog.w(TAG, "Persisted grant for " + uri + " had source " + sourcePkg 6890 + " but instead found " + pi); 6891 } 6892 } 6893 } 6894 } 6895 } catch (FileNotFoundException e) { 6896 // Missing grants is okay 6897 } catch (IOException e) { 6898 Log.wtf(TAG, "Failed reading Uri grants", e); 6899 } catch (XmlPullParserException e) { 6900 Log.wtf(TAG, "Failed reading Uri grants", e); 6901 } finally { 6902 IoUtils.closeQuietly(fis); 6903 } 6904 } 6905 6906 @Override 6907 public void takePersistableUriPermission(Uri uri, final int modeFlags, int userId) { 6908 enforceNotIsolatedCaller("takePersistableUriPermission"); 6909 6910 Preconditions.checkFlagsArgument(modeFlags, 6911 Intent.FLAG_GRANT_READ_URI_PERMISSION | Intent.FLAG_GRANT_WRITE_URI_PERMISSION); 6912 6913 synchronized (this) { 6914 final int callingUid = Binder.getCallingUid(); 6915 boolean persistChanged = false; 6916 GrantUri grantUri = new GrantUri(userId, uri, false); 6917 6918 UriPermission exactPerm = findUriPermissionLocked(callingUid, 6919 new GrantUri(userId, uri, false)); 6920 UriPermission prefixPerm = findUriPermissionLocked(callingUid, 6921 new GrantUri(userId, uri, true)); 6922 6923 final boolean exactValid = (exactPerm != null) 6924 && ((modeFlags & exactPerm.persistableModeFlags) == modeFlags); 6925 final boolean prefixValid = (prefixPerm != null) 6926 && ((modeFlags & prefixPerm.persistableModeFlags) == modeFlags); 6927 6928 if (!(exactValid || prefixValid)) { 6929 throw new SecurityException("No persistable permission grants found for UID " 6930 + callingUid + " and Uri " + grantUri.toSafeString()); 6931 } 6932 6933 if (exactValid) { 6934 persistChanged |= exactPerm.takePersistableModes(modeFlags); 6935 } 6936 if (prefixValid) { 6937 persistChanged |= prefixPerm.takePersistableModes(modeFlags); 6938 } 6939 6940 persistChanged |= maybePrunePersistedUriGrantsLocked(callingUid); 6941 6942 if (persistChanged) { 6943 schedulePersistUriGrants(); 6944 } 6945 } 6946 } 6947 6948 @Override 6949 public void releasePersistableUriPermission(Uri uri, final int modeFlags, int userId) { 6950 enforceNotIsolatedCaller("releasePersistableUriPermission"); 6951 6952 Preconditions.checkFlagsArgument(modeFlags, 6953 Intent.FLAG_GRANT_READ_URI_PERMISSION | Intent.FLAG_GRANT_WRITE_URI_PERMISSION); 6954 6955 synchronized (this) { 6956 final int callingUid = Binder.getCallingUid(); 6957 boolean persistChanged = false; 6958 6959 UriPermission exactPerm = findUriPermissionLocked(callingUid, 6960 new GrantUri(userId, uri, false)); 6961 UriPermission prefixPerm = findUriPermissionLocked(callingUid, 6962 new GrantUri(userId, uri, true)); 6963 if (exactPerm == null && prefixPerm == null) { 6964 throw new SecurityException("No permission grants found for UID " + callingUid 6965 + " and Uri " + uri.toSafeString()); 6966 } 6967 6968 if (exactPerm != null) { 6969 persistChanged |= exactPerm.releasePersistableModes(modeFlags); 6970 removeUriPermissionIfNeededLocked(exactPerm); 6971 } 6972 if (prefixPerm != null) { 6973 persistChanged |= prefixPerm.releasePersistableModes(modeFlags); 6974 removeUriPermissionIfNeededLocked(prefixPerm); 6975 } 6976 6977 if (persistChanged) { 6978 schedulePersistUriGrants(); 6979 } 6980 } 6981 } 6982 6983 /** 6984 * Prune any older {@link UriPermission} for the given UID until outstanding 6985 * persisted grants are below {@link #MAX_PERSISTED_URI_GRANTS}. 6986 * 6987 * @return if any mutations occured that require persisting. 6988 */ 6989 private boolean maybePrunePersistedUriGrantsLocked(int uid) { 6990 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get(uid); 6991 if (perms == null) return false; 6992 if (perms.size() < MAX_PERSISTED_URI_GRANTS) return false; 6993 6994 final ArrayList<UriPermission> persisted = Lists.newArrayList(); 6995 for (UriPermission perm : perms.values()) { 6996 if (perm.persistedModeFlags != 0) { 6997 persisted.add(perm); 6998 } 6999 } 7000 7001 final int trimCount = persisted.size() - MAX_PERSISTED_URI_GRANTS; 7002 if (trimCount <= 0) return false; 7003 7004 Collections.sort(persisted, new UriPermission.PersistedTimeComparator()); 7005 for (int i = 0; i < trimCount; i++) { 7006 final UriPermission perm = persisted.get(i); 7007 7008 if (DEBUG_URI_PERMISSION) { 7009 Slog.v(TAG, "Trimming grant created at " + perm.persistedCreateTime); 7010 } 7011 7012 perm.releasePersistableModes(~0); 7013 removeUriPermissionIfNeededLocked(perm); 7014 } 7015 7016 return true; 7017 } 7018 7019 @Override 7020 public ParceledListSlice<android.content.UriPermission> getPersistedUriPermissions( 7021 String packageName, boolean incoming) { 7022 enforceNotIsolatedCaller("getPersistedUriPermissions"); 7023 Preconditions.checkNotNull(packageName, "packageName"); 7024 7025 final int callingUid = Binder.getCallingUid(); 7026 final IPackageManager pm = AppGlobals.getPackageManager(); 7027 try { 7028 final int packageUid = pm.getPackageUid(packageName, UserHandle.getUserId(callingUid)); 7029 if (packageUid != callingUid) { 7030 throw new SecurityException( 7031 "Package " + packageName + " does not belong to calling UID " + callingUid); 7032 } 7033 } catch (RemoteException e) { 7034 throw new SecurityException("Failed to verify package name ownership"); 7035 } 7036 7037 final ArrayList<android.content.UriPermission> result = Lists.newArrayList(); 7038 synchronized (this) { 7039 if (incoming) { 7040 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get( 7041 callingUid); 7042 if (perms == null) { 7043 Slog.w(TAG, "No permission grants found for " + packageName); 7044 } else { 7045 for (UriPermission perm : perms.values()) { 7046 if (packageName.equals(perm.targetPkg) && perm.persistedModeFlags != 0) { 7047 result.add(perm.buildPersistedPublicApiObject()); 7048 } 7049 } 7050 } 7051 } else { 7052 final int size = mGrantedUriPermissions.size(); 7053 for (int i = 0; i < size; i++) { 7054 final ArrayMap<GrantUri, UriPermission> perms = 7055 mGrantedUriPermissions.valueAt(i); 7056 for (UriPermission perm : perms.values()) { 7057 if (packageName.equals(perm.sourcePkg) && perm.persistedModeFlags != 0) { 7058 result.add(perm.buildPersistedPublicApiObject()); 7059 } 7060 } 7061 } 7062 } 7063 } 7064 return new ParceledListSlice<android.content.UriPermission>(result); 7065 } 7066 7067 @Override 7068 public void showWaitingForDebugger(IApplicationThread who, boolean waiting) { 7069 synchronized (this) { 7070 ProcessRecord app = 7071 who != null ? getRecordForAppLocked(who) : null; 7072 if (app == null) return; 7073 7074 Message msg = Message.obtain(); 7075 msg.what = WAIT_FOR_DEBUGGER_MSG; 7076 msg.obj = app; 7077 msg.arg1 = waiting ? 1 : 0; 7078 mHandler.sendMessage(msg); 7079 } 7080 } 7081 7082 @Override 7083 public void getMemoryInfo(ActivityManager.MemoryInfo outInfo) { 7084 final long homeAppMem = mProcessList.getMemLevel(ProcessList.HOME_APP_ADJ); 7085 final long cachedAppMem = mProcessList.getMemLevel(ProcessList.CACHED_APP_MIN_ADJ); 7086 outInfo.availMem = Process.getFreeMemory(); 7087 outInfo.totalMem = Process.getTotalMemory(); 7088 outInfo.threshold = homeAppMem; 7089 outInfo.lowMemory = outInfo.availMem < (homeAppMem + ((cachedAppMem-homeAppMem)/2)); 7090 outInfo.hiddenAppThreshold = cachedAppMem; 7091 outInfo.secondaryServerThreshold = mProcessList.getMemLevel( 7092 ProcessList.SERVICE_ADJ); 7093 outInfo.visibleAppThreshold = mProcessList.getMemLevel( 7094 ProcessList.VISIBLE_APP_ADJ); 7095 outInfo.foregroundAppThreshold = mProcessList.getMemLevel( 7096 ProcessList.FOREGROUND_APP_ADJ); 7097 } 7098 7099 // ========================================================= 7100 // TASK MANAGEMENT 7101 // ========================================================= 7102 7103 @Override 7104 public List<IAppTask> getAppTasks() { 7105 int callingUid = Binder.getCallingUid(); 7106 long ident = Binder.clearCallingIdentity(); 7107 synchronized(this) { 7108 ArrayList<IAppTask> list = new ArrayList<IAppTask>(); 7109 try { 7110 if (localLOGV) Slog.v(TAG, "getAppTasks"); 7111 7112 final int N = mRecentTasks.size(); 7113 for (int i = 0; i < N; i++) { 7114 TaskRecord tr = mRecentTasks.get(i); 7115 // Skip tasks that are not created by the caller 7116 if (tr.creatorUid == callingUid) { 7117 ActivityManager.RecentTaskInfo taskInfo = 7118 createRecentTaskInfoFromTaskRecord(tr); 7119 AppTaskImpl taskImpl = new AppTaskImpl(taskInfo.persistentId, callingUid); 7120 list.add(taskImpl); 7121 } 7122 } 7123 } finally { 7124 Binder.restoreCallingIdentity(ident); 7125 } 7126 return list; 7127 } 7128 } 7129 7130 @Override 7131 public List<RunningTaskInfo> getTasks(int maxNum, int flags) { 7132 final int callingUid = Binder.getCallingUid(); 7133 ArrayList<RunningTaskInfo> list = new ArrayList<RunningTaskInfo>(); 7134 7135 synchronized(this) { 7136 if (localLOGV) Slog.v( 7137 TAG, "getTasks: max=" + maxNum + ", flags=" + flags); 7138 7139 final boolean allowed = checkCallingPermission( 7140 android.Manifest.permission.GET_TASKS) 7141 == PackageManager.PERMISSION_GRANTED; 7142 if (!allowed) { 7143 Slog.w(TAG, "getTasks: caller " + callingUid 7144 + " does not hold GET_TASKS; limiting output"); 7145 } 7146 7147 // TODO: Improve with MRU list from all ActivityStacks. 7148 mStackSupervisor.getTasksLocked(maxNum, list, callingUid, allowed); 7149 } 7150 7151 return list; 7152 } 7153 7154 TaskRecord getMostRecentTask() { 7155 return mRecentTasks.get(0); 7156 } 7157 7158 /** 7159 * Creates a new RecentTaskInfo from a TaskRecord. 7160 */ 7161 private ActivityManager.RecentTaskInfo createRecentTaskInfoFromTaskRecord(TaskRecord tr) { 7162 // Update the task description to reflect any changes in the task stack 7163 tr.updateTaskDescription(); 7164 7165 // Compose the recent task info 7166 ActivityManager.RecentTaskInfo rti 7167 = new ActivityManager.RecentTaskInfo(); 7168 rti.id = tr.mActivities.isEmpty() ? -1 : tr.taskId; 7169 rti.persistentId = tr.taskId; 7170 rti.baseIntent = new Intent(tr.getBaseIntent()); 7171 rti.origActivity = tr.origActivity; 7172 rti.description = tr.lastDescription; 7173 rti.stackId = tr.stack != null ? tr.stack.mStackId : -1; 7174 rti.userId = tr.userId; 7175 rti.taskDescription = new ActivityManager.TaskDescription(tr.lastTaskDescription); 7176 return rti; 7177 } 7178 7179 @Override 7180 public List<ActivityManager.RecentTaskInfo> getRecentTasks(int maxNum, 7181 int flags, int userId) { 7182 final int callingUid = Binder.getCallingUid(); 7183 userId = handleIncomingUser(Binder.getCallingPid(), callingUid, userId, 7184 false, true, "getRecentTasks", null); 7185 7186 synchronized (this) { 7187 final boolean allowed = checkCallingPermission( 7188 android.Manifest.permission.GET_TASKS) 7189 == PackageManager.PERMISSION_GRANTED; 7190 if (!allowed) { 7191 Slog.w(TAG, "getRecentTasks: caller " + callingUid 7192 + " does not hold GET_TASKS; limiting output"); 7193 } 7194 final boolean detailed = checkCallingPermission( 7195 android.Manifest.permission.GET_DETAILED_TASKS) 7196 == PackageManager.PERMISSION_GRANTED; 7197 7198 IPackageManager pm = AppGlobals.getPackageManager(); 7199 7200 final int N = mRecentTasks.size(); 7201 ArrayList<ActivityManager.RecentTaskInfo> res 7202 = new ArrayList<ActivityManager.RecentTaskInfo>( 7203 maxNum < N ? maxNum : N); 7204 7205 final Set<Integer> includedUsers; 7206 if ((flags & ActivityManager.RECENT_INCLUDE_PROFILES) != 0) { 7207 includedUsers = getProfileIdsLocked(userId); 7208 } else { 7209 includedUsers = new HashSet<Integer>(); 7210 } 7211 includedUsers.add(Integer.valueOf(userId)); 7212 for (int i=0; i<N && maxNum > 0; i++) { 7213 TaskRecord tr = mRecentTasks.get(i); 7214 // Only add calling user or related users recent tasks 7215 if (!includedUsers.contains(Integer.valueOf(tr.userId))) continue; 7216 7217 // Return the entry if desired by the caller. We always return 7218 // the first entry, because callers always expect this to be the 7219 // foreground app. We may filter others if the caller has 7220 // not supplied RECENT_WITH_EXCLUDED and there is some reason 7221 // we should exclude the entry. 7222 7223 if (i == 0 7224 || ((flags&ActivityManager.RECENT_WITH_EXCLUDED) != 0) 7225 || (tr.intent == null) 7226 || ((tr.intent.getFlags() 7227 &Intent.FLAG_ACTIVITY_EXCLUDE_FROM_RECENTS) == 0)) { 7228 if (!allowed) { 7229 // If the caller doesn't have the GET_TASKS permission, then only 7230 // allow them to see a small subset of tasks -- their own and home. 7231 if (!tr.isHomeTask() && tr.creatorUid != callingUid) { 7232 continue; 7233 } 7234 } 7235 7236 ActivityManager.RecentTaskInfo rti = createRecentTaskInfoFromTaskRecord(tr); 7237 if (!detailed) { 7238 rti.baseIntent.replaceExtras((Bundle)null); 7239 } 7240 7241 if ((flags&ActivityManager.RECENT_IGNORE_UNAVAILABLE) != 0) { 7242 // Check whether this activity is currently available. 7243 try { 7244 if (rti.origActivity != null) { 7245 if (pm.getActivityInfo(rti.origActivity, 0, userId) 7246 == null) { 7247 continue; 7248 } 7249 } else if (rti.baseIntent != null) { 7250 if (pm.queryIntentActivities(rti.baseIntent, 7251 null, 0, userId) == null) { 7252 continue; 7253 } 7254 } 7255 } catch (RemoteException e) { 7256 // Will never happen. 7257 } 7258 } 7259 7260 res.add(rti); 7261 maxNum--; 7262 } 7263 } 7264 return res; 7265 } 7266 } 7267 7268 private TaskRecord recentTaskForIdLocked(int id) { 7269 final int N = mRecentTasks.size(); 7270 for (int i=0; i<N; i++) { 7271 TaskRecord tr = mRecentTasks.get(i); 7272 if (tr.taskId == id) { 7273 return tr; 7274 } 7275 } 7276 return null; 7277 } 7278 7279 @Override 7280 public ActivityManager.TaskThumbnails getTaskThumbnails(int id) { 7281 synchronized (this) { 7282 enforceCallingPermission(android.Manifest.permission.READ_FRAME_BUFFER, 7283 "getTaskThumbnails()"); 7284 TaskRecord tr = recentTaskForIdLocked(id); 7285 if (tr != null) { 7286 return tr.getTaskThumbnailsLocked(); 7287 } 7288 } 7289 return null; 7290 } 7291 7292 @Override 7293 public Bitmap getTaskTopThumbnail(int id) { 7294 synchronized (this) { 7295 enforceCallingPermission(android.Manifest.permission.READ_FRAME_BUFFER, 7296 "getTaskTopThumbnail()"); 7297 TaskRecord tr = recentTaskForIdLocked(id); 7298 if (tr != null) { 7299 return tr.getTaskTopThumbnailLocked(); 7300 } 7301 } 7302 return null; 7303 } 7304 7305 @Override 7306 public void setTaskDescription(IBinder token, ActivityManager.TaskDescription td) { 7307 synchronized (this) { 7308 ActivityRecord r = ActivityRecord.isInStackLocked(token); 7309 if (r != null) { 7310 r.taskDescription = td; 7311 r.task.updateTaskDescription(); 7312 } 7313 } 7314 } 7315 7316 @Override 7317 public boolean removeSubTask(int taskId, int subTaskIndex) { 7318 synchronized (this) { 7319 enforceCallingPermission(android.Manifest.permission.REMOVE_TASKS, 7320 "removeSubTask()"); 7321 long ident = Binder.clearCallingIdentity(); 7322 try { 7323 TaskRecord tr = recentTaskForIdLocked(taskId); 7324 if (tr != null) { 7325 return tr.removeTaskActivitiesLocked(subTaskIndex, true) != null; 7326 } 7327 return false; 7328 } finally { 7329 Binder.restoreCallingIdentity(ident); 7330 } 7331 } 7332 } 7333 7334 private void killUnneededProcessLocked(ProcessRecord pr, String reason) { 7335 if (!pr.killedByAm) { 7336 Slog.i(TAG, "Killing " + pr.toShortString() + " (adj " + pr.setAdj + "): " + reason); 7337 EventLog.writeEvent(EventLogTags.AM_KILL, pr.userId, pr.pid, 7338 pr.processName, pr.setAdj, reason); 7339 pr.killedByAm = true; 7340 Process.killProcessQuiet(pr.pid); 7341 } 7342 } 7343 7344 private void cleanUpRemovedTaskLocked(TaskRecord tr, int flags) { 7345 tr.disposeThumbnail(); 7346 mRecentTasks.remove(tr); 7347 final boolean killProcesses = (flags&ActivityManager.REMOVE_TASK_KILL_PROCESS) != 0; 7348 Intent baseIntent = new Intent( 7349 tr.intent != null ? tr.intent : tr.affinityIntent); 7350 ComponentName component = baseIntent.getComponent(); 7351 if (component == null) { 7352 Slog.w(TAG, "Now component for base intent of task: " + tr); 7353 return; 7354 } 7355 7356 // Find any running services associated with this app. 7357 mServices.cleanUpRemovedTaskLocked(tr, component, baseIntent); 7358 7359 if (killProcesses) { 7360 // Find any running processes associated with this app. 7361 final String pkg = component.getPackageName(); 7362 ArrayList<ProcessRecord> procs = new ArrayList<ProcessRecord>(); 7363 ArrayMap<String, SparseArray<ProcessRecord>> pmap = mProcessNames.getMap(); 7364 for (int i=0; i<pmap.size(); i++) { 7365 SparseArray<ProcessRecord> uids = pmap.valueAt(i); 7366 for (int j=0; j<uids.size(); j++) { 7367 ProcessRecord proc = uids.valueAt(j); 7368 if (proc.userId != tr.userId) { 7369 continue; 7370 } 7371 if (!proc.pkgList.containsKey(pkg)) { 7372 continue; 7373 } 7374 procs.add(proc); 7375 } 7376 } 7377 7378 // Kill the running processes. 7379 for (int i=0; i<procs.size(); i++) { 7380 ProcessRecord pr = procs.get(i); 7381 if (pr == mHomeProcess) { 7382 // Don't kill the home process along with tasks from the same package. 7383 continue; 7384 } 7385 if (pr.setSchedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE) { 7386 killUnneededProcessLocked(pr, "remove task"); 7387 } else { 7388 pr.waitingToKill = "remove task"; 7389 } 7390 } 7391 } 7392 } 7393 7394 /** 7395 * Removes the task with the specified task id. 7396 * 7397 * @param taskId Identifier of the task to be removed. 7398 * @param flags Additional operational flags. May be 0 or 7399 * {@link ActivityManager#REMOVE_TASK_KILL_PROCESS}. 7400 * @return Returns true if the given task was found and removed. 7401 */ 7402 private boolean removeTaskByIdLocked(int taskId, int flags) { 7403 TaskRecord tr = recentTaskForIdLocked(taskId); 7404 if (tr != null) { 7405 tr.removeTaskActivitiesLocked(-1, false); 7406 cleanUpRemovedTaskLocked(tr, flags); 7407 if (tr.isPersistable) { 7408 notifyTaskPersisterLocked(tr, true); 7409 } 7410 return true; 7411 } 7412 return false; 7413 } 7414 7415 @Override 7416 public boolean removeTask(int taskId, int flags) { 7417 synchronized (this) { 7418 enforceCallingPermission(android.Manifest.permission.REMOVE_TASKS, 7419 "removeTask()"); 7420 long ident = Binder.clearCallingIdentity(); 7421 try { 7422 return removeTaskByIdLocked(taskId, flags); 7423 } finally { 7424 Binder.restoreCallingIdentity(ident); 7425 } 7426 } 7427 } 7428 7429 /** 7430 * TODO: Add mController hook 7431 */ 7432 @Override 7433 public void moveTaskToFront(int taskId, int flags, Bundle options) { 7434 enforceCallingPermission(android.Manifest.permission.REORDER_TASKS, 7435 "moveTaskToFront()"); 7436 7437 if (DEBUG_STACK) Slog.d(TAG, "moveTaskToFront: moving taskId=" + taskId); 7438 synchronized(this) { 7439 if (!checkAppSwitchAllowedLocked(Binder.getCallingPid(), 7440 Binder.getCallingUid(), "Task to front")) { 7441 ActivityOptions.abort(options); 7442 return; 7443 } 7444 final long origId = Binder.clearCallingIdentity(); 7445 try { 7446 final TaskRecord task = mStackSupervisor.anyTaskForIdLocked(taskId); 7447 if (task == null) { 7448 return; 7449 } 7450 if (mStackSupervisor.isLockTaskModeViolation(task)) { 7451 Slog.e(TAG, "moveTaskToFront: Attempt to violate Lock Task Mode"); 7452 return; 7453 } 7454 mStackSupervisor.findTaskToMoveToFrontLocked(task, flags, options); 7455 } finally { 7456 Binder.restoreCallingIdentity(origId); 7457 } 7458 ActivityOptions.abort(options); 7459 } 7460 } 7461 7462 @Override 7463 public void moveTaskToBack(int taskId) { 7464 enforceCallingPermission(android.Manifest.permission.REORDER_TASKS, 7465 "moveTaskToBack()"); 7466 7467 synchronized(this) { 7468 TaskRecord tr = recentTaskForIdLocked(taskId); 7469 if (tr != null) { 7470 if (DEBUG_STACK) Slog.d(TAG, "moveTaskToBack: moving task=" + tr); 7471 ActivityStack stack = tr.stack; 7472 if (stack.mResumedActivity != null && stack.mResumedActivity.task == tr) { 7473 if (!checkAppSwitchAllowedLocked(Binder.getCallingPid(), 7474 Binder.getCallingUid(), "Task to back")) { 7475 return; 7476 } 7477 } 7478 final long origId = Binder.clearCallingIdentity(); 7479 try { 7480 stack.moveTaskToBackLocked(taskId, null); 7481 } finally { 7482 Binder.restoreCallingIdentity(origId); 7483 } 7484 } 7485 } 7486 } 7487 7488 /** 7489 * Moves an activity, and all of the other activities within the same task, to the bottom 7490 * of the history stack. The activity's order within the task is unchanged. 7491 * 7492 * @param token A reference to the activity we wish to move 7493 * @param nonRoot If false then this only works if the activity is the root 7494 * of a task; if true it will work for any activity in a task. 7495 * @return Returns true if the move completed, false if not. 7496 */ 7497 @Override 7498 public boolean moveActivityTaskToBack(IBinder token, boolean nonRoot) { 7499 enforceNotIsolatedCaller("moveActivityTaskToBack"); 7500 synchronized(this) { 7501 final long origId = Binder.clearCallingIdentity(); 7502 int taskId = ActivityRecord.getTaskForActivityLocked(token, !nonRoot); 7503 if (taskId >= 0) { 7504 return ActivityRecord.getStackLocked(token).moveTaskToBackLocked(taskId, null); 7505 } 7506 Binder.restoreCallingIdentity(origId); 7507 } 7508 return false; 7509 } 7510 7511 @Override 7512 public void moveTaskBackwards(int task) { 7513 enforceCallingPermission(android.Manifest.permission.REORDER_TASKS, 7514 "moveTaskBackwards()"); 7515 7516 synchronized(this) { 7517 if (!checkAppSwitchAllowedLocked(Binder.getCallingPid(), 7518 Binder.getCallingUid(), "Task backwards")) { 7519 return; 7520 } 7521 final long origId = Binder.clearCallingIdentity(); 7522 moveTaskBackwardsLocked(task); 7523 Binder.restoreCallingIdentity(origId); 7524 } 7525 } 7526 7527 private final void moveTaskBackwardsLocked(int task) { 7528 Slog.e(TAG, "moveTaskBackwards not yet implemented!"); 7529 } 7530 7531 @Override 7532 public IBinder getHomeActivityToken() throws RemoteException { 7533 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 7534 "getHomeActivityToken()"); 7535 synchronized (this) { 7536 return mStackSupervisor.getHomeActivityToken(); 7537 } 7538 } 7539 7540 @Override 7541 public IActivityContainer createActivityContainer(IBinder parentActivityToken, 7542 IActivityContainerCallback callback) throws RemoteException { 7543 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 7544 "createActivityContainer()"); 7545 synchronized (this) { 7546 if (parentActivityToken == null) { 7547 throw new IllegalArgumentException("parent token must not be null"); 7548 } 7549 ActivityRecord r = ActivityRecord.forToken(parentActivityToken); 7550 if (r == null) { 7551 return null; 7552 } 7553 if (callback == null) { 7554 throw new IllegalArgumentException("callback must not be null"); 7555 } 7556 return mStackSupervisor.createActivityContainer(r, callback); 7557 } 7558 } 7559 7560 @Override 7561 public void deleteActivityContainer(IActivityContainer container) throws RemoteException { 7562 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 7563 "deleteActivityContainer()"); 7564 synchronized (this) { 7565 mStackSupervisor.deleteActivityContainer(container); 7566 } 7567 } 7568 7569 @Override 7570 public IActivityContainer getEnclosingActivityContainer(IBinder activityToken) 7571 throws RemoteException { 7572 synchronized (this) { 7573 ActivityStack stack = ActivityRecord.getStackLocked(activityToken); 7574 if (stack != null) { 7575 return stack.mActivityContainer; 7576 } 7577 return null; 7578 } 7579 } 7580 7581 @Override 7582 public void moveTaskToStack(int taskId, int stackId, boolean toTop) { 7583 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 7584 "moveTaskToStack()"); 7585 if (stackId == HOME_STACK_ID) { 7586 Slog.e(TAG, "moveTaskToStack: Attempt to move task " + taskId + " to home stack", 7587 new RuntimeException("here").fillInStackTrace()); 7588 } 7589 synchronized (this) { 7590 long ident = Binder.clearCallingIdentity(); 7591 try { 7592 if (DEBUG_STACK) Slog.d(TAG, "moveTaskToStack: moving task=" + taskId + " to stackId=" 7593 + stackId + " toTop=" + toTop); 7594 mStackSupervisor.moveTaskToStack(taskId, stackId, toTop); 7595 } finally { 7596 Binder.restoreCallingIdentity(ident); 7597 } 7598 } 7599 } 7600 7601 @Override 7602 public void resizeStack(int stackBoxId, Rect bounds) { 7603 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 7604 "resizeStackBox()"); 7605 long ident = Binder.clearCallingIdentity(); 7606 try { 7607 mWindowManager.resizeStack(stackBoxId, bounds); 7608 } finally { 7609 Binder.restoreCallingIdentity(ident); 7610 } 7611 } 7612 7613 @Override 7614 public List<StackInfo> getAllStackInfos() { 7615 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 7616 "getAllStackInfos()"); 7617 long ident = Binder.clearCallingIdentity(); 7618 try { 7619 synchronized (this) { 7620 return mStackSupervisor.getAllStackInfosLocked(); 7621 } 7622 } finally { 7623 Binder.restoreCallingIdentity(ident); 7624 } 7625 } 7626 7627 @Override 7628 public StackInfo getStackInfo(int stackId) { 7629 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 7630 "getStackInfo()"); 7631 long ident = Binder.clearCallingIdentity(); 7632 try { 7633 synchronized (this) { 7634 return mStackSupervisor.getStackInfoLocked(stackId); 7635 } 7636 } finally { 7637 Binder.restoreCallingIdentity(ident); 7638 } 7639 } 7640 7641 @Override 7642 public boolean isInHomeStack(int taskId) { 7643 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 7644 "getStackInfo()"); 7645 long ident = Binder.clearCallingIdentity(); 7646 try { 7647 synchronized (this) { 7648 TaskRecord tr = recentTaskForIdLocked(taskId); 7649 return tr != null && tr.stack != null && tr.stack.isHomeStack(); 7650 } 7651 } finally { 7652 Binder.restoreCallingIdentity(ident); 7653 } 7654 } 7655 7656 @Override 7657 public int getTaskForActivity(IBinder token, boolean onlyRoot) { 7658 synchronized(this) { 7659 return ActivityRecord.getTaskForActivityLocked(token, onlyRoot); 7660 } 7661 } 7662 7663 private boolean isLockTaskAuthorized(String pkg) { 7664 final DevicePolicyManager dpm = (DevicePolicyManager) 7665 mContext.getSystemService(Context.DEVICE_POLICY_SERVICE); 7666 try { 7667 int uid = mContext.getPackageManager().getPackageUid(pkg, 7668 Binder.getCallingUserHandle().getIdentifier()); 7669 return (uid == Binder.getCallingUid()) && dpm != null && dpm.isLockTaskPermitted(pkg); 7670 } catch (NameNotFoundException e) { 7671 return false; 7672 } 7673 } 7674 7675 void startLockTaskMode(TaskRecord task) { 7676 final String pkg; 7677 synchronized (this) { 7678 pkg = task.intent.getComponent().getPackageName(); 7679 } 7680 boolean isSystemInitiated = Binder.getCallingUid() == Process.SYSTEM_UID; 7681 if (!isSystemInitiated && !isLockTaskAuthorized(pkg)) { 7682 final TaskRecord taskRecord = task; 7683 mHandler.post(new Runnable() { 7684 @Override 7685 public void run() { 7686 mLockToAppRequest.showLockTaskPrompt(taskRecord); 7687 } 7688 }); 7689 return; 7690 } 7691 long ident = Binder.clearCallingIdentity(); 7692 try { 7693 synchronized (this) { 7694 // Since we lost lock on task, make sure it is still there. 7695 task = mStackSupervisor.anyTaskForIdLocked(task.taskId); 7696 if (task != null) { 7697 if ((mFocusedActivity == null) || (task != mFocusedActivity.task)) { 7698 throw new IllegalArgumentException("Invalid task, not in foreground"); 7699 } 7700 mStackSupervisor.setLockTaskModeLocked(task, isSystemInitiated); 7701 } 7702 } 7703 } finally { 7704 Binder.restoreCallingIdentity(ident); 7705 } 7706 } 7707 7708 @Override 7709 public void startLockTaskMode(int taskId) { 7710 final TaskRecord task; 7711 long ident = Binder.clearCallingIdentity(); 7712 try { 7713 synchronized (this) { 7714 task = mStackSupervisor.anyTaskForIdLocked(taskId); 7715 } 7716 } finally { 7717 Binder.restoreCallingIdentity(ident); 7718 } 7719 if (task != null) { 7720 startLockTaskMode(task); 7721 } 7722 } 7723 7724 @Override 7725 public void startLockTaskMode(IBinder token) { 7726 final TaskRecord task; 7727 long ident = Binder.clearCallingIdentity(); 7728 try { 7729 synchronized (this) { 7730 final ActivityRecord r = ActivityRecord.forToken(token); 7731 if (r == null) { 7732 return; 7733 } 7734 task = r.task; 7735 } 7736 } finally { 7737 Binder.restoreCallingIdentity(ident); 7738 } 7739 if (task != null) { 7740 startLockTaskMode(task); 7741 } 7742 } 7743 7744 @Override 7745 public void startLockTaskModeOnCurrent() throws RemoteException { 7746 checkCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS); 7747 ActivityRecord r = null; 7748 synchronized (this) { 7749 r = mStackSupervisor.topRunningActivityLocked(); 7750 } 7751 startLockTaskMode(r.task); 7752 } 7753 7754 @Override 7755 public void stopLockTaskMode() { 7756 // Verify that the user matches the package of the intent for the TaskRecord 7757 // we are locked to or systtem. This will ensure the same caller for startLockTaskMode 7758 // and stopLockTaskMode. 7759 final int callingUid = Binder.getCallingUid(); 7760 if (callingUid != Process.SYSTEM_UID) { 7761 try { 7762 String pkg = 7763 mStackSupervisor.mLockTaskModeTask.intent.getComponent().getPackageName(); 7764 int uid = mContext.getPackageManager().getPackageUid(pkg, 7765 Binder.getCallingUserHandle().getIdentifier()); 7766 if (uid != callingUid) { 7767 throw new SecurityException("Invalid uid, expected " + uid); 7768 } 7769 } catch (NameNotFoundException e) { 7770 Log.d(TAG, "stopLockTaskMode " + e); 7771 return; 7772 } 7773 } 7774 long ident = Binder.clearCallingIdentity(); 7775 try { 7776 Log.d(TAG, "stopLockTaskMode"); 7777 // Stop lock task 7778 synchronized (this) { 7779 mStackSupervisor.setLockTaskModeLocked(null, false); 7780 } 7781 } finally { 7782 Binder.restoreCallingIdentity(ident); 7783 } 7784 } 7785 7786 @Override 7787 public void stopLockTaskModeOnCurrent() throws RemoteException { 7788 checkCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS); 7789 long ident = Binder.clearCallingIdentity(); 7790 try { 7791 stopLockTaskMode(); 7792 } finally { 7793 Binder.restoreCallingIdentity(ident); 7794 } 7795 } 7796 7797 @Override 7798 public boolean isInLockTaskMode() { 7799 synchronized (this) { 7800 return mStackSupervisor.isInLockTaskMode(); 7801 } 7802 } 7803 7804 // ========================================================= 7805 // CONTENT PROVIDERS 7806 // ========================================================= 7807 7808 private final List<ProviderInfo> generateApplicationProvidersLocked(ProcessRecord app) { 7809 List<ProviderInfo> providers = null; 7810 try { 7811 providers = AppGlobals.getPackageManager(). 7812 queryContentProviders(app.processName, app.uid, 7813 STOCK_PM_FLAGS | PackageManager.GET_URI_PERMISSION_PATTERNS); 7814 } catch (RemoteException ex) { 7815 } 7816 if (DEBUG_MU) 7817 Slog.v(TAG_MU, "generateApplicationProvidersLocked, app.info.uid = " + app.uid); 7818 int userId = app.userId; 7819 if (providers != null) { 7820 int N = providers.size(); 7821 app.pubProviders.ensureCapacity(N + app.pubProviders.size()); 7822 for (int i=0; i<N; i++) { 7823 ProviderInfo cpi = 7824 (ProviderInfo)providers.get(i); 7825 boolean singleton = isSingleton(cpi.processName, cpi.applicationInfo, 7826 cpi.name, cpi.flags); 7827 if (singleton && UserHandle.getUserId(app.uid) != 0) { 7828 // This is a singleton provider, but a user besides the 7829 // default user is asking to initialize a process it runs 7830 // in... well, no, it doesn't actually run in this process, 7831 // it runs in the process of the default user. Get rid of it. 7832 providers.remove(i); 7833 N--; 7834 i--; 7835 continue; 7836 } 7837 7838 ComponentName comp = new ComponentName(cpi.packageName, cpi.name); 7839 ContentProviderRecord cpr = mProviderMap.getProviderByClass(comp, userId); 7840 if (cpr == null) { 7841 cpr = new ContentProviderRecord(this, cpi, app.info, comp, singleton); 7842 mProviderMap.putProviderByClass(comp, cpr); 7843 } 7844 if (DEBUG_MU) 7845 Slog.v(TAG_MU, "generateApplicationProvidersLocked, cpi.uid = " + cpr.uid); 7846 app.pubProviders.put(cpi.name, cpr); 7847 if (!cpi.multiprocess || !"android".equals(cpi.packageName)) { 7848 // Don't add this if it is a platform component that is marked 7849 // to run in multiple processes, because this is actually 7850 // part of the framework so doesn't make sense to track as a 7851 // separate apk in the process. 7852 app.addPackage(cpi.applicationInfo.packageName, mProcessStats); 7853 } 7854 ensurePackageDexOpt(cpi.applicationInfo.packageName); 7855 } 7856 } 7857 return providers; 7858 } 7859 7860 /** 7861 * Check if {@link ProcessRecord} has a possible chance at accessing the 7862 * given {@link ProviderInfo}. Final permission checking is always done 7863 * in {@link ContentProvider}. 7864 */ 7865 private final String checkContentProviderPermissionLocked( 7866 ProviderInfo cpi, ProcessRecord r, int userId, boolean checkUser) { 7867 final int callingPid = (r != null) ? r.pid : Binder.getCallingPid(); 7868 final int callingUid = (r != null) ? r.uid : Binder.getCallingUid(); 7869 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get(callingUid); 7870 // Looking for cross-user grants before to enforce the typical cross-users permissions 7871 if (userId != UserHandle.getUserId(callingUid)) { 7872 if (perms != null) { 7873 for (GrantUri grantUri : perms.keySet()) { 7874 if (grantUri.sourceUserId == userId) { 7875 String authority = grantUri.uri.getAuthority(); 7876 if (authority.equals(cpi.authority)) { 7877 return null; 7878 } 7879 } 7880 } 7881 } 7882 } 7883 if (checkUser) { 7884 userId = handleIncomingUser(callingPid, callingUid, userId, 7885 false, true, "checkContentProviderPermissionLocked " + cpi.authority, null); 7886 } 7887 if (checkComponentPermission(cpi.readPermission, callingPid, callingUid, 7888 cpi.applicationInfo.uid, cpi.exported) 7889 == PackageManager.PERMISSION_GRANTED) { 7890 return null; 7891 } 7892 if (checkComponentPermission(cpi.writePermission, callingPid, callingUid, 7893 cpi.applicationInfo.uid, cpi.exported) 7894 == PackageManager.PERMISSION_GRANTED) { 7895 return null; 7896 } 7897 7898 PathPermission[] pps = cpi.pathPermissions; 7899 if (pps != null) { 7900 int i = pps.length; 7901 while (i > 0) { 7902 i--; 7903 PathPermission pp = pps[i]; 7904 if (checkComponentPermission(pp.getReadPermission(), callingPid, callingUid, 7905 cpi.applicationInfo.uid, cpi.exported) 7906 == PackageManager.PERMISSION_GRANTED) { 7907 return null; 7908 } 7909 if (checkComponentPermission(pp.getWritePermission(), callingPid, callingUid, 7910 cpi.applicationInfo.uid, cpi.exported) 7911 == PackageManager.PERMISSION_GRANTED) { 7912 return null; 7913 } 7914 } 7915 } 7916 7917 if (perms != null) { 7918 for (GrantUri grantUri : perms.keySet()) { 7919 if (grantUri.uri.getAuthority().equals(cpi.authority)) { 7920 return null; 7921 } 7922 } 7923 } 7924 7925 String msg; 7926 if (!cpi.exported) { 7927 msg = "Permission Denial: opening provider " + cpi.name 7928 + " from " + (r != null ? r : "(null)") + " (pid=" + callingPid 7929 + ", uid=" + callingUid + ") that is not exported from uid " 7930 + cpi.applicationInfo.uid; 7931 } else { 7932 msg = "Permission Denial: opening provider " + cpi.name 7933 + " from " + (r != null ? r : "(null)") + " (pid=" + callingPid 7934 + ", uid=" + callingUid + ") requires " 7935 + cpi.readPermission + " or " + cpi.writePermission; 7936 } 7937 Slog.w(TAG, msg); 7938 return msg; 7939 } 7940 7941 ContentProviderConnection incProviderCountLocked(ProcessRecord r, 7942 final ContentProviderRecord cpr, IBinder externalProcessToken, boolean stable) { 7943 if (r != null) { 7944 for (int i=0; i<r.conProviders.size(); i++) { 7945 ContentProviderConnection conn = r.conProviders.get(i); 7946 if (conn.provider == cpr) { 7947 if (DEBUG_PROVIDER) Slog.v(TAG, 7948 "Adding provider requested by " 7949 + r.processName + " from process " 7950 + cpr.info.processName + ": " + cpr.name.flattenToShortString() 7951 + " scnt=" + conn.stableCount + " uscnt=" + conn.unstableCount); 7952 if (stable) { 7953 conn.stableCount++; 7954 conn.numStableIncs++; 7955 } else { 7956 conn.unstableCount++; 7957 conn.numUnstableIncs++; 7958 } 7959 return conn; 7960 } 7961 } 7962 ContentProviderConnection conn = new ContentProviderConnection(cpr, r); 7963 if (stable) { 7964 conn.stableCount = 1; 7965 conn.numStableIncs = 1; 7966 } else { 7967 conn.unstableCount = 1; 7968 conn.numUnstableIncs = 1; 7969 } 7970 cpr.connections.add(conn); 7971 r.conProviders.add(conn); 7972 return conn; 7973 } 7974 cpr.addExternalProcessHandleLocked(externalProcessToken); 7975 return null; 7976 } 7977 7978 boolean decProviderCountLocked(ContentProviderConnection conn, 7979 ContentProviderRecord cpr, IBinder externalProcessToken, boolean stable) { 7980 if (conn != null) { 7981 cpr = conn.provider; 7982 if (DEBUG_PROVIDER) Slog.v(TAG, 7983 "Removing provider requested by " 7984 + conn.client.processName + " from process " 7985 + cpr.info.processName + ": " + cpr.name.flattenToShortString() 7986 + " scnt=" + conn.stableCount + " uscnt=" + conn.unstableCount); 7987 if (stable) { 7988 conn.stableCount--; 7989 } else { 7990 conn.unstableCount--; 7991 } 7992 if (conn.stableCount == 0 && conn.unstableCount == 0) { 7993 cpr.connections.remove(conn); 7994 conn.client.conProviders.remove(conn); 7995 return true; 7996 } 7997 return false; 7998 } 7999 cpr.removeExternalProcessHandleLocked(externalProcessToken); 8000 return false; 8001 } 8002 8003 private final ContentProviderHolder getContentProviderImpl(IApplicationThread caller, 8004 String name, IBinder token, boolean stable, int userId) { 8005 ContentProviderRecord cpr; 8006 ContentProviderConnection conn = null; 8007 ProviderInfo cpi = null; 8008 8009 synchronized(this) { 8010 ProcessRecord r = null; 8011 if (caller != null) { 8012 r = getRecordForAppLocked(caller); 8013 if (r == null) { 8014 throw new SecurityException( 8015 "Unable to find app for caller " + caller 8016 + " (pid=" + Binder.getCallingPid() 8017 + ") when getting content provider " + name); 8018 } 8019 } 8020 8021 boolean checkCrossUser = true; 8022 8023 // First check if this content provider has been published... 8024 cpr = mProviderMap.getProviderByName(name, userId); 8025 // If that didn't work, check if it exists for user 0 and then 8026 // verify that it's a singleton provider before using it. 8027 if (cpr == null && userId != UserHandle.USER_OWNER) { 8028 cpr = mProviderMap.getProviderByName(name, UserHandle.USER_OWNER); 8029 if (cpr != null) { 8030 cpi = cpr.info; 8031 if (isSingleton(cpi.processName, cpi.applicationInfo, 8032 cpi.name, cpi.flags) 8033 && isValidSingletonCall(r.uid, cpi.applicationInfo.uid)) { 8034 userId = UserHandle.USER_OWNER; 8035 checkCrossUser = false; 8036 } else { 8037 cpr = null; 8038 cpi = null; 8039 } 8040 } 8041 } 8042 8043 boolean providerRunning = cpr != null; 8044 if (providerRunning) { 8045 cpi = cpr.info; 8046 String msg; 8047 if ((msg = checkContentProviderPermissionLocked(cpi, r, userId, checkCrossUser)) 8048 != null) { 8049 throw new SecurityException(msg); 8050 } 8051 8052 if (r != null && cpr.canRunHere(r)) { 8053 // This provider has been published or is in the process 8054 // of being published... but it is also allowed to run 8055 // in the caller's process, so don't make a connection 8056 // and just let the caller instantiate its own instance. 8057 ContentProviderHolder holder = cpr.newHolder(null); 8058 // don't give caller the provider object, it needs 8059 // to make its own. 8060 holder.provider = null; 8061 return holder; 8062 } 8063 8064 final long origId = Binder.clearCallingIdentity(); 8065 8066 // In this case the provider instance already exists, so we can 8067 // return it right away. 8068 conn = incProviderCountLocked(r, cpr, token, stable); 8069 if (conn != null && (conn.stableCount+conn.unstableCount) == 1) { 8070 if (cpr.proc != null && r.setAdj <= ProcessList.PERCEPTIBLE_APP_ADJ) { 8071 // If this is a perceptible app accessing the provider, 8072 // make sure to count it as being accessed and thus 8073 // back up on the LRU list. This is good because 8074 // content providers are often expensive to start. 8075 updateLruProcessLocked(cpr.proc, false, null); 8076 } 8077 } 8078 8079 if (cpr.proc != null) { 8080 if (false) { 8081 if (cpr.name.flattenToShortString().equals( 8082 "com.android.providers.calendar/.CalendarProvider2")) { 8083 Slog.v(TAG, "****************** KILLING " 8084 + cpr.name.flattenToShortString()); 8085 Process.killProcess(cpr.proc.pid); 8086 } 8087 } 8088 boolean success = updateOomAdjLocked(cpr.proc); 8089 if (DEBUG_PROVIDER) Slog.i(TAG, "Adjust success: " + success); 8090 // NOTE: there is still a race here where a signal could be 8091 // pending on the process even though we managed to update its 8092 // adj level. Not sure what to do about this, but at least 8093 // the race is now smaller. 8094 if (!success) { 8095 // Uh oh... it looks like the provider's process 8096 // has been killed on us. We need to wait for a new 8097 // process to be started, and make sure its death 8098 // doesn't kill our process. 8099 Slog.i(TAG, 8100 "Existing provider " + cpr.name.flattenToShortString() 8101 + " is crashing; detaching " + r); 8102 boolean lastRef = decProviderCountLocked(conn, cpr, token, stable); 8103 appDiedLocked(cpr.proc, cpr.proc.pid, cpr.proc.thread); 8104 if (!lastRef) { 8105 // This wasn't the last ref our process had on 8106 // the provider... we have now been killed, bail. 8107 return null; 8108 } 8109 providerRunning = false; 8110 conn = null; 8111 } 8112 } 8113 8114 Binder.restoreCallingIdentity(origId); 8115 } 8116 8117 boolean singleton; 8118 if (!providerRunning) { 8119 try { 8120 cpi = AppGlobals.getPackageManager(). 8121 resolveContentProvider(name, 8122 STOCK_PM_FLAGS | PackageManager.GET_URI_PERMISSION_PATTERNS, userId); 8123 } catch (RemoteException ex) { 8124 } 8125 if (cpi == null) { 8126 return null; 8127 } 8128 // If the provider is a singleton AND 8129 // (it's a call within the same user || the provider is a 8130 // privileged app) 8131 // Then allow connecting to the singleton provider 8132 singleton = isSingleton(cpi.processName, cpi.applicationInfo, 8133 cpi.name, cpi.flags) 8134 && isValidSingletonCall(r.uid, cpi.applicationInfo.uid); 8135 if (singleton) { 8136 userId = UserHandle.USER_OWNER; 8137 } 8138 cpi.applicationInfo = getAppInfoForUser(cpi.applicationInfo, userId); 8139 8140 String msg; 8141 if ((msg = checkContentProviderPermissionLocked(cpi, r, userId, !singleton)) 8142 != null) { 8143 throw new SecurityException(msg); 8144 } 8145 8146 if (!mProcessesReady && !mDidUpdate && !mWaitingUpdate 8147 && !cpi.processName.equals("system")) { 8148 // If this content provider does not run in the system 8149 // process, and the system is not yet ready to run other 8150 // processes, then fail fast instead of hanging. 8151 throw new IllegalArgumentException( 8152 "Attempt to launch content provider before system ready"); 8153 } 8154 8155 // Make sure that the user who owns this provider is started. If not, 8156 // we don't want to allow it to run. 8157 if (mStartedUsers.get(userId) == null) { 8158 Slog.w(TAG, "Unable to launch app " 8159 + cpi.applicationInfo.packageName + "/" 8160 + cpi.applicationInfo.uid + " for provider " 8161 + name + ": user " + userId + " is stopped"); 8162 return null; 8163 } 8164 8165 ComponentName comp = new ComponentName(cpi.packageName, cpi.name); 8166 cpr = mProviderMap.getProviderByClass(comp, userId); 8167 final boolean firstClass = cpr == null; 8168 if (firstClass) { 8169 try { 8170 ApplicationInfo ai = 8171 AppGlobals.getPackageManager(). 8172 getApplicationInfo( 8173 cpi.applicationInfo.packageName, 8174 STOCK_PM_FLAGS, userId); 8175 if (ai == null) { 8176 Slog.w(TAG, "No package info for content provider " 8177 + cpi.name); 8178 return null; 8179 } 8180 ai = getAppInfoForUser(ai, userId); 8181 cpr = new ContentProviderRecord(this, cpi, ai, comp, singleton); 8182 } catch (RemoteException ex) { 8183 // pm is in same process, this will never happen. 8184 } 8185 } 8186 8187 if (r != null && cpr.canRunHere(r)) { 8188 // If this is a multiprocess provider, then just return its 8189 // info and allow the caller to instantiate it. Only do 8190 // this if the provider is the same user as the caller's 8191 // process, or can run as root (so can be in any process). 8192 return cpr.newHolder(null); 8193 } 8194 8195 if (DEBUG_PROVIDER) { 8196 RuntimeException e = new RuntimeException("here"); 8197 Slog.w(TAG, "LAUNCHING REMOTE PROVIDER (myuid " + (r != null ? r.uid : null) 8198 + " pruid " + cpr.appInfo.uid + "): " + cpr.info.name, e); 8199 } 8200 8201 // This is single process, and our app is now connecting to it. 8202 // See if we are already in the process of launching this 8203 // provider. 8204 final int N = mLaunchingProviders.size(); 8205 int i; 8206 for (i=0; i<N; i++) { 8207 if (mLaunchingProviders.get(i) == cpr) { 8208 break; 8209 } 8210 } 8211 8212 // If the provider is not already being launched, then get it 8213 // started. 8214 if (i >= N) { 8215 final long origId = Binder.clearCallingIdentity(); 8216 8217 try { 8218 // Content provider is now in use, its package can't be stopped. 8219 try { 8220 AppGlobals.getPackageManager().setPackageStoppedState( 8221 cpr.appInfo.packageName, false, userId); 8222 } catch (RemoteException e) { 8223 } catch (IllegalArgumentException e) { 8224 Slog.w(TAG, "Failed trying to unstop package " 8225 + cpr.appInfo.packageName + ": " + e); 8226 } 8227 8228 // Use existing process if already started 8229 ProcessRecord proc = getProcessRecordLocked( 8230 cpi.processName, cpr.appInfo.uid, false); 8231 if (proc != null && proc.thread != null) { 8232 if (DEBUG_PROVIDER) { 8233 Slog.d(TAG, "Installing in existing process " + proc); 8234 } 8235 proc.pubProviders.put(cpi.name, cpr); 8236 try { 8237 proc.thread.scheduleInstallProvider(cpi); 8238 } catch (RemoteException e) { 8239 } 8240 } else { 8241 proc = startProcessLocked(cpi.processName, 8242 cpr.appInfo, false, 0, "content provider", 8243 new ComponentName(cpi.applicationInfo.packageName, 8244 cpi.name), false, false, false); 8245 if (proc == null) { 8246 Slog.w(TAG, "Unable to launch app " 8247 + cpi.applicationInfo.packageName + "/" 8248 + cpi.applicationInfo.uid + " for provider " 8249 + name + ": process is bad"); 8250 return null; 8251 } 8252 } 8253 cpr.launchingApp = proc; 8254 mLaunchingProviders.add(cpr); 8255 } finally { 8256 Binder.restoreCallingIdentity(origId); 8257 } 8258 } 8259 8260 // Make sure the provider is published (the same provider class 8261 // may be published under multiple names). 8262 if (firstClass) { 8263 mProviderMap.putProviderByClass(comp, cpr); 8264 } 8265 8266 mProviderMap.putProviderByName(name, cpr); 8267 conn = incProviderCountLocked(r, cpr, token, stable); 8268 if (conn != null) { 8269 conn.waiting = true; 8270 } 8271 } 8272 } 8273 8274 // Wait for the provider to be published... 8275 synchronized (cpr) { 8276 while (cpr.provider == null) { 8277 if (cpr.launchingApp == null) { 8278 Slog.w(TAG, "Unable to launch app " 8279 + cpi.applicationInfo.packageName + "/" 8280 + cpi.applicationInfo.uid + " for provider " 8281 + name + ": launching app became null"); 8282 EventLog.writeEvent(EventLogTags.AM_PROVIDER_LOST_PROCESS, 8283 UserHandle.getUserId(cpi.applicationInfo.uid), 8284 cpi.applicationInfo.packageName, 8285 cpi.applicationInfo.uid, name); 8286 return null; 8287 } 8288 try { 8289 if (DEBUG_MU) { 8290 Slog.v(TAG_MU, "Waiting to start provider " + cpr + " launchingApp=" 8291 + cpr.launchingApp); 8292 } 8293 if (conn != null) { 8294 conn.waiting = true; 8295 } 8296 cpr.wait(); 8297 } catch (InterruptedException ex) { 8298 } finally { 8299 if (conn != null) { 8300 conn.waiting = false; 8301 } 8302 } 8303 } 8304 } 8305 return cpr != null ? cpr.newHolder(conn) : null; 8306 } 8307 8308 @Override 8309 public final ContentProviderHolder getContentProvider( 8310 IApplicationThread caller, String name, int userId, boolean stable) { 8311 enforceNotIsolatedCaller("getContentProvider"); 8312 if (caller == null) { 8313 String msg = "null IApplicationThread when getting content provider " 8314 + name; 8315 Slog.w(TAG, msg); 8316 throw new SecurityException(msg); 8317 } 8318 // The incoming user check is now handled in checkContentProviderPermissionLocked() to deal 8319 // with cross-user grant. 8320 return getContentProviderImpl(caller, name, null, stable, userId); 8321 } 8322 8323 public ContentProviderHolder getContentProviderExternal( 8324 String name, int userId, IBinder token) { 8325 enforceCallingPermission(android.Manifest.permission.ACCESS_CONTENT_PROVIDERS_EXTERNALLY, 8326 "Do not have permission in call getContentProviderExternal()"); 8327 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 8328 false, true, "getContentProvider", null); 8329 return getContentProviderExternalUnchecked(name, token, userId); 8330 } 8331 8332 private ContentProviderHolder getContentProviderExternalUnchecked(String name, 8333 IBinder token, int userId) { 8334 return getContentProviderImpl(null, name, token, true, userId); 8335 } 8336 8337 /** 8338 * Drop a content provider from a ProcessRecord's bookkeeping 8339 */ 8340 public void removeContentProvider(IBinder connection, boolean stable) { 8341 enforceNotIsolatedCaller("removeContentProvider"); 8342 long ident = Binder.clearCallingIdentity(); 8343 try { 8344 synchronized (this) { 8345 ContentProviderConnection conn; 8346 try { 8347 conn = (ContentProviderConnection)connection; 8348 } catch (ClassCastException e) { 8349 String msg ="removeContentProvider: " + connection 8350 + " not a ContentProviderConnection"; 8351 Slog.w(TAG, msg); 8352 throw new IllegalArgumentException(msg); 8353 } 8354 if (conn == null) { 8355 throw new NullPointerException("connection is null"); 8356 } 8357 if (decProviderCountLocked(conn, null, null, stable)) { 8358 updateOomAdjLocked(); 8359 } 8360 } 8361 } finally { 8362 Binder.restoreCallingIdentity(ident); 8363 } 8364 } 8365 8366 public void removeContentProviderExternal(String name, IBinder token) { 8367 enforceCallingPermission(android.Manifest.permission.ACCESS_CONTENT_PROVIDERS_EXTERNALLY, 8368 "Do not have permission in call removeContentProviderExternal()"); 8369 removeContentProviderExternalUnchecked(name, token, UserHandle.getCallingUserId()); 8370 } 8371 8372 private void removeContentProviderExternalUnchecked(String name, IBinder token, int userId) { 8373 synchronized (this) { 8374 ContentProviderRecord cpr = mProviderMap.getProviderByName(name, userId); 8375 if(cpr == null) { 8376 //remove from mProvidersByClass 8377 if(localLOGV) Slog.v(TAG, name+" content provider not found in providers list"); 8378 return; 8379 } 8380 8381 //update content provider record entry info 8382 ComponentName comp = new ComponentName(cpr.info.packageName, cpr.info.name); 8383 ContentProviderRecord localCpr = mProviderMap.getProviderByClass(comp, userId); 8384 if (localCpr.hasExternalProcessHandles()) { 8385 if (localCpr.removeExternalProcessHandleLocked(token)) { 8386 updateOomAdjLocked(); 8387 } else { 8388 Slog.e(TAG, "Attmpt to remove content provider " + localCpr 8389 + " with no external reference for token: " 8390 + token + "."); 8391 } 8392 } else { 8393 Slog.e(TAG, "Attmpt to remove content provider: " + localCpr 8394 + " with no external references."); 8395 } 8396 } 8397 } 8398 8399 public final void publishContentProviders(IApplicationThread caller, 8400 List<ContentProviderHolder> providers) { 8401 if (providers == null) { 8402 return; 8403 } 8404 8405 enforceNotIsolatedCaller("publishContentProviders"); 8406 synchronized (this) { 8407 final ProcessRecord r = getRecordForAppLocked(caller); 8408 if (DEBUG_MU) 8409 Slog.v(TAG_MU, "ProcessRecord uid = " + r.uid); 8410 if (r == null) { 8411 throw new SecurityException( 8412 "Unable to find app for caller " + caller 8413 + " (pid=" + Binder.getCallingPid() 8414 + ") when publishing content providers"); 8415 } 8416 8417 final long origId = Binder.clearCallingIdentity(); 8418 8419 final int N = providers.size(); 8420 for (int i=0; i<N; i++) { 8421 ContentProviderHolder src = providers.get(i); 8422 if (src == null || src.info == null || src.provider == null) { 8423 continue; 8424 } 8425 ContentProviderRecord dst = r.pubProviders.get(src.info.name); 8426 if (DEBUG_MU) 8427 Slog.v(TAG_MU, "ContentProviderRecord uid = " + dst.uid); 8428 if (dst != null) { 8429 ComponentName comp = new ComponentName(dst.info.packageName, dst.info.name); 8430 mProviderMap.putProviderByClass(comp, dst); 8431 String names[] = dst.info.authority.split(";"); 8432 for (int j = 0; j < names.length; j++) { 8433 mProviderMap.putProviderByName(names[j], dst); 8434 } 8435 8436 int NL = mLaunchingProviders.size(); 8437 int j; 8438 for (j=0; j<NL; j++) { 8439 if (mLaunchingProviders.get(j) == dst) { 8440 mLaunchingProviders.remove(j); 8441 j--; 8442 NL--; 8443 } 8444 } 8445 synchronized (dst) { 8446 dst.provider = src.provider; 8447 dst.proc = r; 8448 dst.notifyAll(); 8449 } 8450 updateOomAdjLocked(r); 8451 } 8452 } 8453 8454 Binder.restoreCallingIdentity(origId); 8455 } 8456 } 8457 8458 public boolean refContentProvider(IBinder connection, int stable, int unstable) { 8459 ContentProviderConnection conn; 8460 try { 8461 conn = (ContentProviderConnection)connection; 8462 } catch (ClassCastException e) { 8463 String msg ="refContentProvider: " + connection 8464 + " not a ContentProviderConnection"; 8465 Slog.w(TAG, msg); 8466 throw new IllegalArgumentException(msg); 8467 } 8468 if (conn == null) { 8469 throw new NullPointerException("connection is null"); 8470 } 8471 8472 synchronized (this) { 8473 if (stable > 0) { 8474 conn.numStableIncs += stable; 8475 } 8476 stable = conn.stableCount + stable; 8477 if (stable < 0) { 8478 throw new IllegalStateException("stableCount < 0: " + stable); 8479 } 8480 8481 if (unstable > 0) { 8482 conn.numUnstableIncs += unstable; 8483 } 8484 unstable = conn.unstableCount + unstable; 8485 if (unstable < 0) { 8486 throw new IllegalStateException("unstableCount < 0: " + unstable); 8487 } 8488 8489 if ((stable+unstable) <= 0) { 8490 throw new IllegalStateException("ref counts can't go to zero here: stable=" 8491 + stable + " unstable=" + unstable); 8492 } 8493 conn.stableCount = stable; 8494 conn.unstableCount = unstable; 8495 return !conn.dead; 8496 } 8497 } 8498 8499 public void unstableProviderDied(IBinder connection) { 8500 ContentProviderConnection conn; 8501 try { 8502 conn = (ContentProviderConnection)connection; 8503 } catch (ClassCastException e) { 8504 String msg ="refContentProvider: " + connection 8505 + " not a ContentProviderConnection"; 8506 Slog.w(TAG, msg); 8507 throw new IllegalArgumentException(msg); 8508 } 8509 if (conn == null) { 8510 throw new NullPointerException("connection is null"); 8511 } 8512 8513 // Safely retrieve the content provider associated with the connection. 8514 IContentProvider provider; 8515 synchronized (this) { 8516 provider = conn.provider.provider; 8517 } 8518 8519 if (provider == null) { 8520 // Um, yeah, we're way ahead of you. 8521 return; 8522 } 8523 8524 // Make sure the caller is being honest with us. 8525 if (provider.asBinder().pingBinder()) { 8526 // Er, no, still looks good to us. 8527 synchronized (this) { 8528 Slog.w(TAG, "unstableProviderDied: caller " + Binder.getCallingUid() 8529 + " says " + conn + " died, but we don't agree"); 8530 return; 8531 } 8532 } 8533 8534 // Well look at that! It's dead! 8535 synchronized (this) { 8536 if (conn.provider.provider != provider) { 8537 // But something changed... good enough. 8538 return; 8539 } 8540 8541 ProcessRecord proc = conn.provider.proc; 8542 if (proc == null || proc.thread == null) { 8543 // Seems like the process is already cleaned up. 8544 return; 8545 } 8546 8547 // As far as we're concerned, this is just like receiving a 8548 // death notification... just a bit prematurely. 8549 Slog.i(TAG, "Process " + proc.processName + " (pid " + proc.pid 8550 + ") early provider death"); 8551 final long ident = Binder.clearCallingIdentity(); 8552 try { 8553 appDiedLocked(proc, proc.pid, proc.thread); 8554 } finally { 8555 Binder.restoreCallingIdentity(ident); 8556 } 8557 } 8558 } 8559 8560 @Override 8561 public void appNotRespondingViaProvider(IBinder connection) { 8562 enforceCallingPermission( 8563 android.Manifest.permission.REMOVE_TASKS, "appNotRespondingViaProvider()"); 8564 8565 final ContentProviderConnection conn = (ContentProviderConnection) connection; 8566 if (conn == null) { 8567 Slog.w(TAG, "ContentProviderConnection is null"); 8568 return; 8569 } 8570 8571 final ProcessRecord host = conn.provider.proc; 8572 if (host == null) { 8573 Slog.w(TAG, "Failed to find hosting ProcessRecord"); 8574 return; 8575 } 8576 8577 final long token = Binder.clearCallingIdentity(); 8578 try { 8579 appNotResponding(host, null, null, false, "ContentProvider not responding"); 8580 } finally { 8581 Binder.restoreCallingIdentity(token); 8582 } 8583 } 8584 8585 public final void installSystemProviders() { 8586 List<ProviderInfo> providers; 8587 synchronized (this) { 8588 ProcessRecord app = mProcessNames.get("system", Process.SYSTEM_UID); 8589 providers = generateApplicationProvidersLocked(app); 8590 if (providers != null) { 8591 for (int i=providers.size()-1; i>=0; i--) { 8592 ProviderInfo pi = (ProviderInfo)providers.get(i); 8593 if ((pi.applicationInfo.flags&ApplicationInfo.FLAG_SYSTEM) == 0) { 8594 Slog.w(TAG, "Not installing system proc provider " + pi.name 8595 + ": not system .apk"); 8596 providers.remove(i); 8597 } 8598 } 8599 } 8600 } 8601 if (providers != null) { 8602 mSystemThread.installSystemProviders(providers); 8603 } 8604 8605 mCoreSettingsObserver = new CoreSettingsObserver(this); 8606 8607 mUsageStatsService.monitorPackages(); 8608 } 8609 8610 /** 8611 * Allows app to retrieve the MIME type of a URI without having permission 8612 * to access its content provider. 8613 * 8614 * CTS tests for this functionality can be run with "runtest cts-appsecurity". 8615 * 8616 * Test cases are at cts/tests/appsecurity-tests/test-apps/UsePermissionDiffCert/ 8617 * src/com/android/cts/usespermissiondiffcertapp/AccessPermissionWithDiffSigTest.java 8618 */ 8619 public String getProviderMimeType(Uri uri, int userId) { 8620 enforceNotIsolatedCaller("getProviderMimeType"); 8621 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 8622 userId, false, true, "getProviderMimeType", null); 8623 final String name = uri.getAuthority(); 8624 final long ident = Binder.clearCallingIdentity(); 8625 ContentProviderHolder holder = null; 8626 8627 try { 8628 holder = getContentProviderExternalUnchecked(name, null, userId); 8629 if (holder != null) { 8630 return holder.provider.getType(uri); 8631 } 8632 } catch (RemoteException e) { 8633 Log.w(TAG, "Content provider dead retrieving " + uri, e); 8634 return null; 8635 } finally { 8636 if (holder != null) { 8637 removeContentProviderExternalUnchecked(name, null, userId); 8638 } 8639 Binder.restoreCallingIdentity(ident); 8640 } 8641 8642 return null; 8643 } 8644 8645 // ========================================================= 8646 // GLOBAL MANAGEMENT 8647 // ========================================================= 8648 8649 final ProcessRecord newProcessRecordLocked(ApplicationInfo info, String customProcess, 8650 boolean isolated) { 8651 String proc = customProcess != null ? customProcess : info.processName; 8652 BatteryStatsImpl.Uid.Proc ps = null; 8653 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 8654 int uid = info.uid; 8655 if (isolated) { 8656 int userId = UserHandle.getUserId(uid); 8657 int stepsLeft = Process.LAST_ISOLATED_UID - Process.FIRST_ISOLATED_UID + 1; 8658 while (true) { 8659 if (mNextIsolatedProcessUid < Process.FIRST_ISOLATED_UID 8660 || mNextIsolatedProcessUid > Process.LAST_ISOLATED_UID) { 8661 mNextIsolatedProcessUid = Process.FIRST_ISOLATED_UID; 8662 } 8663 uid = UserHandle.getUid(userId, mNextIsolatedProcessUid); 8664 mNextIsolatedProcessUid++; 8665 if (mIsolatedProcesses.indexOfKey(uid) < 0) { 8666 // No process for this uid, use it. 8667 break; 8668 } 8669 stepsLeft--; 8670 if (stepsLeft <= 0) { 8671 return null; 8672 } 8673 } 8674 } 8675 return new ProcessRecord(stats, info, proc, uid); 8676 } 8677 8678 final ProcessRecord addAppLocked(ApplicationInfo info, boolean isolated, 8679 String abiOverride) { 8680 ProcessRecord app; 8681 if (!isolated) { 8682 app = getProcessRecordLocked(info.processName, info.uid, true); 8683 } else { 8684 app = null; 8685 } 8686 8687 if (app == null) { 8688 app = newProcessRecordLocked(info, null, isolated); 8689 mProcessNames.put(info.processName, app.uid, app); 8690 if (isolated) { 8691 mIsolatedProcesses.put(app.uid, app); 8692 } 8693 updateLruProcessLocked(app, false, null); 8694 updateOomAdjLocked(); 8695 } 8696 8697 // This package really, really can not be stopped. 8698 try { 8699 AppGlobals.getPackageManager().setPackageStoppedState( 8700 info.packageName, false, UserHandle.getUserId(app.uid)); 8701 } catch (RemoteException e) { 8702 } catch (IllegalArgumentException e) { 8703 Slog.w(TAG, "Failed trying to unstop package " 8704 + info.packageName + ": " + e); 8705 } 8706 8707 if ((info.flags&(ApplicationInfo.FLAG_SYSTEM|ApplicationInfo.FLAG_PERSISTENT)) 8708 == (ApplicationInfo.FLAG_SYSTEM|ApplicationInfo.FLAG_PERSISTENT)) { 8709 app.persistent = true; 8710 app.maxAdj = ProcessList.PERSISTENT_PROC_ADJ; 8711 } 8712 if (app.thread == null && mPersistentStartingProcesses.indexOf(app) < 0) { 8713 mPersistentStartingProcesses.add(app); 8714 startProcessLocked(app, "added application", app.processName, 8715 abiOverride); 8716 } 8717 8718 return app; 8719 } 8720 8721 public void unhandledBack() { 8722 enforceCallingPermission(android.Manifest.permission.FORCE_BACK, 8723 "unhandledBack()"); 8724 8725 synchronized(this) { 8726 final long origId = Binder.clearCallingIdentity(); 8727 try { 8728 getFocusedStack().unhandledBackLocked(); 8729 } finally { 8730 Binder.restoreCallingIdentity(origId); 8731 } 8732 } 8733 } 8734 8735 public ParcelFileDescriptor openContentUri(Uri uri) throws RemoteException { 8736 enforceNotIsolatedCaller("openContentUri"); 8737 final int userId = UserHandle.getCallingUserId(); 8738 String name = uri.getAuthority(); 8739 ContentProviderHolder cph = getContentProviderExternalUnchecked(name, null, userId); 8740 ParcelFileDescriptor pfd = null; 8741 if (cph != null) { 8742 // We record the binder invoker's uid in thread-local storage before 8743 // going to the content provider to open the file. Later, in the code 8744 // that handles all permissions checks, we look for this uid and use 8745 // that rather than the Activity Manager's own uid. The effect is that 8746 // we do the check against the caller's permissions even though it looks 8747 // to the content provider like the Activity Manager itself is making 8748 // the request. 8749 sCallerIdentity.set(new Identity( 8750 Binder.getCallingPid(), Binder.getCallingUid())); 8751 try { 8752 pfd = cph.provider.openFile(null, uri, "r", null); 8753 } catch (FileNotFoundException e) { 8754 // do nothing; pfd will be returned null 8755 } finally { 8756 // Ensure that whatever happens, we clean up the identity state 8757 sCallerIdentity.remove(); 8758 } 8759 8760 // We've got the fd now, so we're done with the provider. 8761 removeContentProviderExternalUnchecked(name, null, userId); 8762 } else { 8763 Slog.d(TAG, "Failed to get provider for authority '" + name + "'"); 8764 } 8765 return pfd; 8766 } 8767 8768 // Actually is sleeping or shutting down or whatever else in the future 8769 // is an inactive state. 8770 public boolean isSleepingOrShuttingDown() { 8771 return mSleeping || mShuttingDown; 8772 } 8773 8774 public boolean isSleeping() { 8775 return mSleeping; 8776 } 8777 8778 void goingToSleep() { 8779 synchronized(this) { 8780 mWentToSleep = true; 8781 updateEventDispatchingLocked(); 8782 goToSleepIfNeededLocked(); 8783 } 8784 } 8785 8786 void finishRunningVoiceLocked() { 8787 if (mRunningVoice) { 8788 mRunningVoice = false; 8789 goToSleepIfNeededLocked(); 8790 } 8791 } 8792 8793 void goToSleepIfNeededLocked() { 8794 if (mWentToSleep && !mRunningVoice) { 8795 if (!mSleeping) { 8796 mSleeping = true; 8797 mStackSupervisor.goingToSleepLocked(); 8798 8799 // Initialize the wake times of all processes. 8800 checkExcessivePowerUsageLocked(false); 8801 mHandler.removeMessages(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 8802 Message nmsg = mHandler.obtainMessage(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 8803 mHandler.sendMessageDelayed(nmsg, POWER_CHECK_DELAY); 8804 } 8805 } 8806 } 8807 8808 void notifyTaskPersisterLocked(TaskRecord task, boolean flush) { 8809 mTaskPersister.notify(task, flush); 8810 } 8811 8812 @Override 8813 public boolean shutdown(int timeout) { 8814 if (checkCallingPermission(android.Manifest.permission.SHUTDOWN) 8815 != PackageManager.PERMISSION_GRANTED) { 8816 throw new SecurityException("Requires permission " 8817 + android.Manifest.permission.SHUTDOWN); 8818 } 8819 8820 boolean timedout = false; 8821 8822 synchronized(this) { 8823 mShuttingDown = true; 8824 updateEventDispatchingLocked(); 8825 timedout = mStackSupervisor.shutdownLocked(timeout); 8826 } 8827 8828 mAppOpsService.shutdown(); 8829 mUsageStatsService.shutdown(); 8830 mBatteryStatsService.shutdown(); 8831 synchronized (this) { 8832 mProcessStats.shutdownLocked(); 8833 } 8834 notifyTaskPersisterLocked(null, true); 8835 8836 return timedout; 8837 } 8838 8839 public final void activitySlept(IBinder token) { 8840 if (localLOGV) Slog.v(TAG, "Activity slept: token=" + token); 8841 8842 final long origId = Binder.clearCallingIdentity(); 8843 8844 synchronized (this) { 8845 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 8846 if (r != null) { 8847 mStackSupervisor.activitySleptLocked(r); 8848 } 8849 } 8850 8851 Binder.restoreCallingIdentity(origId); 8852 } 8853 8854 void logLockScreen(String msg) { 8855 if (DEBUG_LOCKSCREEN) Slog.d(TAG, Debug.getCallers(2) + ":" + msg + 8856 " mLockScreenShown=" + mLockScreenShown + " mWentToSleep=" + 8857 mWentToSleep + " mSleeping=" + mSleeping + " mDismissKeyguardOnNextActivity=" + 8858 mStackSupervisor.mDismissKeyguardOnNextActivity); 8859 } 8860 8861 private void comeOutOfSleepIfNeededLocked() { 8862 if ((!mWentToSleep && !mLockScreenShown) || mRunningVoice) { 8863 if (mSleeping) { 8864 mSleeping = false; 8865 mStackSupervisor.comeOutOfSleepIfNeededLocked(); 8866 } 8867 } 8868 } 8869 8870 void wakingUp() { 8871 synchronized(this) { 8872 mWentToSleep = false; 8873 updateEventDispatchingLocked(); 8874 comeOutOfSleepIfNeededLocked(); 8875 } 8876 } 8877 8878 void startRunningVoiceLocked() { 8879 if (!mRunningVoice) { 8880 mRunningVoice = true; 8881 comeOutOfSleepIfNeededLocked(); 8882 } 8883 } 8884 8885 private void updateEventDispatchingLocked() { 8886 mWindowManager.setEventDispatching(mBooted && !mWentToSleep && !mShuttingDown); 8887 } 8888 8889 public void setLockScreenShown(boolean shown) { 8890 if (checkCallingPermission(android.Manifest.permission.DEVICE_POWER) 8891 != PackageManager.PERMISSION_GRANTED) { 8892 throw new SecurityException("Requires permission " 8893 + android.Manifest.permission.DEVICE_POWER); 8894 } 8895 8896 synchronized(this) { 8897 long ident = Binder.clearCallingIdentity(); 8898 try { 8899 if (DEBUG_LOCKSCREEN) logLockScreen(" shown=" + shown); 8900 mLockScreenShown = shown; 8901 comeOutOfSleepIfNeededLocked(); 8902 } finally { 8903 Binder.restoreCallingIdentity(ident); 8904 } 8905 } 8906 } 8907 8908 public void stopAppSwitches() { 8909 if (checkCallingPermission(android.Manifest.permission.STOP_APP_SWITCHES) 8910 != PackageManager.PERMISSION_GRANTED) { 8911 throw new SecurityException("Requires permission " 8912 + android.Manifest.permission.STOP_APP_SWITCHES); 8913 } 8914 8915 synchronized(this) { 8916 mAppSwitchesAllowedTime = SystemClock.uptimeMillis() 8917 + APP_SWITCH_DELAY_TIME; 8918 mDidAppSwitch = false; 8919 mHandler.removeMessages(DO_PENDING_ACTIVITY_LAUNCHES_MSG); 8920 Message msg = mHandler.obtainMessage(DO_PENDING_ACTIVITY_LAUNCHES_MSG); 8921 mHandler.sendMessageDelayed(msg, APP_SWITCH_DELAY_TIME); 8922 } 8923 } 8924 8925 public void resumeAppSwitches() { 8926 if (checkCallingPermission(android.Manifest.permission.STOP_APP_SWITCHES) 8927 != PackageManager.PERMISSION_GRANTED) { 8928 throw new SecurityException("Requires permission " 8929 + android.Manifest.permission.STOP_APP_SWITCHES); 8930 } 8931 8932 synchronized(this) { 8933 // Note that we don't execute any pending app switches... we will 8934 // let those wait until either the timeout, or the next start 8935 // activity request. 8936 mAppSwitchesAllowedTime = 0; 8937 } 8938 } 8939 8940 boolean checkAppSwitchAllowedLocked(int callingPid, int callingUid, 8941 String name) { 8942 if (mAppSwitchesAllowedTime < SystemClock.uptimeMillis()) { 8943 return true; 8944 } 8945 8946 final int perm = checkComponentPermission( 8947 android.Manifest.permission.STOP_APP_SWITCHES, callingPid, 8948 callingUid, -1, true); 8949 if (perm == PackageManager.PERMISSION_GRANTED) { 8950 return true; 8951 } 8952 8953 Slog.w(TAG, name + " request from " + callingUid + " stopped"); 8954 return false; 8955 } 8956 8957 public void setDebugApp(String packageName, boolean waitForDebugger, 8958 boolean persistent) { 8959 enforceCallingPermission(android.Manifest.permission.SET_DEBUG_APP, 8960 "setDebugApp()"); 8961 8962 long ident = Binder.clearCallingIdentity(); 8963 try { 8964 // Note that this is not really thread safe if there are multiple 8965 // callers into it at the same time, but that's not a situation we 8966 // care about. 8967 if (persistent) { 8968 final ContentResolver resolver = mContext.getContentResolver(); 8969 Settings.Global.putString( 8970 resolver, Settings.Global.DEBUG_APP, 8971 packageName); 8972 Settings.Global.putInt( 8973 resolver, Settings.Global.WAIT_FOR_DEBUGGER, 8974 waitForDebugger ? 1 : 0); 8975 } 8976 8977 synchronized (this) { 8978 if (!persistent) { 8979 mOrigDebugApp = mDebugApp; 8980 mOrigWaitForDebugger = mWaitForDebugger; 8981 } 8982 mDebugApp = packageName; 8983 mWaitForDebugger = waitForDebugger; 8984 mDebugTransient = !persistent; 8985 if (packageName != null) { 8986 forceStopPackageLocked(packageName, -1, false, false, true, true, 8987 false, UserHandle.USER_ALL, "set debug app"); 8988 } 8989 } 8990 } finally { 8991 Binder.restoreCallingIdentity(ident); 8992 } 8993 } 8994 8995 void setOpenGlTraceApp(ApplicationInfo app, String processName) { 8996 synchronized (this) { 8997 boolean isDebuggable = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 8998 if (!isDebuggable) { 8999 if ((app.flags&ApplicationInfo.FLAG_DEBUGGABLE) == 0) { 9000 throw new SecurityException("Process not debuggable: " + app.packageName); 9001 } 9002 } 9003 9004 mOpenGlTraceApp = processName; 9005 } 9006 } 9007 9008 void setProfileApp(ApplicationInfo app, String processName, String profileFile, 9009 ParcelFileDescriptor profileFd, boolean autoStopProfiler) { 9010 synchronized (this) { 9011 boolean isDebuggable = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 9012 if (!isDebuggable) { 9013 if ((app.flags&ApplicationInfo.FLAG_DEBUGGABLE) == 0) { 9014 throw new SecurityException("Process not debuggable: " + app.packageName); 9015 } 9016 } 9017 mProfileApp = processName; 9018 mProfileFile = profileFile; 9019 if (mProfileFd != null) { 9020 try { 9021 mProfileFd.close(); 9022 } catch (IOException e) { 9023 } 9024 mProfileFd = null; 9025 } 9026 mProfileFd = profileFd; 9027 mProfileType = 0; 9028 mAutoStopProfiler = autoStopProfiler; 9029 } 9030 } 9031 9032 @Override 9033 public void setAlwaysFinish(boolean enabled) { 9034 enforceCallingPermission(android.Manifest.permission.SET_ALWAYS_FINISH, 9035 "setAlwaysFinish()"); 9036 9037 Settings.Global.putInt( 9038 mContext.getContentResolver(), 9039 Settings.Global.ALWAYS_FINISH_ACTIVITIES, enabled ? 1 : 0); 9040 9041 synchronized (this) { 9042 mAlwaysFinishActivities = enabled; 9043 } 9044 } 9045 9046 @Override 9047 public void setActivityController(IActivityController controller) { 9048 enforceCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER, 9049 "setActivityController()"); 9050 synchronized (this) { 9051 mController = controller; 9052 Watchdog.getInstance().setActivityController(controller); 9053 } 9054 } 9055 9056 @Override 9057 public void setUserIsMonkey(boolean userIsMonkey) { 9058 synchronized (this) { 9059 synchronized (mPidsSelfLocked) { 9060 final int callingPid = Binder.getCallingPid(); 9061 ProcessRecord precessRecord = mPidsSelfLocked.get(callingPid); 9062 if (precessRecord == null) { 9063 throw new SecurityException("Unknown process: " + callingPid); 9064 } 9065 if (precessRecord.instrumentationUiAutomationConnection == null) { 9066 throw new SecurityException("Only an instrumentation process " 9067 + "with a UiAutomation can call setUserIsMonkey"); 9068 } 9069 } 9070 mUserIsMonkey = userIsMonkey; 9071 } 9072 } 9073 9074 @Override 9075 public boolean isUserAMonkey() { 9076 synchronized (this) { 9077 // If there is a controller also implies the user is a monkey. 9078 return (mUserIsMonkey || mController != null); 9079 } 9080 } 9081 9082 public void requestBugReport() { 9083 enforceCallingPermission(android.Manifest.permission.DUMP, "requestBugReport"); 9084 SystemProperties.set("ctl.start", "bugreport"); 9085 } 9086 9087 public static long getInputDispatchingTimeoutLocked(ActivityRecord r) { 9088 return r != null ? getInputDispatchingTimeoutLocked(r.app) : KEY_DISPATCHING_TIMEOUT; 9089 } 9090 9091 public static long getInputDispatchingTimeoutLocked(ProcessRecord r) { 9092 if (r != null && (r.instrumentationClass != null || r.usingWrapper)) { 9093 return INSTRUMENTATION_KEY_DISPATCHING_TIMEOUT; 9094 } 9095 return KEY_DISPATCHING_TIMEOUT; 9096 } 9097 9098 @Override 9099 public long inputDispatchingTimedOut(int pid, final boolean aboveSystem, String reason) { 9100 if (checkCallingPermission(android.Manifest.permission.FILTER_EVENTS) 9101 != PackageManager.PERMISSION_GRANTED) { 9102 throw new SecurityException("Requires permission " 9103 + android.Manifest.permission.FILTER_EVENTS); 9104 } 9105 ProcessRecord proc; 9106 long timeout; 9107 synchronized (this) { 9108 synchronized (mPidsSelfLocked) { 9109 proc = mPidsSelfLocked.get(pid); 9110 } 9111 timeout = getInputDispatchingTimeoutLocked(proc); 9112 } 9113 9114 if (!inputDispatchingTimedOut(proc, null, null, aboveSystem, reason)) { 9115 return -1; 9116 } 9117 9118 return timeout; 9119 } 9120 9121 /** 9122 * Handle input dispatching timeouts. 9123 * Returns whether input dispatching should be aborted or not. 9124 */ 9125 public boolean inputDispatchingTimedOut(final ProcessRecord proc, 9126 final ActivityRecord activity, final ActivityRecord parent, 9127 final boolean aboveSystem, String reason) { 9128 if (checkCallingPermission(android.Manifest.permission.FILTER_EVENTS) 9129 != PackageManager.PERMISSION_GRANTED) { 9130 throw new SecurityException("Requires permission " 9131 + android.Manifest.permission.FILTER_EVENTS); 9132 } 9133 9134 final String annotation; 9135 if (reason == null) { 9136 annotation = "Input dispatching timed out"; 9137 } else { 9138 annotation = "Input dispatching timed out (" + reason + ")"; 9139 } 9140 9141 if (proc != null) { 9142 synchronized (this) { 9143 if (proc.debugging) { 9144 return false; 9145 } 9146 9147 if (mDidDexOpt) { 9148 // Give more time since we were dexopting. 9149 mDidDexOpt = false; 9150 return false; 9151 } 9152 9153 if (proc.instrumentationClass != null) { 9154 Bundle info = new Bundle(); 9155 info.putString("shortMsg", "keyDispatchingTimedOut"); 9156 info.putString("longMsg", annotation); 9157 finishInstrumentationLocked(proc, Activity.RESULT_CANCELED, info); 9158 return true; 9159 } 9160 } 9161 mHandler.post(new Runnable() { 9162 @Override 9163 public void run() { 9164 appNotResponding(proc, activity, parent, aboveSystem, annotation); 9165 } 9166 }); 9167 } 9168 9169 return true; 9170 } 9171 9172 public Bundle getAssistContextExtras(int requestType) { 9173 enforceCallingPermission(android.Manifest.permission.GET_TOP_ACTIVITY_INFO, 9174 "getAssistContextExtras()"); 9175 PendingAssistExtras pae; 9176 Bundle extras = new Bundle(); 9177 synchronized (this) { 9178 ActivityRecord activity = getFocusedStack().mResumedActivity; 9179 if (activity == null) { 9180 Slog.w(TAG, "getAssistContextExtras failed: no resumed activity"); 9181 return null; 9182 } 9183 extras.putString(Intent.EXTRA_ASSIST_PACKAGE, activity.packageName); 9184 if (activity.app == null || activity.app.thread == null) { 9185 Slog.w(TAG, "getAssistContextExtras failed: no process for " + activity); 9186 return extras; 9187 } 9188 if (activity.app.pid == Binder.getCallingPid()) { 9189 Slog.w(TAG, "getAssistContextExtras failed: request process same as " + activity); 9190 return extras; 9191 } 9192 pae = new PendingAssistExtras(activity); 9193 try { 9194 activity.app.thread.requestAssistContextExtras(activity.appToken, pae, 9195 requestType); 9196 mPendingAssistExtras.add(pae); 9197 mHandler.postDelayed(pae, PENDING_ASSIST_EXTRAS_TIMEOUT); 9198 } catch (RemoteException e) { 9199 Slog.w(TAG, "getAssistContextExtras failed: crash calling " + activity); 9200 return extras; 9201 } 9202 } 9203 synchronized (pae) { 9204 while (!pae.haveResult) { 9205 try { 9206 pae.wait(); 9207 } catch (InterruptedException e) { 9208 } 9209 } 9210 if (pae.result != null) { 9211 extras.putBundle(Intent.EXTRA_ASSIST_CONTEXT, pae.result); 9212 } 9213 } 9214 synchronized (this) { 9215 mPendingAssistExtras.remove(pae); 9216 mHandler.removeCallbacks(pae); 9217 } 9218 return extras; 9219 } 9220 9221 public void reportAssistContextExtras(IBinder token, Bundle extras) { 9222 PendingAssistExtras pae = (PendingAssistExtras)token; 9223 synchronized (pae) { 9224 pae.result = extras; 9225 pae.haveResult = true; 9226 pae.notifyAll(); 9227 } 9228 } 9229 9230 public void registerProcessObserver(IProcessObserver observer) { 9231 enforceCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER, 9232 "registerProcessObserver()"); 9233 synchronized (this) { 9234 mProcessObservers.register(observer); 9235 } 9236 } 9237 9238 @Override 9239 public void unregisterProcessObserver(IProcessObserver observer) { 9240 synchronized (this) { 9241 mProcessObservers.unregister(observer); 9242 } 9243 } 9244 9245 @Override 9246 public boolean convertFromTranslucent(IBinder token) { 9247 final long origId = Binder.clearCallingIdentity(); 9248 try { 9249 synchronized (this) { 9250 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 9251 if (r == null) { 9252 return false; 9253 } 9254 if (r.changeWindowTranslucency(true)) { 9255 mWindowManager.setAppFullscreen(token, true); 9256 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0); 9257 return true; 9258 } 9259 return false; 9260 } 9261 } finally { 9262 Binder.restoreCallingIdentity(origId); 9263 } 9264 } 9265 9266 @Override 9267 public boolean convertToTranslucent(IBinder token, ActivityOptions options) { 9268 final long origId = Binder.clearCallingIdentity(); 9269 try { 9270 synchronized (this) { 9271 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 9272 if (r == null) { 9273 return false; 9274 } 9275 if (r.changeWindowTranslucency(false)) { 9276 r.task.stack.convertToTranslucent(r, options); 9277 mWindowManager.setAppFullscreen(token, false); 9278 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0); 9279 return true; 9280 } 9281 return false; 9282 } 9283 } finally { 9284 Binder.restoreCallingIdentity(origId); 9285 } 9286 } 9287 9288 @Override 9289 public ActivityOptions getActivityOptions(IBinder token) { 9290 final long origId = Binder.clearCallingIdentity(); 9291 try { 9292 synchronized (this) { 9293 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 9294 if (r != null) { 9295 final ActivityOptions activityOptions = r.pendingOptions; 9296 r.pendingOptions = null; 9297 return activityOptions; 9298 } 9299 return null; 9300 } 9301 } finally { 9302 Binder.restoreCallingIdentity(origId); 9303 } 9304 } 9305 9306 @Override 9307 public void setImmersive(IBinder token, boolean immersive) { 9308 synchronized(this) { 9309 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 9310 if (r == null) { 9311 throw new IllegalArgumentException(); 9312 } 9313 r.immersive = immersive; 9314 9315 // update associated state if we're frontmost 9316 if (r == mFocusedActivity) { 9317 if (DEBUG_IMMERSIVE) { 9318 Slog.d(TAG, "Frontmost changed immersion: "+ r); 9319 } 9320 applyUpdateLockStateLocked(r); 9321 } 9322 } 9323 } 9324 9325 @Override 9326 public boolean isImmersive(IBinder token) { 9327 synchronized (this) { 9328 ActivityRecord r = ActivityRecord.isInStackLocked(token); 9329 if (r == null) { 9330 throw new IllegalArgumentException(); 9331 } 9332 return r.immersive; 9333 } 9334 } 9335 9336 public boolean isTopActivityImmersive() { 9337 enforceNotIsolatedCaller("startActivity"); 9338 synchronized (this) { 9339 ActivityRecord r = getFocusedStack().topRunningActivityLocked(null); 9340 return (r != null) ? r.immersive : false; 9341 } 9342 } 9343 9344 public final void enterSafeMode() { 9345 synchronized(this) { 9346 // It only makes sense to do this before the system is ready 9347 // and started launching other packages. 9348 if (!mSystemReady) { 9349 try { 9350 AppGlobals.getPackageManager().enterSafeMode(); 9351 } catch (RemoteException e) { 9352 } 9353 } 9354 9355 mSafeMode = true; 9356 } 9357 } 9358 9359 public final void showSafeModeOverlay() { 9360 View v = LayoutInflater.from(mContext).inflate( 9361 com.android.internal.R.layout.safe_mode, null); 9362 WindowManager.LayoutParams lp = new WindowManager.LayoutParams(); 9363 lp.type = WindowManager.LayoutParams.TYPE_SECURE_SYSTEM_OVERLAY; 9364 lp.width = WindowManager.LayoutParams.WRAP_CONTENT; 9365 lp.height = WindowManager.LayoutParams.WRAP_CONTENT; 9366 lp.gravity = Gravity.BOTTOM | Gravity.START; 9367 lp.format = v.getBackground().getOpacity(); 9368 lp.flags = WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE 9369 | WindowManager.LayoutParams.FLAG_NOT_TOUCHABLE; 9370 lp.privateFlags |= WindowManager.LayoutParams.PRIVATE_FLAG_SHOW_FOR_ALL_USERS; 9371 ((WindowManager)mContext.getSystemService( 9372 Context.WINDOW_SERVICE)).addView(v, lp); 9373 } 9374 9375 public void noteWakeupAlarm(IIntentSender sender, int sourceUid, String sourcePkg) { 9376 if (!(sender instanceof PendingIntentRecord)) { 9377 return; 9378 } 9379 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 9380 synchronized (stats) { 9381 if (mBatteryStatsService.isOnBattery()) { 9382 mBatteryStatsService.enforceCallingPermission(); 9383 PendingIntentRecord rec = (PendingIntentRecord)sender; 9384 int MY_UID = Binder.getCallingUid(); 9385 int uid = rec.uid == MY_UID ? Process.SYSTEM_UID : rec.uid; 9386 BatteryStatsImpl.Uid.Pkg pkg = 9387 stats.getPackageStatsLocked(sourceUid >= 0 ? sourceUid : uid, 9388 sourcePkg != null ? sourcePkg : rec.key.packageName); 9389 pkg.incWakeupsLocked(); 9390 } 9391 } 9392 } 9393 9394 public boolean killPids(int[] pids, String pReason, boolean secure) { 9395 if (Binder.getCallingUid() != Process.SYSTEM_UID) { 9396 throw new SecurityException("killPids only available to the system"); 9397 } 9398 String reason = (pReason == null) ? "Unknown" : pReason; 9399 // XXX Note: don't acquire main activity lock here, because the window 9400 // manager calls in with its locks held. 9401 9402 boolean killed = false; 9403 synchronized (mPidsSelfLocked) { 9404 int[] types = new int[pids.length]; 9405 int worstType = 0; 9406 for (int i=0; i<pids.length; i++) { 9407 ProcessRecord proc = mPidsSelfLocked.get(pids[i]); 9408 if (proc != null) { 9409 int type = proc.setAdj; 9410 types[i] = type; 9411 if (type > worstType) { 9412 worstType = type; 9413 } 9414 } 9415 } 9416 9417 // If the worst oom_adj is somewhere in the cached proc LRU range, 9418 // then constrain it so we will kill all cached procs. 9419 if (worstType < ProcessList.CACHED_APP_MAX_ADJ 9420 && worstType > ProcessList.CACHED_APP_MIN_ADJ) { 9421 worstType = ProcessList.CACHED_APP_MIN_ADJ; 9422 } 9423 9424 // If this is not a secure call, don't let it kill processes that 9425 // are important. 9426 if (!secure && worstType < ProcessList.SERVICE_ADJ) { 9427 worstType = ProcessList.SERVICE_ADJ; 9428 } 9429 9430 Slog.w(TAG, "Killing processes " + reason + " at adjustment " + worstType); 9431 for (int i=0; i<pids.length; i++) { 9432 ProcessRecord proc = mPidsSelfLocked.get(pids[i]); 9433 if (proc == null) { 9434 continue; 9435 } 9436 int adj = proc.setAdj; 9437 if (adj >= worstType && !proc.killedByAm) { 9438 killUnneededProcessLocked(proc, reason); 9439 killed = true; 9440 } 9441 } 9442 } 9443 return killed; 9444 } 9445 9446 @Override 9447 public void killUid(int uid, String reason) { 9448 if (Binder.getCallingUid() != Process.SYSTEM_UID) { 9449 throw new SecurityException("killUid only available to the system"); 9450 } 9451 synchronized (this) { 9452 killPackageProcessesLocked(null, UserHandle.getAppId(uid), UserHandle.getUserId(uid), 9453 ProcessList.FOREGROUND_APP_ADJ-1, false, true, true, false, 9454 reason != null ? reason : "kill uid"); 9455 } 9456 } 9457 9458 @Override 9459 public boolean killProcessesBelowForeground(String reason) { 9460 if (Binder.getCallingUid() != Process.SYSTEM_UID) { 9461 throw new SecurityException("killProcessesBelowForeground() only available to system"); 9462 } 9463 9464 return killProcessesBelowAdj(ProcessList.FOREGROUND_APP_ADJ, reason); 9465 } 9466 9467 private boolean killProcessesBelowAdj(int belowAdj, String reason) { 9468 if (Binder.getCallingUid() != Process.SYSTEM_UID) { 9469 throw new SecurityException("killProcessesBelowAdj() only available to system"); 9470 } 9471 9472 boolean killed = false; 9473 synchronized (mPidsSelfLocked) { 9474 final int size = mPidsSelfLocked.size(); 9475 for (int i = 0; i < size; i++) { 9476 final int pid = mPidsSelfLocked.keyAt(i); 9477 final ProcessRecord proc = mPidsSelfLocked.valueAt(i); 9478 if (proc == null) continue; 9479 9480 final int adj = proc.setAdj; 9481 if (adj > belowAdj && !proc.killedByAm) { 9482 killUnneededProcessLocked(proc, reason); 9483 killed = true; 9484 } 9485 } 9486 } 9487 return killed; 9488 } 9489 9490 @Override 9491 public void hang(final IBinder who, boolean allowRestart) { 9492 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 9493 != PackageManager.PERMISSION_GRANTED) { 9494 throw new SecurityException("Requires permission " 9495 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 9496 } 9497 9498 final IBinder.DeathRecipient death = new DeathRecipient() { 9499 @Override 9500 public void binderDied() { 9501 synchronized (this) { 9502 notifyAll(); 9503 } 9504 } 9505 }; 9506 9507 try { 9508 who.linkToDeath(death, 0); 9509 } catch (RemoteException e) { 9510 Slog.w(TAG, "hang: given caller IBinder is already dead."); 9511 return; 9512 } 9513 9514 synchronized (this) { 9515 Watchdog.getInstance().setAllowRestart(allowRestart); 9516 Slog.i(TAG, "Hanging system process at request of pid " + Binder.getCallingPid()); 9517 synchronized (death) { 9518 while (who.isBinderAlive()) { 9519 try { 9520 death.wait(); 9521 } catch (InterruptedException e) { 9522 } 9523 } 9524 } 9525 Watchdog.getInstance().setAllowRestart(true); 9526 } 9527 } 9528 9529 @Override 9530 public void restart() { 9531 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 9532 != PackageManager.PERMISSION_GRANTED) { 9533 throw new SecurityException("Requires permission " 9534 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 9535 } 9536 9537 Log.i(TAG, "Sending shutdown broadcast..."); 9538 9539 BroadcastReceiver br = new BroadcastReceiver() { 9540 @Override public void onReceive(Context context, Intent intent) { 9541 // Now the broadcast is done, finish up the low-level shutdown. 9542 Log.i(TAG, "Shutting down activity manager..."); 9543 shutdown(10000); 9544 Log.i(TAG, "Shutdown complete, restarting!"); 9545 Process.killProcess(Process.myPid()); 9546 System.exit(10); 9547 } 9548 }; 9549 9550 // First send the high-level shut down broadcast. 9551 Intent intent = new Intent(Intent.ACTION_SHUTDOWN); 9552 intent.addFlags(Intent.FLAG_RECEIVER_FOREGROUND); 9553 intent.putExtra(Intent.EXTRA_SHUTDOWN_USERSPACE_ONLY, true); 9554 /* For now we are not doing a clean shutdown, because things seem to get unhappy. 9555 mContext.sendOrderedBroadcastAsUser(intent, 9556 UserHandle.ALL, null, br, mHandler, 0, null, null); 9557 */ 9558 br.onReceive(mContext, intent); 9559 } 9560 9561 private long getLowRamTimeSinceIdle(long now) { 9562 return mLowRamTimeSinceLastIdle + (mLowRamStartTime > 0 ? (now-mLowRamStartTime) : 0); 9563 } 9564 9565 @Override 9566 public void performIdleMaintenance() { 9567 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 9568 != PackageManager.PERMISSION_GRANTED) { 9569 throw new SecurityException("Requires permission " 9570 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 9571 } 9572 9573 synchronized (this) { 9574 final long now = SystemClock.uptimeMillis(); 9575 final long timeSinceLastIdle = now - mLastIdleTime; 9576 final long lowRamSinceLastIdle = getLowRamTimeSinceIdle(now); 9577 mLastIdleTime = now; 9578 mLowRamTimeSinceLastIdle = 0; 9579 if (mLowRamStartTime != 0) { 9580 mLowRamStartTime = now; 9581 } 9582 9583 StringBuilder sb = new StringBuilder(128); 9584 sb.append("Idle maintenance over "); 9585 TimeUtils.formatDuration(timeSinceLastIdle, sb); 9586 sb.append(" low RAM for "); 9587 TimeUtils.formatDuration(lowRamSinceLastIdle, sb); 9588 Slog.i(TAG, sb.toString()); 9589 9590 // If at least 1/3 of our time since the last idle period has been spent 9591 // with RAM low, then we want to kill processes. 9592 boolean doKilling = lowRamSinceLastIdle > (timeSinceLastIdle/3); 9593 9594 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 9595 ProcessRecord proc = mLruProcesses.get(i); 9596 if (proc.notCachedSinceIdle) { 9597 if (proc.setProcState > ActivityManager.PROCESS_STATE_TOP 9598 && proc.setProcState <= ActivityManager.PROCESS_STATE_SERVICE) { 9599 if (doKilling && proc.initialIdlePss != 0 9600 && proc.lastPss > ((proc.initialIdlePss*3)/2)) { 9601 killUnneededProcessLocked(proc, "idle maint (pss " + proc.lastPss 9602 + " from " + proc.initialIdlePss + ")"); 9603 } 9604 } 9605 } else if (proc.setProcState < ActivityManager.PROCESS_STATE_HOME) { 9606 proc.notCachedSinceIdle = true; 9607 proc.initialIdlePss = 0; 9608 proc.nextPssTime = ProcessList.computeNextPssTime(proc.curProcState, true, 9609 isSleeping(), now); 9610 } 9611 } 9612 9613 mHandler.removeMessages(REQUEST_ALL_PSS_MSG); 9614 mHandler.sendEmptyMessageDelayed(REQUEST_ALL_PSS_MSG, 2*60*1000); 9615 } 9616 } 9617 9618 private void retrieveSettings() { 9619 final ContentResolver resolver = mContext.getContentResolver(); 9620 String debugApp = Settings.Global.getString( 9621 resolver, Settings.Global.DEBUG_APP); 9622 boolean waitForDebugger = Settings.Global.getInt( 9623 resolver, Settings.Global.WAIT_FOR_DEBUGGER, 0) != 0; 9624 boolean alwaysFinishActivities = Settings.Global.getInt( 9625 resolver, Settings.Global.ALWAYS_FINISH_ACTIVITIES, 0) != 0; 9626 boolean forceRtl = Settings.Global.getInt( 9627 resolver, Settings.Global.DEVELOPMENT_FORCE_RTL, 0) != 0; 9628 // Transfer any global setting for forcing RTL layout, into a System Property 9629 SystemProperties.set(Settings.Global.DEVELOPMENT_FORCE_RTL, forceRtl ? "1":"0"); 9630 9631 Configuration configuration = new Configuration(); 9632 Settings.System.getConfiguration(resolver, configuration); 9633 if (forceRtl) { 9634 // This will take care of setting the correct layout direction flags 9635 configuration.setLayoutDirection(configuration.locale); 9636 } 9637 9638 synchronized (this) { 9639 mDebugApp = mOrigDebugApp = debugApp; 9640 mWaitForDebugger = mOrigWaitForDebugger = waitForDebugger; 9641 mAlwaysFinishActivities = alwaysFinishActivities; 9642 // This happens before any activities are started, so we can 9643 // change mConfiguration in-place. 9644 updateConfigurationLocked(configuration, null, false, true); 9645 if (DEBUG_CONFIGURATION) Slog.v(TAG, "Initial config: " + mConfiguration); 9646 } 9647 } 9648 9649 public boolean testIsSystemReady() { 9650 // no need to synchronize(this) just to read & return the value 9651 return mSystemReady; 9652 } 9653 9654 private static File getCalledPreBootReceiversFile() { 9655 File dataDir = Environment.getDataDirectory(); 9656 File systemDir = new File(dataDir, "system"); 9657 File fname = new File(systemDir, "called_pre_boots.dat"); 9658 return fname; 9659 } 9660 9661 static final int LAST_DONE_VERSION = 10000; 9662 9663 private static ArrayList<ComponentName> readLastDonePreBootReceivers() { 9664 ArrayList<ComponentName> lastDoneReceivers = new ArrayList<ComponentName>(); 9665 File file = getCalledPreBootReceiversFile(); 9666 FileInputStream fis = null; 9667 try { 9668 fis = new FileInputStream(file); 9669 DataInputStream dis = new DataInputStream(new BufferedInputStream(fis, 2048)); 9670 int fvers = dis.readInt(); 9671 if (fvers == LAST_DONE_VERSION) { 9672 String vers = dis.readUTF(); 9673 String codename = dis.readUTF(); 9674 String build = dis.readUTF(); 9675 if (android.os.Build.VERSION.RELEASE.equals(vers) 9676 && android.os.Build.VERSION.CODENAME.equals(codename) 9677 && android.os.Build.VERSION.INCREMENTAL.equals(build)) { 9678 int num = dis.readInt(); 9679 while (num > 0) { 9680 num--; 9681 String pkg = dis.readUTF(); 9682 String cls = dis.readUTF(); 9683 lastDoneReceivers.add(new ComponentName(pkg, cls)); 9684 } 9685 } 9686 } 9687 } catch (FileNotFoundException e) { 9688 } catch (IOException e) { 9689 Slog.w(TAG, "Failure reading last done pre-boot receivers", e); 9690 } finally { 9691 if (fis != null) { 9692 try { 9693 fis.close(); 9694 } catch (IOException e) { 9695 } 9696 } 9697 } 9698 return lastDoneReceivers; 9699 } 9700 9701 private static void writeLastDonePreBootReceivers(ArrayList<ComponentName> list) { 9702 File file = getCalledPreBootReceiversFile(); 9703 FileOutputStream fos = null; 9704 DataOutputStream dos = null; 9705 try { 9706 Slog.i(TAG, "Writing new set of last done pre-boot receivers..."); 9707 fos = new FileOutputStream(file); 9708 dos = new DataOutputStream(new BufferedOutputStream(fos, 2048)); 9709 dos.writeInt(LAST_DONE_VERSION); 9710 dos.writeUTF(android.os.Build.VERSION.RELEASE); 9711 dos.writeUTF(android.os.Build.VERSION.CODENAME); 9712 dos.writeUTF(android.os.Build.VERSION.INCREMENTAL); 9713 dos.writeInt(list.size()); 9714 for (int i=0; i<list.size(); i++) { 9715 dos.writeUTF(list.get(i).getPackageName()); 9716 dos.writeUTF(list.get(i).getClassName()); 9717 } 9718 } catch (IOException e) { 9719 Slog.w(TAG, "Failure writing last done pre-boot receivers", e); 9720 file.delete(); 9721 } finally { 9722 FileUtils.sync(fos); 9723 if (dos != null) { 9724 try { 9725 dos.close(); 9726 } catch (IOException e) { 9727 // TODO Auto-generated catch block 9728 e.printStackTrace(); 9729 } 9730 } 9731 } 9732 } 9733 9734 public void systemReady(final Runnable goingCallback) { 9735 synchronized(this) { 9736 if (mSystemReady) { 9737 if (goingCallback != null) goingCallback.run(); 9738 return; 9739 } 9740 9741 if (mRecentTasks == null) { 9742 mRecentTasks = mTaskPersister.restoreTasksLocked(); 9743 if (!mRecentTasks.isEmpty()) { 9744 mStackSupervisor.createStackForRestoredTaskHistory(mRecentTasks); 9745 } 9746 mTaskPersister.startPersisting(); 9747 } 9748 9749 // Check to see if there are any update receivers to run. 9750 if (!mDidUpdate) { 9751 if (mWaitingUpdate) { 9752 return; 9753 } 9754 Intent intent = new Intent(Intent.ACTION_PRE_BOOT_COMPLETED); 9755 List<ResolveInfo> ris = null; 9756 try { 9757 ris = AppGlobals.getPackageManager().queryIntentReceivers( 9758 intent, null, 0, 0); 9759 } catch (RemoteException e) { 9760 } 9761 if (ris != null) { 9762 for (int i=ris.size()-1; i>=0; i--) { 9763 if ((ris.get(i).activityInfo.applicationInfo.flags 9764 &ApplicationInfo.FLAG_SYSTEM) == 0) { 9765 ris.remove(i); 9766 } 9767 } 9768 intent.addFlags(Intent.FLAG_RECEIVER_BOOT_UPGRADE); 9769 9770 ArrayList<ComponentName> lastDoneReceivers = readLastDonePreBootReceivers(); 9771 9772 final ArrayList<ComponentName> doneReceivers = new ArrayList<ComponentName>(); 9773 for (int i=0; i<ris.size(); i++) { 9774 ActivityInfo ai = ris.get(i).activityInfo; 9775 ComponentName comp = new ComponentName(ai.packageName, ai.name); 9776 if (lastDoneReceivers.contains(comp)) { 9777 // We already did the pre boot receiver for this app with the current 9778 // platform version, so don't do it again... 9779 ris.remove(i); 9780 i--; 9781 // ...however, do keep it as one that has been done, so we don't 9782 // forget about it when rewriting the file of last done receivers. 9783 doneReceivers.add(comp); 9784 } 9785 } 9786 9787 final int[] users = getUsersLocked(); 9788 for (int i=0; i<ris.size(); i++) { 9789 ActivityInfo ai = ris.get(i).activityInfo; 9790 ComponentName comp = new ComponentName(ai.packageName, ai.name); 9791 doneReceivers.add(comp); 9792 intent.setComponent(comp); 9793 for (int j=0; j<users.length; j++) { 9794 IIntentReceiver finisher = null; 9795 if (i == ris.size()-1 && j == users.length-1) { 9796 finisher = new IIntentReceiver.Stub() { 9797 public void performReceive(Intent intent, int resultCode, 9798 String data, Bundle extras, boolean ordered, 9799 boolean sticky, int sendingUser) { 9800 // The raw IIntentReceiver interface is called 9801 // with the AM lock held, so redispatch to 9802 // execute our code without the lock. 9803 mHandler.post(new Runnable() { 9804 public void run() { 9805 synchronized (ActivityManagerService.this) { 9806 mDidUpdate = true; 9807 } 9808 writeLastDonePreBootReceivers(doneReceivers); 9809 showBootMessage(mContext.getText( 9810 R.string.android_upgrading_complete), 9811 false); 9812 systemReady(goingCallback); 9813 } 9814 }); 9815 } 9816 }; 9817 } 9818 Slog.i(TAG, "Sending system update to " + intent.getComponent() 9819 + " for user " + users[j]); 9820 broadcastIntentLocked(null, null, intent, null, finisher, 9821 0, null, null, null, AppOpsManager.OP_NONE, 9822 true, false, MY_PID, Process.SYSTEM_UID, 9823 users[j]); 9824 if (finisher != null) { 9825 mWaitingUpdate = true; 9826 } 9827 } 9828 } 9829 } 9830 if (mWaitingUpdate) { 9831 return; 9832 } 9833 mDidUpdate = true; 9834 } 9835 9836 mAppOpsService.systemReady(); 9837 mUsageStatsService.systemReady(); 9838 mSystemReady = true; 9839 } 9840 9841 ArrayList<ProcessRecord> procsToKill = null; 9842 synchronized(mPidsSelfLocked) { 9843 for (int i=mPidsSelfLocked.size()-1; i>=0; i--) { 9844 ProcessRecord proc = mPidsSelfLocked.valueAt(i); 9845 if (!isAllowedWhileBooting(proc.info)){ 9846 if (procsToKill == null) { 9847 procsToKill = new ArrayList<ProcessRecord>(); 9848 } 9849 procsToKill.add(proc); 9850 } 9851 } 9852 } 9853 9854 synchronized(this) { 9855 if (procsToKill != null) { 9856 for (int i=procsToKill.size()-1; i>=0; i--) { 9857 ProcessRecord proc = procsToKill.get(i); 9858 Slog.i(TAG, "Removing system update proc: " + proc); 9859 removeProcessLocked(proc, true, false, "system update done"); 9860 } 9861 } 9862 9863 // Now that we have cleaned up any update processes, we 9864 // are ready to start launching real processes and know that 9865 // we won't trample on them any more. 9866 mProcessesReady = true; 9867 } 9868 9869 Slog.i(TAG, "System now ready"); 9870 EventLog.writeEvent(EventLogTags.BOOT_PROGRESS_AMS_READY, 9871 SystemClock.uptimeMillis()); 9872 9873 synchronized(this) { 9874 // Make sure we have no pre-ready processes sitting around. 9875 9876 if (mFactoryTest == FactoryTest.FACTORY_TEST_LOW_LEVEL) { 9877 ResolveInfo ri = mContext.getPackageManager() 9878 .resolveActivity(new Intent(Intent.ACTION_FACTORY_TEST), 9879 STOCK_PM_FLAGS); 9880 CharSequence errorMsg = null; 9881 if (ri != null) { 9882 ActivityInfo ai = ri.activityInfo; 9883 ApplicationInfo app = ai.applicationInfo; 9884 if ((app.flags&ApplicationInfo.FLAG_SYSTEM) != 0) { 9885 mTopAction = Intent.ACTION_FACTORY_TEST; 9886 mTopData = null; 9887 mTopComponent = new ComponentName(app.packageName, 9888 ai.name); 9889 } else { 9890 errorMsg = mContext.getResources().getText( 9891 com.android.internal.R.string.factorytest_not_system); 9892 } 9893 } else { 9894 errorMsg = mContext.getResources().getText( 9895 com.android.internal.R.string.factorytest_no_action); 9896 } 9897 if (errorMsg != null) { 9898 mTopAction = null; 9899 mTopData = null; 9900 mTopComponent = null; 9901 Message msg = Message.obtain(); 9902 msg.what = SHOW_FACTORY_ERROR_MSG; 9903 msg.getData().putCharSequence("msg", errorMsg); 9904 mHandler.sendMessage(msg); 9905 } 9906 } 9907 } 9908 9909 retrieveSettings(); 9910 9911 synchronized (this) { 9912 readGrantedUriPermissionsLocked(); 9913 } 9914 9915 if (goingCallback != null) goingCallback.run(); 9916 9917 mSystemServiceManager.startUser(mCurrentUserId); 9918 9919 synchronized (this) { 9920 if (mFactoryTest != FactoryTest.FACTORY_TEST_LOW_LEVEL) { 9921 try { 9922 List apps = AppGlobals.getPackageManager(). 9923 getPersistentApplications(STOCK_PM_FLAGS); 9924 if (apps != null) { 9925 int N = apps.size(); 9926 int i; 9927 for (i=0; i<N; i++) { 9928 ApplicationInfo info 9929 = (ApplicationInfo)apps.get(i); 9930 if (info != null && 9931 !info.packageName.equals("android")) { 9932 addAppLocked(info, false, null /* ABI override */); 9933 } 9934 } 9935 } 9936 } catch (RemoteException ex) { 9937 // pm is in same process, this will never happen. 9938 } 9939 } 9940 9941 // Start up initial activity. 9942 mBooting = true; 9943 9944 try { 9945 if (AppGlobals.getPackageManager().hasSystemUidErrors()) { 9946 Message msg = Message.obtain(); 9947 msg.what = SHOW_UID_ERROR_MSG; 9948 mHandler.sendMessage(msg); 9949 } 9950 } catch (RemoteException e) { 9951 } 9952 9953 long ident = Binder.clearCallingIdentity(); 9954 try { 9955 Intent intent = new Intent(Intent.ACTION_USER_STARTED); 9956 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 9957 | Intent.FLAG_RECEIVER_FOREGROUND); 9958 intent.putExtra(Intent.EXTRA_USER_HANDLE, mCurrentUserId); 9959 broadcastIntentLocked(null, null, intent, 9960 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 9961 false, false, MY_PID, Process.SYSTEM_UID, mCurrentUserId); 9962 intent = new Intent(Intent.ACTION_USER_STARTING); 9963 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 9964 intent.putExtra(Intent.EXTRA_USER_HANDLE, mCurrentUserId); 9965 broadcastIntentLocked(null, null, intent, 9966 null, new IIntentReceiver.Stub() { 9967 @Override 9968 public void performReceive(Intent intent, int resultCode, String data, 9969 Bundle extras, boolean ordered, boolean sticky, int sendingUser) 9970 throws RemoteException { 9971 } 9972 }, 0, null, null, 9973 android.Manifest.permission.INTERACT_ACROSS_USERS, AppOpsManager.OP_NONE, 9974 true, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 9975 } catch (Throwable t) { 9976 Slog.wtf(TAG, "Failed sending first user broadcasts", t); 9977 } finally { 9978 Binder.restoreCallingIdentity(ident); 9979 } 9980 mStackSupervisor.resumeTopActivitiesLocked(); 9981 sendUserSwitchBroadcastsLocked(-1, mCurrentUserId); 9982 } 9983 } 9984 9985 private boolean makeAppCrashingLocked(ProcessRecord app, 9986 String shortMsg, String longMsg, String stackTrace) { 9987 app.crashing = true; 9988 app.crashingReport = generateProcessError(app, 9989 ActivityManager.ProcessErrorStateInfo.CRASHED, null, shortMsg, longMsg, stackTrace); 9990 startAppProblemLocked(app); 9991 app.stopFreezingAllLocked(); 9992 return handleAppCrashLocked(app, shortMsg, longMsg, stackTrace); 9993 } 9994 9995 private void makeAppNotRespondingLocked(ProcessRecord app, 9996 String activity, String shortMsg, String longMsg) { 9997 app.notResponding = true; 9998 app.notRespondingReport = generateProcessError(app, 9999 ActivityManager.ProcessErrorStateInfo.NOT_RESPONDING, 10000 activity, shortMsg, longMsg, null); 10001 startAppProblemLocked(app); 10002 app.stopFreezingAllLocked(); 10003 } 10004 10005 /** 10006 * Generate a process error record, suitable for attachment to a ProcessRecord. 10007 * 10008 * @param app The ProcessRecord in which the error occurred. 10009 * @param condition Crashing, Application Not Responding, etc. Values are defined in 10010 * ActivityManager.AppErrorStateInfo 10011 * @param activity The activity associated with the crash, if known. 10012 * @param shortMsg Short message describing the crash. 10013 * @param longMsg Long message describing the crash. 10014 * @param stackTrace Full crash stack trace, may be null. 10015 * 10016 * @return Returns a fully-formed AppErrorStateInfo record. 10017 */ 10018 private ActivityManager.ProcessErrorStateInfo generateProcessError(ProcessRecord app, 10019 int condition, String activity, String shortMsg, String longMsg, String stackTrace) { 10020 ActivityManager.ProcessErrorStateInfo report = new ActivityManager.ProcessErrorStateInfo(); 10021 10022 report.condition = condition; 10023 report.processName = app.processName; 10024 report.pid = app.pid; 10025 report.uid = app.info.uid; 10026 report.tag = activity; 10027 report.shortMsg = shortMsg; 10028 report.longMsg = longMsg; 10029 report.stackTrace = stackTrace; 10030 10031 return report; 10032 } 10033 10034 void killAppAtUsersRequest(ProcessRecord app, Dialog fromDialog) { 10035 synchronized (this) { 10036 app.crashing = false; 10037 app.crashingReport = null; 10038 app.notResponding = false; 10039 app.notRespondingReport = null; 10040 if (app.anrDialog == fromDialog) { 10041 app.anrDialog = null; 10042 } 10043 if (app.waitDialog == fromDialog) { 10044 app.waitDialog = null; 10045 } 10046 if (app.pid > 0 && app.pid != MY_PID) { 10047 handleAppCrashLocked(app, null, null, null); 10048 killUnneededProcessLocked(app, "user request after error"); 10049 } 10050 } 10051 } 10052 10053 private boolean handleAppCrashLocked(ProcessRecord app, String shortMsg, String longMsg, 10054 String stackTrace) { 10055 long now = SystemClock.uptimeMillis(); 10056 10057 Long crashTime; 10058 if (!app.isolated) { 10059 crashTime = mProcessCrashTimes.get(app.info.processName, app.uid); 10060 } else { 10061 crashTime = null; 10062 } 10063 if (crashTime != null && now < crashTime+ProcessList.MIN_CRASH_INTERVAL) { 10064 // This process loses! 10065 Slog.w(TAG, "Process " + app.info.processName 10066 + " has crashed too many times: killing!"); 10067 EventLog.writeEvent(EventLogTags.AM_PROCESS_CRASHED_TOO_MUCH, 10068 app.userId, app.info.processName, app.uid); 10069 mStackSupervisor.handleAppCrashLocked(app); 10070 if (!app.persistent) { 10071 // We don't want to start this process again until the user 10072 // explicitly does so... but for persistent process, we really 10073 // need to keep it running. If a persistent process is actually 10074 // repeatedly crashing, then badness for everyone. 10075 EventLog.writeEvent(EventLogTags.AM_PROC_BAD, app.userId, app.uid, 10076 app.info.processName); 10077 if (!app.isolated) { 10078 // XXX We don't have a way to mark isolated processes 10079 // as bad, since they don't have a peristent identity. 10080 mBadProcesses.put(app.info.processName, app.uid, 10081 new BadProcessInfo(now, shortMsg, longMsg, stackTrace)); 10082 mProcessCrashTimes.remove(app.info.processName, app.uid); 10083 } 10084 app.bad = true; 10085 app.removed = true; 10086 // Don't let services in this process be restarted and potentially 10087 // annoy the user repeatedly. Unless it is persistent, since those 10088 // processes run critical code. 10089 removeProcessLocked(app, false, false, "crash"); 10090 mStackSupervisor.resumeTopActivitiesLocked(); 10091 return false; 10092 } 10093 mStackSupervisor.resumeTopActivitiesLocked(); 10094 } else { 10095 mStackSupervisor.finishTopRunningActivityLocked(app); 10096 } 10097 10098 // Bump up the crash count of any services currently running in the proc. 10099 for (int i=app.services.size()-1; i>=0; i--) { 10100 // Any services running in the application need to be placed 10101 // back in the pending list. 10102 ServiceRecord sr = app.services.valueAt(i); 10103 sr.crashCount++; 10104 } 10105 10106 // If the crashing process is what we consider to be the "home process" and it has been 10107 // replaced by a third-party app, clear the package preferred activities from packages 10108 // with a home activity running in the process to prevent a repeatedly crashing app 10109 // from blocking the user to manually clear the list. 10110 final ArrayList<ActivityRecord> activities = app.activities; 10111 if (app == mHomeProcess && activities.size() > 0 10112 && (mHomeProcess.info.flags & ApplicationInfo.FLAG_SYSTEM) == 0) { 10113 for (int activityNdx = activities.size() - 1; activityNdx >= 0; --activityNdx) { 10114 final ActivityRecord r = activities.get(activityNdx); 10115 if (r.isHomeActivity()) { 10116 Log.i(TAG, "Clearing package preferred activities from " + r.packageName); 10117 try { 10118 ActivityThread.getPackageManager() 10119 .clearPackagePreferredActivities(r.packageName); 10120 } catch (RemoteException c) { 10121 // pm is in same process, this will never happen. 10122 } 10123 } 10124 } 10125 } 10126 10127 if (!app.isolated) { 10128 // XXX Can't keep track of crash times for isolated processes, 10129 // because they don't have a perisistent identity. 10130 mProcessCrashTimes.put(app.info.processName, app.uid, now); 10131 } 10132 10133 return true; 10134 } 10135 10136 void startAppProblemLocked(ProcessRecord app) { 10137 if (app.userId == mCurrentUserId) { 10138 app.errorReportReceiver = ApplicationErrorReport.getErrorReportReceiver( 10139 mContext, app.info.packageName, app.info.flags); 10140 } else { 10141 // If this app is not running under the current user, then we 10142 // can't give it a report button because that would require 10143 // launching the report UI under a different user. 10144 app.errorReportReceiver = null; 10145 } 10146 skipCurrentReceiverLocked(app); 10147 } 10148 10149 void skipCurrentReceiverLocked(ProcessRecord app) { 10150 for (BroadcastQueue queue : mBroadcastQueues) { 10151 queue.skipCurrentReceiverLocked(app); 10152 } 10153 } 10154 10155 /** 10156 * Used by {@link com.android.internal.os.RuntimeInit} to report when an application crashes. 10157 * The application process will exit immediately after this call returns. 10158 * @param app object of the crashing app, null for the system server 10159 * @param crashInfo describing the exception 10160 */ 10161 public void handleApplicationCrash(IBinder app, ApplicationErrorReport.CrashInfo crashInfo) { 10162 ProcessRecord r = findAppProcess(app, "Crash"); 10163 final String processName = app == null ? "system_server" 10164 : (r == null ? "unknown" : r.processName); 10165 10166 handleApplicationCrashInner("crash", r, processName, crashInfo); 10167 } 10168 10169 /* Native crash reporting uses this inner version because it needs to be somewhat 10170 * decoupled from the AM-managed cleanup lifecycle 10171 */ 10172 void handleApplicationCrashInner(String eventType, ProcessRecord r, String processName, 10173 ApplicationErrorReport.CrashInfo crashInfo) { 10174 EventLog.writeEvent(EventLogTags.AM_CRASH, Binder.getCallingPid(), 10175 UserHandle.getUserId(Binder.getCallingUid()), processName, 10176 r == null ? -1 : r.info.flags, 10177 crashInfo.exceptionClassName, 10178 crashInfo.exceptionMessage, 10179 crashInfo.throwFileName, 10180 crashInfo.throwLineNumber); 10181 10182 addErrorToDropBox(eventType, r, processName, null, null, null, null, null, crashInfo); 10183 10184 crashApplication(r, crashInfo); 10185 } 10186 10187 public void handleApplicationStrictModeViolation( 10188 IBinder app, 10189 int violationMask, 10190 StrictMode.ViolationInfo info) { 10191 ProcessRecord r = findAppProcess(app, "StrictMode"); 10192 if (r == null) { 10193 return; 10194 } 10195 10196 if ((violationMask & StrictMode.PENALTY_DROPBOX) != 0) { 10197 Integer stackFingerprint = info.hashCode(); 10198 boolean logIt = true; 10199 synchronized (mAlreadyLoggedViolatedStacks) { 10200 if (mAlreadyLoggedViolatedStacks.contains(stackFingerprint)) { 10201 logIt = false; 10202 // TODO: sub-sample into EventLog for these, with 10203 // the info.durationMillis? Then we'd get 10204 // the relative pain numbers, without logging all 10205 // the stack traces repeatedly. We'd want to do 10206 // likewise in the client code, which also does 10207 // dup suppression, before the Binder call. 10208 } else { 10209 if (mAlreadyLoggedViolatedStacks.size() >= MAX_DUP_SUPPRESSED_STACKS) { 10210 mAlreadyLoggedViolatedStacks.clear(); 10211 } 10212 mAlreadyLoggedViolatedStacks.add(stackFingerprint); 10213 } 10214 } 10215 if (logIt) { 10216 logStrictModeViolationToDropBox(r, info); 10217 } 10218 } 10219 10220 if ((violationMask & StrictMode.PENALTY_DIALOG) != 0) { 10221 AppErrorResult result = new AppErrorResult(); 10222 synchronized (this) { 10223 final long origId = Binder.clearCallingIdentity(); 10224 10225 Message msg = Message.obtain(); 10226 msg.what = SHOW_STRICT_MODE_VIOLATION_MSG; 10227 HashMap<String, Object> data = new HashMap<String, Object>(); 10228 data.put("result", result); 10229 data.put("app", r); 10230 data.put("violationMask", violationMask); 10231 data.put("info", info); 10232 msg.obj = data; 10233 mHandler.sendMessage(msg); 10234 10235 Binder.restoreCallingIdentity(origId); 10236 } 10237 int res = result.get(); 10238 Slog.w(TAG, "handleApplicationStrictModeViolation; res=" + res); 10239 } 10240 } 10241 10242 // Depending on the policy in effect, there could be a bunch of 10243 // these in quick succession so we try to batch these together to 10244 // minimize disk writes, number of dropbox entries, and maximize 10245 // compression, by having more fewer, larger records. 10246 private void logStrictModeViolationToDropBox( 10247 ProcessRecord process, 10248 StrictMode.ViolationInfo info) { 10249 if (info == null) { 10250 return; 10251 } 10252 final boolean isSystemApp = process == null || 10253 (process.info.flags & (ApplicationInfo.FLAG_SYSTEM | 10254 ApplicationInfo.FLAG_UPDATED_SYSTEM_APP)) != 0; 10255 final String processName = process == null ? "unknown" : process.processName; 10256 final String dropboxTag = isSystemApp ? "system_app_strictmode" : "data_app_strictmode"; 10257 final DropBoxManager dbox = (DropBoxManager) 10258 mContext.getSystemService(Context.DROPBOX_SERVICE); 10259 10260 // Exit early if the dropbox isn't configured to accept this report type. 10261 if (dbox == null || !dbox.isTagEnabled(dropboxTag)) return; 10262 10263 boolean bufferWasEmpty; 10264 boolean needsFlush; 10265 final StringBuilder sb = isSystemApp ? mStrictModeBuffer : new StringBuilder(1024); 10266 synchronized (sb) { 10267 bufferWasEmpty = sb.length() == 0; 10268 appendDropBoxProcessHeaders(process, processName, sb); 10269 sb.append("Build: ").append(Build.FINGERPRINT).append("\n"); 10270 sb.append("System-App: ").append(isSystemApp).append("\n"); 10271 sb.append("Uptime-Millis: ").append(info.violationUptimeMillis).append("\n"); 10272 if (info.violationNumThisLoop != 0) { 10273 sb.append("Loop-Violation-Number: ").append(info.violationNumThisLoop).append("\n"); 10274 } 10275 if (info.numAnimationsRunning != 0) { 10276 sb.append("Animations-Running: ").append(info.numAnimationsRunning).append("\n"); 10277 } 10278 if (info.broadcastIntentAction != null) { 10279 sb.append("Broadcast-Intent-Action: ").append(info.broadcastIntentAction).append("\n"); 10280 } 10281 if (info.durationMillis != -1) { 10282 sb.append("Duration-Millis: ").append(info.durationMillis).append("\n"); 10283 } 10284 if (info.numInstances != -1) { 10285 sb.append("Instance-Count: ").append(info.numInstances).append("\n"); 10286 } 10287 if (info.tags != null) { 10288 for (String tag : info.tags) { 10289 sb.append("Span-Tag: ").append(tag).append("\n"); 10290 } 10291 } 10292 sb.append("\n"); 10293 if (info.crashInfo != null && info.crashInfo.stackTrace != null) { 10294 sb.append(info.crashInfo.stackTrace); 10295 } 10296 sb.append("\n"); 10297 10298 // Only buffer up to ~64k. Various logging bits truncate 10299 // things at 128k. 10300 needsFlush = (sb.length() > 64 * 1024); 10301 } 10302 10303 // Flush immediately if the buffer's grown too large, or this 10304 // is a non-system app. Non-system apps are isolated with a 10305 // different tag & policy and not batched. 10306 // 10307 // Batching is useful during internal testing with 10308 // StrictMode settings turned up high. Without batching, 10309 // thousands of separate files could be created on boot. 10310 if (!isSystemApp || needsFlush) { 10311 new Thread("Error dump: " + dropboxTag) { 10312 @Override 10313 public void run() { 10314 String report; 10315 synchronized (sb) { 10316 report = sb.toString(); 10317 sb.delete(0, sb.length()); 10318 sb.trimToSize(); 10319 } 10320 if (report.length() != 0) { 10321 dbox.addText(dropboxTag, report); 10322 } 10323 } 10324 }.start(); 10325 return; 10326 } 10327 10328 // System app batching: 10329 if (!bufferWasEmpty) { 10330 // An existing dropbox-writing thread is outstanding, so 10331 // we don't need to start it up. The existing thread will 10332 // catch the buffer appends we just did. 10333 return; 10334 } 10335 10336 // Worker thread to both batch writes and to avoid blocking the caller on I/O. 10337 // (After this point, we shouldn't access AMS internal data structures.) 10338 new Thread("Error dump: " + dropboxTag) { 10339 @Override 10340 public void run() { 10341 // 5 second sleep to let stacks arrive and be batched together 10342 try { 10343 Thread.sleep(5000); // 5 seconds 10344 } catch (InterruptedException e) {} 10345 10346 String errorReport; 10347 synchronized (mStrictModeBuffer) { 10348 errorReport = mStrictModeBuffer.toString(); 10349 if (errorReport.length() == 0) { 10350 return; 10351 } 10352 mStrictModeBuffer.delete(0, mStrictModeBuffer.length()); 10353 mStrictModeBuffer.trimToSize(); 10354 } 10355 dbox.addText(dropboxTag, errorReport); 10356 } 10357 }.start(); 10358 } 10359 10360 /** 10361 * Used by {@link Log} via {@link com.android.internal.os.RuntimeInit} to report serious errors. 10362 * @param app object of the crashing app, null for the system server 10363 * @param tag reported by the caller 10364 * @param crashInfo describing the context of the error 10365 * @return true if the process should exit immediately (WTF is fatal) 10366 */ 10367 public boolean handleApplicationWtf(IBinder app, String tag, 10368 ApplicationErrorReport.CrashInfo crashInfo) { 10369 ProcessRecord r = findAppProcess(app, "WTF"); 10370 final String processName = app == null ? "system_server" 10371 : (r == null ? "unknown" : r.processName); 10372 10373 EventLog.writeEvent(EventLogTags.AM_WTF, 10374 UserHandle.getUserId(Binder.getCallingUid()), Binder.getCallingPid(), 10375 processName, 10376 r == null ? -1 : r.info.flags, 10377 tag, crashInfo.exceptionMessage); 10378 10379 addErrorToDropBox("wtf", r, processName, null, null, tag, null, null, crashInfo); 10380 10381 if (r != null && r.pid != Process.myPid() && 10382 Settings.Global.getInt(mContext.getContentResolver(), 10383 Settings.Global.WTF_IS_FATAL, 0) != 0) { 10384 crashApplication(r, crashInfo); 10385 return true; 10386 } else { 10387 return false; 10388 } 10389 } 10390 10391 /** 10392 * @param app object of some object (as stored in {@link com.android.internal.os.RuntimeInit}) 10393 * @return the corresponding {@link ProcessRecord} object, or null if none could be found 10394 */ 10395 private ProcessRecord findAppProcess(IBinder app, String reason) { 10396 if (app == null) { 10397 return null; 10398 } 10399 10400 synchronized (this) { 10401 final int NP = mProcessNames.getMap().size(); 10402 for (int ip=0; ip<NP; ip++) { 10403 SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 10404 final int NA = apps.size(); 10405 for (int ia=0; ia<NA; ia++) { 10406 ProcessRecord p = apps.valueAt(ia); 10407 if (p.thread != null && p.thread.asBinder() == app) { 10408 return p; 10409 } 10410 } 10411 } 10412 10413 Slog.w(TAG, "Can't find mystery application for " + reason 10414 + " from pid=" + Binder.getCallingPid() 10415 + " uid=" + Binder.getCallingUid() + ": " + app); 10416 return null; 10417 } 10418 } 10419 10420 /** 10421 * Utility function for addErrorToDropBox and handleStrictModeViolation's logging 10422 * to append various headers to the dropbox log text. 10423 */ 10424 private void appendDropBoxProcessHeaders(ProcessRecord process, String processName, 10425 StringBuilder sb) { 10426 // Watchdog thread ends up invoking this function (with 10427 // a null ProcessRecord) to add the stack file to dropbox. 10428 // Do not acquire a lock on this (am) in such cases, as it 10429 // could cause a potential deadlock, if and when watchdog 10430 // is invoked due to unavailability of lock on am and it 10431 // would prevent watchdog from killing system_server. 10432 if (process == null) { 10433 sb.append("Process: ").append(processName).append("\n"); 10434 return; 10435 } 10436 // Note: ProcessRecord 'process' is guarded by the service 10437 // instance. (notably process.pkgList, which could otherwise change 10438 // concurrently during execution of this method) 10439 synchronized (this) { 10440 sb.append("Process: ").append(processName).append("\n"); 10441 int flags = process.info.flags; 10442 IPackageManager pm = AppGlobals.getPackageManager(); 10443 sb.append("Flags: 0x").append(Integer.toString(flags, 16)).append("\n"); 10444 for (int ip=0; ip<process.pkgList.size(); ip++) { 10445 String pkg = process.pkgList.keyAt(ip); 10446 sb.append("Package: ").append(pkg); 10447 try { 10448 PackageInfo pi = pm.getPackageInfo(pkg, 0, UserHandle.getCallingUserId()); 10449 if (pi != null) { 10450 sb.append(" v").append(pi.versionCode); 10451 if (pi.versionName != null) { 10452 sb.append(" (").append(pi.versionName).append(")"); 10453 } 10454 } 10455 } catch (RemoteException e) { 10456 Slog.e(TAG, "Error getting package info: " + pkg, e); 10457 } 10458 sb.append("\n"); 10459 } 10460 } 10461 } 10462 10463 private static String processClass(ProcessRecord process) { 10464 if (process == null || process.pid == MY_PID) { 10465 return "system_server"; 10466 } else if ((process.info.flags & ApplicationInfo.FLAG_SYSTEM) != 0) { 10467 return "system_app"; 10468 } else { 10469 return "data_app"; 10470 } 10471 } 10472 10473 /** 10474 * Write a description of an error (crash, WTF, ANR) to the drop box. 10475 * @param eventType to include in the drop box tag ("crash", "wtf", etc.) 10476 * @param process which caused the error, null means the system server 10477 * @param activity which triggered the error, null if unknown 10478 * @param parent activity related to the error, null if unknown 10479 * @param subject line related to the error, null if absent 10480 * @param report in long form describing the error, null if absent 10481 * @param logFile to include in the report, null if none 10482 * @param crashInfo giving an application stack trace, null if absent 10483 */ 10484 public void addErrorToDropBox(String eventType, 10485 ProcessRecord process, String processName, ActivityRecord activity, 10486 ActivityRecord parent, String subject, 10487 final String report, final File logFile, 10488 final ApplicationErrorReport.CrashInfo crashInfo) { 10489 // NOTE -- this must never acquire the ActivityManagerService lock, 10490 // otherwise the watchdog may be prevented from resetting the system. 10491 10492 final String dropboxTag = processClass(process) + "_" + eventType; 10493 final DropBoxManager dbox = (DropBoxManager) 10494 mContext.getSystemService(Context.DROPBOX_SERVICE); 10495 10496 // Exit early if the dropbox isn't configured to accept this report type. 10497 if (dbox == null || !dbox.isTagEnabled(dropboxTag)) return; 10498 10499 final StringBuilder sb = new StringBuilder(1024); 10500 appendDropBoxProcessHeaders(process, processName, sb); 10501 if (activity != null) { 10502 sb.append("Activity: ").append(activity.shortComponentName).append("\n"); 10503 } 10504 if (parent != null && parent.app != null && parent.app.pid != process.pid) { 10505 sb.append("Parent-Process: ").append(parent.app.processName).append("\n"); 10506 } 10507 if (parent != null && parent != activity) { 10508 sb.append("Parent-Activity: ").append(parent.shortComponentName).append("\n"); 10509 } 10510 if (subject != null) { 10511 sb.append("Subject: ").append(subject).append("\n"); 10512 } 10513 sb.append("Build: ").append(Build.FINGERPRINT).append("\n"); 10514 if (Debug.isDebuggerConnected()) { 10515 sb.append("Debugger: Connected\n"); 10516 } 10517 sb.append("\n"); 10518 10519 // Do the rest in a worker thread to avoid blocking the caller on I/O 10520 // (After this point, we shouldn't access AMS internal data structures.) 10521 Thread worker = new Thread("Error dump: " + dropboxTag) { 10522 @Override 10523 public void run() { 10524 if (report != null) { 10525 sb.append(report); 10526 } 10527 if (logFile != null) { 10528 try { 10529 sb.append(FileUtils.readTextFile(logFile, DROPBOX_MAX_SIZE, 10530 "\n\n[[TRUNCATED]]")); 10531 } catch (IOException e) { 10532 Slog.e(TAG, "Error reading " + logFile, e); 10533 } 10534 } 10535 if (crashInfo != null && crashInfo.stackTrace != null) { 10536 sb.append(crashInfo.stackTrace); 10537 } 10538 10539 String setting = Settings.Global.ERROR_LOGCAT_PREFIX + dropboxTag; 10540 int lines = Settings.Global.getInt(mContext.getContentResolver(), setting, 0); 10541 if (lines > 0) { 10542 sb.append("\n"); 10543 10544 // Merge several logcat streams, and take the last N lines 10545 InputStreamReader input = null; 10546 try { 10547 java.lang.Process logcat = new ProcessBuilder("/system/bin/logcat", 10548 "-v", "time", "-b", "events", "-b", "system", "-b", "main", 10549 "-t", String.valueOf(lines)).redirectErrorStream(true).start(); 10550 10551 try { logcat.getOutputStream().close(); } catch (IOException e) {} 10552 try { logcat.getErrorStream().close(); } catch (IOException e) {} 10553 input = new InputStreamReader(logcat.getInputStream()); 10554 10555 int num; 10556 char[] buf = new char[8192]; 10557 while ((num = input.read(buf)) > 0) sb.append(buf, 0, num); 10558 } catch (IOException e) { 10559 Slog.e(TAG, "Error running logcat", e); 10560 } finally { 10561 if (input != null) try { input.close(); } catch (IOException e) {} 10562 } 10563 } 10564 10565 dbox.addText(dropboxTag, sb.toString()); 10566 } 10567 }; 10568 10569 if (process == null) { 10570 // If process is null, we are being called from some internal code 10571 // and may be about to die -- run this synchronously. 10572 worker.run(); 10573 } else { 10574 worker.start(); 10575 } 10576 } 10577 10578 /** 10579 * Bring up the "unexpected error" dialog box for a crashing app. 10580 * Deal with edge cases (intercepts from instrumented applications, 10581 * ActivityController, error intent receivers, that sort of thing). 10582 * @param r the application crashing 10583 * @param crashInfo describing the failure 10584 */ 10585 private void crashApplication(ProcessRecord r, ApplicationErrorReport.CrashInfo crashInfo) { 10586 long timeMillis = System.currentTimeMillis(); 10587 String shortMsg = crashInfo.exceptionClassName; 10588 String longMsg = crashInfo.exceptionMessage; 10589 String stackTrace = crashInfo.stackTrace; 10590 if (shortMsg != null && longMsg != null) { 10591 longMsg = shortMsg + ": " + longMsg; 10592 } else if (shortMsg != null) { 10593 longMsg = shortMsg; 10594 } 10595 10596 AppErrorResult result = new AppErrorResult(); 10597 synchronized (this) { 10598 if (mController != null) { 10599 try { 10600 String name = r != null ? r.processName : null; 10601 int pid = r != null ? r.pid : Binder.getCallingPid(); 10602 if (!mController.appCrashed(name, pid, 10603 shortMsg, longMsg, timeMillis, crashInfo.stackTrace)) { 10604 Slog.w(TAG, "Force-killing crashed app " + name 10605 + " at watcher's request"); 10606 Process.killProcess(pid); 10607 return; 10608 } 10609 } catch (RemoteException e) { 10610 mController = null; 10611 Watchdog.getInstance().setActivityController(null); 10612 } 10613 } 10614 10615 final long origId = Binder.clearCallingIdentity(); 10616 10617 // If this process is running instrumentation, finish it. 10618 if (r != null && r.instrumentationClass != null) { 10619 Slog.w(TAG, "Error in app " + r.processName 10620 + " running instrumentation " + r.instrumentationClass + ":"); 10621 if (shortMsg != null) Slog.w(TAG, " " + shortMsg); 10622 if (longMsg != null) Slog.w(TAG, " " + longMsg); 10623 Bundle info = new Bundle(); 10624 info.putString("shortMsg", shortMsg); 10625 info.putString("longMsg", longMsg); 10626 finishInstrumentationLocked(r, Activity.RESULT_CANCELED, info); 10627 Binder.restoreCallingIdentity(origId); 10628 return; 10629 } 10630 10631 // If we can't identify the process or it's already exceeded its crash quota, 10632 // quit right away without showing a crash dialog. 10633 if (r == null || !makeAppCrashingLocked(r, shortMsg, longMsg, stackTrace)) { 10634 Binder.restoreCallingIdentity(origId); 10635 return; 10636 } 10637 10638 Message msg = Message.obtain(); 10639 msg.what = SHOW_ERROR_MSG; 10640 HashMap data = new HashMap(); 10641 data.put("result", result); 10642 data.put("app", r); 10643 msg.obj = data; 10644 mHandler.sendMessage(msg); 10645 10646 Binder.restoreCallingIdentity(origId); 10647 } 10648 10649 int res = result.get(); 10650 10651 Intent appErrorIntent = null; 10652 synchronized (this) { 10653 if (r != null && !r.isolated) { 10654 // XXX Can't keep track of crash time for isolated processes, 10655 // since they don't have a persistent identity. 10656 mProcessCrashTimes.put(r.info.processName, r.uid, 10657 SystemClock.uptimeMillis()); 10658 } 10659 if (res == AppErrorDialog.FORCE_QUIT_AND_REPORT) { 10660 appErrorIntent = createAppErrorIntentLocked(r, timeMillis, crashInfo); 10661 } 10662 } 10663 10664 if (appErrorIntent != null) { 10665 try { 10666 mContext.startActivityAsUser(appErrorIntent, new UserHandle(r.userId)); 10667 } catch (ActivityNotFoundException e) { 10668 Slog.w(TAG, "bug report receiver dissappeared", e); 10669 } 10670 } 10671 } 10672 10673 Intent createAppErrorIntentLocked(ProcessRecord r, 10674 long timeMillis, ApplicationErrorReport.CrashInfo crashInfo) { 10675 ApplicationErrorReport report = createAppErrorReportLocked(r, timeMillis, crashInfo); 10676 if (report == null) { 10677 return null; 10678 } 10679 Intent result = new Intent(Intent.ACTION_APP_ERROR); 10680 result.setComponent(r.errorReportReceiver); 10681 result.putExtra(Intent.EXTRA_BUG_REPORT, report); 10682 result.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK); 10683 return result; 10684 } 10685 10686 private ApplicationErrorReport createAppErrorReportLocked(ProcessRecord r, 10687 long timeMillis, ApplicationErrorReport.CrashInfo crashInfo) { 10688 if (r.errorReportReceiver == null) { 10689 return null; 10690 } 10691 10692 if (!r.crashing && !r.notResponding && !r.forceCrashReport) { 10693 return null; 10694 } 10695 10696 ApplicationErrorReport report = new ApplicationErrorReport(); 10697 report.packageName = r.info.packageName; 10698 report.installerPackageName = r.errorReportReceiver.getPackageName(); 10699 report.processName = r.processName; 10700 report.time = timeMillis; 10701 report.systemApp = (r.info.flags & ApplicationInfo.FLAG_SYSTEM) != 0; 10702 10703 if (r.crashing || r.forceCrashReport) { 10704 report.type = ApplicationErrorReport.TYPE_CRASH; 10705 report.crashInfo = crashInfo; 10706 } else if (r.notResponding) { 10707 report.type = ApplicationErrorReport.TYPE_ANR; 10708 report.anrInfo = new ApplicationErrorReport.AnrInfo(); 10709 10710 report.anrInfo.activity = r.notRespondingReport.tag; 10711 report.anrInfo.cause = r.notRespondingReport.shortMsg; 10712 report.anrInfo.info = r.notRespondingReport.longMsg; 10713 } 10714 10715 return report; 10716 } 10717 10718 public List<ActivityManager.ProcessErrorStateInfo> getProcessesInErrorState() { 10719 enforceNotIsolatedCaller("getProcessesInErrorState"); 10720 // assume our apps are happy - lazy create the list 10721 List<ActivityManager.ProcessErrorStateInfo> errList = null; 10722 10723 final boolean allUsers = ActivityManager.checkUidPermission(INTERACT_ACROSS_USERS_FULL, 10724 Binder.getCallingUid()) == PackageManager.PERMISSION_GRANTED; 10725 int userId = UserHandle.getUserId(Binder.getCallingUid()); 10726 10727 synchronized (this) { 10728 10729 // iterate across all processes 10730 for (int i=mLruProcesses.size()-1; i>=0; i--) { 10731 ProcessRecord app = mLruProcesses.get(i); 10732 if (!allUsers && app.userId != userId) { 10733 continue; 10734 } 10735 if ((app.thread != null) && (app.crashing || app.notResponding)) { 10736 // This one's in trouble, so we'll generate a report for it 10737 // crashes are higher priority (in case there's a crash *and* an anr) 10738 ActivityManager.ProcessErrorStateInfo report = null; 10739 if (app.crashing) { 10740 report = app.crashingReport; 10741 } else if (app.notResponding) { 10742 report = app.notRespondingReport; 10743 } 10744 10745 if (report != null) { 10746 if (errList == null) { 10747 errList = new ArrayList<ActivityManager.ProcessErrorStateInfo>(1); 10748 } 10749 errList.add(report); 10750 } else { 10751 Slog.w(TAG, "Missing app error report, app = " + app.processName + 10752 " crashing = " + app.crashing + 10753 " notResponding = " + app.notResponding); 10754 } 10755 } 10756 } 10757 } 10758 10759 return errList; 10760 } 10761 10762 static int oomAdjToImportance(int adj, ActivityManager.RunningAppProcessInfo currApp) { 10763 if (adj >= ProcessList.CACHED_APP_MIN_ADJ) { 10764 if (currApp != null) { 10765 currApp.lru = adj - ProcessList.CACHED_APP_MIN_ADJ + 1; 10766 } 10767 return ActivityManager.RunningAppProcessInfo.IMPORTANCE_BACKGROUND; 10768 } else if (adj >= ProcessList.SERVICE_B_ADJ) { 10769 return ActivityManager.RunningAppProcessInfo.IMPORTANCE_SERVICE; 10770 } else if (adj >= ProcessList.HOME_APP_ADJ) { 10771 if (currApp != null) { 10772 currApp.lru = 0; 10773 } 10774 return ActivityManager.RunningAppProcessInfo.IMPORTANCE_BACKGROUND; 10775 } else if (adj >= ProcessList.SERVICE_ADJ) { 10776 return ActivityManager.RunningAppProcessInfo.IMPORTANCE_SERVICE; 10777 } else if (adj >= ProcessList.HEAVY_WEIGHT_APP_ADJ) { 10778 return ActivityManager.RunningAppProcessInfo.IMPORTANCE_CANT_SAVE_STATE; 10779 } else if (adj >= ProcessList.PERCEPTIBLE_APP_ADJ) { 10780 return ActivityManager.RunningAppProcessInfo.IMPORTANCE_PERCEPTIBLE; 10781 } else if (adj >= ProcessList.VISIBLE_APP_ADJ) { 10782 return ActivityManager.RunningAppProcessInfo.IMPORTANCE_VISIBLE; 10783 } else { 10784 return ActivityManager.RunningAppProcessInfo.IMPORTANCE_FOREGROUND; 10785 } 10786 } 10787 10788 private void fillInProcMemInfo(ProcessRecord app, 10789 ActivityManager.RunningAppProcessInfo outInfo) { 10790 outInfo.pid = app.pid; 10791 outInfo.uid = app.info.uid; 10792 if (mHeavyWeightProcess == app) { 10793 outInfo.flags |= ActivityManager.RunningAppProcessInfo.FLAG_CANT_SAVE_STATE; 10794 } 10795 if (app.persistent) { 10796 outInfo.flags |= ActivityManager.RunningAppProcessInfo.FLAG_PERSISTENT; 10797 } 10798 if (app.activities.size() > 0) { 10799 outInfo.flags |= ActivityManager.RunningAppProcessInfo.FLAG_HAS_ACTIVITIES; 10800 } 10801 outInfo.lastTrimLevel = app.trimMemoryLevel; 10802 int adj = app.curAdj; 10803 outInfo.importance = oomAdjToImportance(adj, outInfo); 10804 outInfo.importanceReasonCode = app.adjTypeCode; 10805 outInfo.processState = app.curProcState; 10806 } 10807 10808 public List<ActivityManager.RunningAppProcessInfo> getRunningAppProcesses() { 10809 enforceNotIsolatedCaller("getRunningAppProcesses"); 10810 // Lazy instantiation of list 10811 List<ActivityManager.RunningAppProcessInfo> runList = null; 10812 final boolean allUsers = ActivityManager.checkUidPermission(INTERACT_ACROSS_USERS_FULL, 10813 Binder.getCallingUid()) == PackageManager.PERMISSION_GRANTED; 10814 int userId = UserHandle.getUserId(Binder.getCallingUid()); 10815 synchronized (this) { 10816 // Iterate across all processes 10817 for (int i=mLruProcesses.size()-1; i>=0; i--) { 10818 ProcessRecord app = mLruProcesses.get(i); 10819 if (!allUsers && app.userId != userId) { 10820 continue; 10821 } 10822 if ((app.thread != null) && (!app.crashing && !app.notResponding)) { 10823 // Generate process state info for running application 10824 ActivityManager.RunningAppProcessInfo currApp = 10825 new ActivityManager.RunningAppProcessInfo(app.processName, 10826 app.pid, app.getPackageList()); 10827 fillInProcMemInfo(app, currApp); 10828 if (app.adjSource instanceof ProcessRecord) { 10829 currApp.importanceReasonPid = ((ProcessRecord)app.adjSource).pid; 10830 currApp.importanceReasonImportance = oomAdjToImportance( 10831 app.adjSourceOom, null); 10832 } else if (app.adjSource instanceof ActivityRecord) { 10833 ActivityRecord r = (ActivityRecord)app.adjSource; 10834 if (r.app != null) currApp.importanceReasonPid = r.app.pid; 10835 } 10836 if (app.adjTarget instanceof ComponentName) { 10837 currApp.importanceReasonComponent = (ComponentName)app.adjTarget; 10838 } 10839 //Slog.v(TAG, "Proc " + app.processName + ": imp=" + currApp.importance 10840 // + " lru=" + currApp.lru); 10841 if (runList == null) { 10842 runList = new ArrayList<ActivityManager.RunningAppProcessInfo>(); 10843 } 10844 runList.add(currApp); 10845 } 10846 } 10847 } 10848 return runList; 10849 } 10850 10851 public List<ApplicationInfo> getRunningExternalApplications() { 10852 enforceNotIsolatedCaller("getRunningExternalApplications"); 10853 List<ActivityManager.RunningAppProcessInfo> runningApps = getRunningAppProcesses(); 10854 List<ApplicationInfo> retList = new ArrayList<ApplicationInfo>(); 10855 if (runningApps != null && runningApps.size() > 0) { 10856 Set<String> extList = new HashSet<String>(); 10857 for (ActivityManager.RunningAppProcessInfo app : runningApps) { 10858 if (app.pkgList != null) { 10859 for (String pkg : app.pkgList) { 10860 extList.add(pkg); 10861 } 10862 } 10863 } 10864 IPackageManager pm = AppGlobals.getPackageManager(); 10865 for (String pkg : extList) { 10866 try { 10867 ApplicationInfo info = pm.getApplicationInfo(pkg, 0, UserHandle.getCallingUserId()); 10868 if ((info.flags & ApplicationInfo.FLAG_EXTERNAL_STORAGE) != 0) { 10869 retList.add(info); 10870 } 10871 } catch (RemoteException e) { 10872 } 10873 } 10874 } 10875 return retList; 10876 } 10877 10878 @Override 10879 public void getMyMemoryState(ActivityManager.RunningAppProcessInfo outInfo) { 10880 enforceNotIsolatedCaller("getMyMemoryState"); 10881 synchronized (this) { 10882 ProcessRecord proc; 10883 synchronized (mPidsSelfLocked) { 10884 proc = mPidsSelfLocked.get(Binder.getCallingPid()); 10885 } 10886 fillInProcMemInfo(proc, outInfo); 10887 } 10888 } 10889 10890 @Override 10891 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 10892 if (checkCallingPermission(android.Manifest.permission.DUMP) 10893 != PackageManager.PERMISSION_GRANTED) { 10894 pw.println("Permission Denial: can't dump ActivityManager from from pid=" 10895 + Binder.getCallingPid() 10896 + ", uid=" + Binder.getCallingUid() 10897 + " without permission " 10898 + android.Manifest.permission.DUMP); 10899 return; 10900 } 10901 10902 boolean dumpAll = false; 10903 boolean dumpClient = false; 10904 String dumpPackage = null; 10905 10906 int opti = 0; 10907 while (opti < args.length) { 10908 String opt = args[opti]; 10909 if (opt == null || opt.length() <= 0 || opt.charAt(0) != '-') { 10910 break; 10911 } 10912 opti++; 10913 if ("-a".equals(opt)) { 10914 dumpAll = true; 10915 } else if ("-c".equals(opt)) { 10916 dumpClient = true; 10917 } else if ("-h".equals(opt)) { 10918 pw.println("Activity manager dump options:"); 10919 pw.println(" [-a] [-c] [-h] [cmd] ..."); 10920 pw.println(" cmd may be one of:"); 10921 pw.println(" a[ctivities]: activity stack state"); 10922 pw.println(" b[roadcasts] [PACKAGE_NAME] [history [-s]]: broadcast state"); 10923 pw.println(" i[ntents] [PACKAGE_NAME]: pending intent state"); 10924 pw.println(" p[rocesses] [PACKAGE_NAME]: process state"); 10925 pw.println(" o[om]: out of memory management"); 10926 pw.println(" prov[iders] [COMP_SPEC ...]: content provider state"); 10927 pw.println(" provider [COMP_SPEC]: provider client-side state"); 10928 pw.println(" s[ervices] [COMP_SPEC ...]: service state"); 10929 pw.println(" service [COMP_SPEC]: service client-side state"); 10930 pw.println(" package [PACKAGE_NAME]: all state related to given package"); 10931 pw.println(" all: dump all activities"); 10932 pw.println(" top: dump the top activity"); 10933 pw.println(" cmd may also be a COMP_SPEC to dump activities."); 10934 pw.println(" COMP_SPEC may be a component name (com.foo/.myApp),"); 10935 pw.println(" a partial substring in a component name, a"); 10936 pw.println(" hex object identifier."); 10937 pw.println(" -a: include all available server state."); 10938 pw.println(" -c: include client state."); 10939 return; 10940 } else { 10941 pw.println("Unknown argument: " + opt + "; use -h for help"); 10942 } 10943 } 10944 10945 long origId = Binder.clearCallingIdentity(); 10946 boolean more = false; 10947 // Is the caller requesting to dump a particular piece of data? 10948 if (opti < args.length) { 10949 String cmd = args[opti]; 10950 opti++; 10951 if ("activities".equals(cmd) || "a".equals(cmd)) { 10952 synchronized (this) { 10953 dumpActivitiesLocked(fd, pw, args, opti, true, dumpClient, null); 10954 } 10955 } else if ("broadcasts".equals(cmd) || "b".equals(cmd)) { 10956 String[] newArgs; 10957 String name; 10958 if (opti >= args.length) { 10959 name = null; 10960 newArgs = EMPTY_STRING_ARRAY; 10961 } else { 10962 name = args[opti]; 10963 opti++; 10964 newArgs = new String[args.length - opti]; 10965 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 10966 args.length - opti); 10967 } 10968 synchronized (this) { 10969 dumpBroadcastsLocked(fd, pw, args, opti, true, name); 10970 } 10971 } else if ("intents".equals(cmd) || "i".equals(cmd)) { 10972 String[] newArgs; 10973 String name; 10974 if (opti >= args.length) { 10975 name = null; 10976 newArgs = EMPTY_STRING_ARRAY; 10977 } else { 10978 name = args[opti]; 10979 opti++; 10980 newArgs = new String[args.length - opti]; 10981 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 10982 args.length - opti); 10983 } 10984 synchronized (this) { 10985 dumpPendingIntentsLocked(fd, pw, args, opti, true, name); 10986 } 10987 } else if ("processes".equals(cmd) || "p".equals(cmd)) { 10988 String[] newArgs; 10989 String name; 10990 if (opti >= args.length) { 10991 name = null; 10992 newArgs = EMPTY_STRING_ARRAY; 10993 } else { 10994 name = args[opti]; 10995 opti++; 10996 newArgs = new String[args.length - opti]; 10997 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 10998 args.length - opti); 10999 } 11000 synchronized (this) { 11001 dumpProcessesLocked(fd, pw, args, opti, true, name); 11002 } 11003 } else if ("oom".equals(cmd) || "o".equals(cmd)) { 11004 synchronized (this) { 11005 dumpOomLocked(fd, pw, args, opti, true); 11006 } 11007 } else if ("provider".equals(cmd)) { 11008 String[] newArgs; 11009 String name; 11010 if (opti >= args.length) { 11011 name = null; 11012 newArgs = EMPTY_STRING_ARRAY; 11013 } else { 11014 name = args[opti]; 11015 opti++; 11016 newArgs = new String[args.length - opti]; 11017 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, args.length - opti); 11018 } 11019 if (!dumpProvider(fd, pw, name, newArgs, 0, dumpAll)) { 11020 pw.println("No providers match: " + name); 11021 pw.println("Use -h for help."); 11022 } 11023 } else if ("providers".equals(cmd) || "prov".equals(cmd)) { 11024 synchronized (this) { 11025 dumpProvidersLocked(fd, pw, args, opti, true, null); 11026 } 11027 } else if ("service".equals(cmd)) { 11028 String[] newArgs; 11029 String name; 11030 if (opti >= args.length) { 11031 name = null; 11032 newArgs = EMPTY_STRING_ARRAY; 11033 } else { 11034 name = args[opti]; 11035 opti++; 11036 newArgs = new String[args.length - opti]; 11037 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 11038 args.length - opti); 11039 } 11040 if (!mServices.dumpService(fd, pw, name, newArgs, 0, dumpAll)) { 11041 pw.println("No services match: " + name); 11042 pw.println("Use -h for help."); 11043 } 11044 } else if ("package".equals(cmd)) { 11045 String[] newArgs; 11046 if (opti >= args.length) { 11047 pw.println("package: no package name specified"); 11048 pw.println("Use -h for help."); 11049 } else { 11050 dumpPackage = args[opti]; 11051 opti++; 11052 newArgs = new String[args.length - opti]; 11053 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 11054 args.length - opti); 11055 args = newArgs; 11056 opti = 0; 11057 more = true; 11058 } 11059 } else if ("services".equals(cmd) || "s".equals(cmd)) { 11060 synchronized (this) { 11061 mServices.dumpServicesLocked(fd, pw, args, opti, true, dumpClient, null); 11062 } 11063 } else { 11064 // Dumping a single activity? 11065 if (!dumpActivity(fd, pw, cmd, args, opti, dumpAll)) { 11066 pw.println("Bad activity command, or no activities match: " + cmd); 11067 pw.println("Use -h for help."); 11068 } 11069 } 11070 if (!more) { 11071 Binder.restoreCallingIdentity(origId); 11072 return; 11073 } 11074 } 11075 11076 // No piece of data specified, dump everything. 11077 synchronized (this) { 11078 dumpPendingIntentsLocked(fd, pw, args, opti, dumpAll, dumpPackage); 11079 pw.println(); 11080 if (dumpAll) { 11081 pw.println("-------------------------------------------------------------------------------"); 11082 } 11083 dumpBroadcastsLocked(fd, pw, args, opti, dumpAll, dumpPackage); 11084 pw.println(); 11085 if (dumpAll) { 11086 pw.println("-------------------------------------------------------------------------------"); 11087 } 11088 dumpProvidersLocked(fd, pw, args, opti, dumpAll, dumpPackage); 11089 pw.println(); 11090 if (dumpAll) { 11091 pw.println("-------------------------------------------------------------------------------"); 11092 } 11093 mServices.dumpServicesLocked(fd, pw, args, opti, dumpAll, dumpClient, dumpPackage); 11094 pw.println(); 11095 if (dumpAll) { 11096 pw.println("-------------------------------------------------------------------------------"); 11097 } 11098 dumpActivitiesLocked(fd, pw, args, opti, dumpAll, dumpClient, dumpPackage); 11099 pw.println(); 11100 if (dumpAll) { 11101 pw.println("-------------------------------------------------------------------------------"); 11102 } 11103 dumpProcessesLocked(fd, pw, args, opti, dumpAll, dumpPackage); 11104 } 11105 Binder.restoreCallingIdentity(origId); 11106 } 11107 11108 void dumpActivitiesLocked(FileDescriptor fd, PrintWriter pw, String[] args, 11109 int opti, boolean dumpAll, boolean dumpClient, String dumpPackage) { 11110 pw.println("ACTIVITY MANAGER ACTIVITIES (dumpsys activity activities)"); 11111 11112 boolean printedAnything = mStackSupervisor.dumpActivitiesLocked(fd, pw, dumpAll, dumpClient, 11113 dumpPackage); 11114 boolean needSep = printedAnything; 11115 11116 boolean printed = ActivityStackSupervisor.printThisActivity(pw, mFocusedActivity, 11117 dumpPackage, needSep, " mFocusedActivity: "); 11118 if (printed) { 11119 printedAnything = true; 11120 needSep = false; 11121 } 11122 11123 if (dumpPackage == null) { 11124 if (needSep) { 11125 pw.println(); 11126 } 11127 needSep = true; 11128 printedAnything = true; 11129 mStackSupervisor.dump(pw, " "); 11130 } 11131 11132 if (mRecentTasks.size() > 0) { 11133 boolean printedHeader = false; 11134 11135 final int N = mRecentTasks.size(); 11136 for (int i=0; i<N; i++) { 11137 TaskRecord tr = mRecentTasks.get(i); 11138 if (dumpPackage != null) { 11139 if (tr.realActivity == null || 11140 !dumpPackage.equals(tr.realActivity)) { 11141 continue; 11142 } 11143 } 11144 if (!printedHeader) { 11145 if (needSep) { 11146 pw.println(); 11147 } 11148 pw.println(" Recent tasks:"); 11149 printedHeader = true; 11150 printedAnything = true; 11151 } 11152 pw.print(" * Recent #"); pw.print(i); pw.print(": "); 11153 pw.println(tr); 11154 if (dumpAll) { 11155 mRecentTasks.get(i).dump(pw, " "); 11156 } 11157 } 11158 } 11159 11160 if (!printedAnything) { 11161 pw.println(" (nothing)"); 11162 } 11163 } 11164 11165 void dumpProcessesLocked(FileDescriptor fd, PrintWriter pw, String[] args, 11166 int opti, boolean dumpAll, String dumpPackage) { 11167 boolean needSep = false; 11168 boolean printedAnything = false; 11169 int numPers = 0; 11170 11171 pw.println("ACTIVITY MANAGER RUNNING PROCESSES (dumpsys activity processes)"); 11172 11173 if (dumpAll) { 11174 final int NP = mProcessNames.getMap().size(); 11175 for (int ip=0; ip<NP; ip++) { 11176 SparseArray<ProcessRecord> procs = mProcessNames.getMap().valueAt(ip); 11177 final int NA = procs.size(); 11178 for (int ia=0; ia<NA; ia++) { 11179 ProcessRecord r = procs.valueAt(ia); 11180 if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) { 11181 continue; 11182 } 11183 if (!needSep) { 11184 pw.println(" All known processes:"); 11185 needSep = true; 11186 printedAnything = true; 11187 } 11188 pw.print(r.persistent ? " *PERS*" : " *APP*"); 11189 pw.print(" UID "); pw.print(procs.keyAt(ia)); 11190 pw.print(" "); pw.println(r); 11191 r.dump(pw, " "); 11192 if (r.persistent) { 11193 numPers++; 11194 } 11195 } 11196 } 11197 } 11198 11199 if (mIsolatedProcesses.size() > 0) { 11200 boolean printed = false; 11201 for (int i=0; i<mIsolatedProcesses.size(); i++) { 11202 ProcessRecord r = mIsolatedProcesses.valueAt(i); 11203 if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) { 11204 continue; 11205 } 11206 if (!printed) { 11207 if (needSep) { 11208 pw.println(); 11209 } 11210 pw.println(" Isolated process list (sorted by uid):"); 11211 printedAnything = true; 11212 printed = true; 11213 needSep = true; 11214 } 11215 pw.println(String.format("%sIsolated #%2d: %s", 11216 " ", i, r.toString())); 11217 } 11218 } 11219 11220 if (mLruProcesses.size() > 0) { 11221 if (needSep) { 11222 pw.println(); 11223 } 11224 pw.print(" Process LRU list (sorted by oom_adj, "); pw.print(mLruProcesses.size()); 11225 pw.print(" total, non-act at "); 11226 pw.print(mLruProcesses.size()-mLruProcessActivityStart); 11227 pw.print(", non-svc at "); 11228 pw.print(mLruProcesses.size()-mLruProcessServiceStart); 11229 pw.println("):"); 11230 dumpProcessOomList(pw, this, mLruProcesses, " ", "Proc", "PERS", false, dumpPackage); 11231 needSep = true; 11232 printedAnything = true; 11233 } 11234 11235 if (dumpAll || dumpPackage != null) { 11236 synchronized (mPidsSelfLocked) { 11237 boolean printed = false; 11238 for (int i=0; i<mPidsSelfLocked.size(); i++) { 11239 ProcessRecord r = mPidsSelfLocked.valueAt(i); 11240 if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) { 11241 continue; 11242 } 11243 if (!printed) { 11244 if (needSep) pw.println(); 11245 needSep = true; 11246 pw.println(" PID mappings:"); 11247 printed = true; 11248 printedAnything = true; 11249 } 11250 pw.print(" PID #"); pw.print(mPidsSelfLocked.keyAt(i)); 11251 pw.print(": "); pw.println(mPidsSelfLocked.valueAt(i)); 11252 } 11253 } 11254 } 11255 11256 if (mForegroundProcesses.size() > 0) { 11257 synchronized (mPidsSelfLocked) { 11258 boolean printed = false; 11259 for (int i=0; i<mForegroundProcesses.size(); i++) { 11260 ProcessRecord r = mPidsSelfLocked.get( 11261 mForegroundProcesses.valueAt(i).pid); 11262 if (dumpPackage != null && (r == null 11263 || !r.pkgList.containsKey(dumpPackage))) { 11264 continue; 11265 } 11266 if (!printed) { 11267 if (needSep) pw.println(); 11268 needSep = true; 11269 pw.println(" Foreground Processes:"); 11270 printed = true; 11271 printedAnything = true; 11272 } 11273 pw.print(" PID #"); pw.print(mForegroundProcesses.keyAt(i)); 11274 pw.print(": "); pw.println(mForegroundProcesses.valueAt(i)); 11275 } 11276 } 11277 } 11278 11279 if (mPersistentStartingProcesses.size() > 0) { 11280 if (needSep) pw.println(); 11281 needSep = true; 11282 printedAnything = true; 11283 pw.println(" Persisent processes that are starting:"); 11284 dumpProcessList(pw, this, mPersistentStartingProcesses, " ", 11285 "Starting Norm", "Restarting PERS", dumpPackage); 11286 } 11287 11288 if (mRemovedProcesses.size() > 0) { 11289 if (needSep) pw.println(); 11290 needSep = true; 11291 printedAnything = true; 11292 pw.println(" Processes that are being removed:"); 11293 dumpProcessList(pw, this, mRemovedProcesses, " ", 11294 "Removed Norm", "Removed PERS", dumpPackage); 11295 } 11296 11297 if (mProcessesOnHold.size() > 0) { 11298 if (needSep) pw.println(); 11299 needSep = true; 11300 printedAnything = true; 11301 pw.println(" Processes that are on old until the system is ready:"); 11302 dumpProcessList(pw, this, mProcessesOnHold, " ", 11303 "OnHold Norm", "OnHold PERS", dumpPackage); 11304 } 11305 11306 needSep = dumpProcessesToGc(fd, pw, args, opti, needSep, dumpAll, dumpPackage); 11307 11308 if (mProcessCrashTimes.getMap().size() > 0) { 11309 boolean printed = false; 11310 long now = SystemClock.uptimeMillis(); 11311 final ArrayMap<String, SparseArray<Long>> pmap = mProcessCrashTimes.getMap(); 11312 final int NP = pmap.size(); 11313 for (int ip=0; ip<NP; ip++) { 11314 String pname = pmap.keyAt(ip); 11315 SparseArray<Long> uids = pmap.valueAt(ip); 11316 final int N = uids.size(); 11317 for (int i=0; i<N; i++) { 11318 int puid = uids.keyAt(i); 11319 ProcessRecord r = mProcessNames.get(pname, puid); 11320 if (dumpPackage != null && (r == null 11321 || !r.pkgList.containsKey(dumpPackage))) { 11322 continue; 11323 } 11324 if (!printed) { 11325 if (needSep) pw.println(); 11326 needSep = true; 11327 pw.println(" Time since processes crashed:"); 11328 printed = true; 11329 printedAnything = true; 11330 } 11331 pw.print(" Process "); pw.print(pname); 11332 pw.print(" uid "); pw.print(puid); 11333 pw.print(": last crashed "); 11334 TimeUtils.formatDuration(now-uids.valueAt(i), pw); 11335 pw.println(" ago"); 11336 } 11337 } 11338 } 11339 11340 if (mBadProcesses.getMap().size() > 0) { 11341 boolean printed = false; 11342 final ArrayMap<String, SparseArray<BadProcessInfo>> pmap = mBadProcesses.getMap(); 11343 final int NP = pmap.size(); 11344 for (int ip=0; ip<NP; ip++) { 11345 String pname = pmap.keyAt(ip); 11346 SparseArray<BadProcessInfo> uids = pmap.valueAt(ip); 11347 final int N = uids.size(); 11348 for (int i=0; i<N; i++) { 11349 int puid = uids.keyAt(i); 11350 ProcessRecord r = mProcessNames.get(pname, puid); 11351 if (dumpPackage != null && (r == null 11352 || !r.pkgList.containsKey(dumpPackage))) { 11353 continue; 11354 } 11355 if (!printed) { 11356 if (needSep) pw.println(); 11357 needSep = true; 11358 pw.println(" Bad processes:"); 11359 printedAnything = true; 11360 } 11361 BadProcessInfo info = uids.valueAt(i); 11362 pw.print(" Bad process "); pw.print(pname); 11363 pw.print(" uid "); pw.print(puid); 11364 pw.print(": crashed at time "); pw.println(info.time); 11365 if (info.shortMsg != null) { 11366 pw.print(" Short msg: "); pw.println(info.shortMsg); 11367 } 11368 if (info.longMsg != null) { 11369 pw.print(" Long msg: "); pw.println(info.longMsg); 11370 } 11371 if (info.stack != null) { 11372 pw.println(" Stack:"); 11373 int lastPos = 0; 11374 for (int pos=0; pos<info.stack.length(); pos++) { 11375 if (info.stack.charAt(pos) == '\n') { 11376 pw.print(" "); 11377 pw.write(info.stack, lastPos, pos-lastPos); 11378 pw.println(); 11379 lastPos = pos+1; 11380 } 11381 } 11382 if (lastPos < info.stack.length()) { 11383 pw.print(" "); 11384 pw.write(info.stack, lastPos, info.stack.length()-lastPos); 11385 pw.println(); 11386 } 11387 } 11388 } 11389 } 11390 } 11391 11392 if (dumpPackage == null) { 11393 pw.println(); 11394 needSep = false; 11395 pw.println(" mStartedUsers:"); 11396 for (int i=0; i<mStartedUsers.size(); i++) { 11397 UserStartedState uss = mStartedUsers.valueAt(i); 11398 pw.print(" User #"); pw.print(uss.mHandle.getIdentifier()); 11399 pw.print(": "); uss.dump("", pw); 11400 } 11401 pw.print(" mStartedUserArray: ["); 11402 for (int i=0; i<mStartedUserArray.length; i++) { 11403 if (i > 0) pw.print(", "); 11404 pw.print(mStartedUserArray[i]); 11405 } 11406 pw.println("]"); 11407 pw.print(" mUserLru: ["); 11408 for (int i=0; i<mUserLru.size(); i++) { 11409 if (i > 0) pw.print(", "); 11410 pw.print(mUserLru.get(i)); 11411 } 11412 pw.println("]"); 11413 if (dumpAll) { 11414 pw.print(" mStartedUserArray: "); pw.println(Arrays.toString(mStartedUserArray)); 11415 } 11416 } 11417 if (mHomeProcess != null && (dumpPackage == null 11418 || mHomeProcess.pkgList.containsKey(dumpPackage))) { 11419 if (needSep) { 11420 pw.println(); 11421 needSep = false; 11422 } 11423 pw.println(" mHomeProcess: " + mHomeProcess); 11424 } 11425 if (mPreviousProcess != null && (dumpPackage == null 11426 || mPreviousProcess.pkgList.containsKey(dumpPackage))) { 11427 if (needSep) { 11428 pw.println(); 11429 needSep = false; 11430 } 11431 pw.println(" mPreviousProcess: " + mPreviousProcess); 11432 } 11433 if (dumpAll) { 11434 StringBuilder sb = new StringBuilder(128); 11435 sb.append(" mPreviousProcessVisibleTime: "); 11436 TimeUtils.formatDuration(mPreviousProcessVisibleTime, sb); 11437 pw.println(sb); 11438 } 11439 if (mHeavyWeightProcess != null && (dumpPackage == null 11440 || mHeavyWeightProcess.pkgList.containsKey(dumpPackage))) { 11441 if (needSep) { 11442 pw.println(); 11443 needSep = false; 11444 } 11445 pw.println(" mHeavyWeightProcess: " + mHeavyWeightProcess); 11446 } 11447 if (dumpPackage == null) { 11448 pw.println(" mConfiguration: " + mConfiguration); 11449 } 11450 if (dumpAll) { 11451 pw.println(" mConfigWillChange: " + getFocusedStack().mConfigWillChange); 11452 if (mCompatModePackages.getPackages().size() > 0) { 11453 boolean printed = false; 11454 for (Map.Entry<String, Integer> entry 11455 : mCompatModePackages.getPackages().entrySet()) { 11456 String pkg = entry.getKey(); 11457 int mode = entry.getValue(); 11458 if (dumpPackage != null && !dumpPackage.equals(pkg)) { 11459 continue; 11460 } 11461 if (!printed) { 11462 pw.println(" mScreenCompatPackages:"); 11463 printed = true; 11464 } 11465 pw.print(" "); pw.print(pkg); pw.print(": "); 11466 pw.print(mode); pw.println(); 11467 } 11468 } 11469 } 11470 if (dumpPackage == null) { 11471 if (mSleeping || mWentToSleep || mLockScreenShown) { 11472 pw.println(" mSleeping=" + mSleeping + " mWentToSleep=" + mWentToSleep 11473 + " mLockScreenShown " + mLockScreenShown); 11474 } 11475 if (mShuttingDown || mRunningVoice) { 11476 pw.print(" mShuttingDown=" + mShuttingDown + " mRunningVoice=" + mRunningVoice); 11477 } 11478 } 11479 if (mDebugApp != null || mOrigDebugApp != null || mDebugTransient 11480 || mOrigWaitForDebugger) { 11481 if (dumpPackage == null || dumpPackage.equals(mDebugApp) 11482 || dumpPackage.equals(mOrigDebugApp)) { 11483 if (needSep) { 11484 pw.println(); 11485 needSep = false; 11486 } 11487 pw.println(" mDebugApp=" + mDebugApp + "/orig=" + mOrigDebugApp 11488 + " mDebugTransient=" + mDebugTransient 11489 + " mOrigWaitForDebugger=" + mOrigWaitForDebugger); 11490 } 11491 } 11492 if (mOpenGlTraceApp != null) { 11493 if (dumpPackage == null || dumpPackage.equals(mOpenGlTraceApp)) { 11494 if (needSep) { 11495 pw.println(); 11496 needSep = false; 11497 } 11498 pw.println(" mOpenGlTraceApp=" + mOpenGlTraceApp); 11499 } 11500 } 11501 if (mProfileApp != null || mProfileProc != null || mProfileFile != null 11502 || mProfileFd != null) { 11503 if (dumpPackage == null || dumpPackage.equals(mProfileApp)) { 11504 if (needSep) { 11505 pw.println(); 11506 needSep = false; 11507 } 11508 pw.println(" mProfileApp=" + mProfileApp + " mProfileProc=" + mProfileProc); 11509 pw.println(" mProfileFile=" + mProfileFile + " mProfileFd=" + mProfileFd); 11510 pw.println(" mProfileType=" + mProfileType + " mAutoStopProfiler=" 11511 + mAutoStopProfiler); 11512 } 11513 } 11514 if (dumpPackage == null) { 11515 if (mAlwaysFinishActivities || mController != null) { 11516 pw.println(" mAlwaysFinishActivities=" + mAlwaysFinishActivities 11517 + " mController=" + mController); 11518 } 11519 if (dumpAll) { 11520 pw.println(" Total persistent processes: " + numPers); 11521 pw.println(" mProcessesReady=" + mProcessesReady 11522 + " mSystemReady=" + mSystemReady); 11523 pw.println(" mBooting=" + mBooting 11524 + " mBooted=" + mBooted 11525 + " mFactoryTest=" + mFactoryTest); 11526 pw.print(" mLastPowerCheckRealtime="); 11527 TimeUtils.formatDuration(mLastPowerCheckRealtime, pw); 11528 pw.println(""); 11529 pw.print(" mLastPowerCheckUptime="); 11530 TimeUtils.formatDuration(mLastPowerCheckUptime, pw); 11531 pw.println(""); 11532 pw.println(" mGoingToSleep=" + mStackSupervisor.mGoingToSleep); 11533 pw.println(" mLaunchingActivity=" + mStackSupervisor.mLaunchingActivity); 11534 pw.println(" mAdjSeq=" + mAdjSeq + " mLruSeq=" + mLruSeq); 11535 pw.println(" mNumNonCachedProcs=" + mNumNonCachedProcs 11536 + " (" + mLruProcesses.size() + " total)" 11537 + " mNumCachedHiddenProcs=" + mNumCachedHiddenProcs 11538 + " mNumServiceProcs=" + mNumServiceProcs 11539 + " mNewNumServiceProcs=" + mNewNumServiceProcs); 11540 pw.println(" mAllowLowerMemLevel=" + mAllowLowerMemLevel 11541 + " mLastMemoryLevel" + mLastMemoryLevel 11542 + " mLastNumProcesses" + mLastNumProcesses); 11543 long now = SystemClock.uptimeMillis(); 11544 pw.print(" mLastIdleTime="); 11545 TimeUtils.formatDuration(now, mLastIdleTime, pw); 11546 pw.print(" mLowRamSinceLastIdle="); 11547 TimeUtils.formatDuration(getLowRamTimeSinceIdle(now), pw); 11548 pw.println(); 11549 } 11550 } 11551 11552 if (!printedAnything) { 11553 pw.println(" (nothing)"); 11554 } 11555 } 11556 11557 boolean dumpProcessesToGc(FileDescriptor fd, PrintWriter pw, String[] args, 11558 int opti, boolean needSep, boolean dumpAll, String dumpPackage) { 11559 if (mProcessesToGc.size() > 0) { 11560 boolean printed = false; 11561 long now = SystemClock.uptimeMillis(); 11562 for (int i=0; i<mProcessesToGc.size(); i++) { 11563 ProcessRecord proc = mProcessesToGc.get(i); 11564 if (dumpPackage != null && !dumpPackage.equals(proc.info.packageName)) { 11565 continue; 11566 } 11567 if (!printed) { 11568 if (needSep) pw.println(); 11569 needSep = true; 11570 pw.println(" Processes that are waiting to GC:"); 11571 printed = true; 11572 } 11573 pw.print(" Process "); pw.println(proc); 11574 pw.print(" lowMem="); pw.print(proc.reportLowMemory); 11575 pw.print(", last gced="); 11576 pw.print(now-proc.lastRequestedGc); 11577 pw.print(" ms ago, last lowMem="); 11578 pw.print(now-proc.lastLowMemory); 11579 pw.println(" ms ago"); 11580 11581 } 11582 } 11583 return needSep; 11584 } 11585 11586 void printOomLevel(PrintWriter pw, String name, int adj) { 11587 pw.print(" "); 11588 if (adj >= 0) { 11589 pw.print(' '); 11590 if (adj < 10) pw.print(' '); 11591 } else { 11592 if (adj > -10) pw.print(' '); 11593 } 11594 pw.print(adj); 11595 pw.print(": "); 11596 pw.print(name); 11597 pw.print(" ("); 11598 pw.print(mProcessList.getMemLevel(adj)/1024); 11599 pw.println(" kB)"); 11600 } 11601 11602 boolean dumpOomLocked(FileDescriptor fd, PrintWriter pw, String[] args, 11603 int opti, boolean dumpAll) { 11604 boolean needSep = false; 11605 11606 if (mLruProcesses.size() > 0) { 11607 if (needSep) pw.println(); 11608 needSep = true; 11609 pw.println(" OOM levels:"); 11610 printOomLevel(pw, "SYSTEM_ADJ", ProcessList.SYSTEM_ADJ); 11611 printOomLevel(pw, "PERSISTENT_PROC_ADJ", ProcessList.PERSISTENT_PROC_ADJ); 11612 printOomLevel(pw, "FOREGROUND_APP_ADJ", ProcessList.FOREGROUND_APP_ADJ); 11613 printOomLevel(pw, "VISIBLE_APP_ADJ", ProcessList.VISIBLE_APP_ADJ); 11614 printOomLevel(pw, "PERCEPTIBLE_APP_ADJ", ProcessList.PERCEPTIBLE_APP_ADJ); 11615 printOomLevel(pw, "BACKUP_APP_ADJ", ProcessList.BACKUP_APP_ADJ); 11616 printOomLevel(pw, "HEAVY_WEIGHT_APP_ADJ", ProcessList.HEAVY_WEIGHT_APP_ADJ); 11617 printOomLevel(pw, "SERVICE_ADJ", ProcessList.SERVICE_ADJ); 11618 printOomLevel(pw, "HOME_APP_ADJ", ProcessList.HOME_APP_ADJ); 11619 printOomLevel(pw, "PREVIOUS_APP_ADJ", ProcessList.PREVIOUS_APP_ADJ); 11620 printOomLevel(pw, "SERVICE_B_ADJ", ProcessList.SERVICE_B_ADJ); 11621 printOomLevel(pw, "CACHED_APP_MIN_ADJ", ProcessList.CACHED_APP_MIN_ADJ); 11622 printOomLevel(pw, "CACHED_APP_MAX_ADJ", ProcessList.CACHED_APP_MAX_ADJ); 11623 11624 if (needSep) pw.println(); 11625 pw.print(" Process OOM control ("); pw.print(mLruProcesses.size()); 11626 pw.print(" total, non-act at "); 11627 pw.print(mLruProcesses.size()-mLruProcessActivityStart); 11628 pw.print(", non-svc at "); 11629 pw.print(mLruProcesses.size()-mLruProcessServiceStart); 11630 pw.println("):"); 11631 dumpProcessOomList(pw, this, mLruProcesses, " ", "Proc", "PERS", true, null); 11632 needSep = true; 11633 } 11634 11635 dumpProcessesToGc(fd, pw, args, opti, needSep, dumpAll, null); 11636 11637 pw.println(); 11638 pw.println(" mHomeProcess: " + mHomeProcess); 11639 pw.println(" mPreviousProcess: " + mPreviousProcess); 11640 if (mHeavyWeightProcess != null) { 11641 pw.println(" mHeavyWeightProcess: " + mHeavyWeightProcess); 11642 } 11643 11644 return true; 11645 } 11646 11647 /** 11648 * There are three ways to call this: 11649 * - no provider specified: dump all the providers 11650 * - a flattened component name that matched an existing provider was specified as the 11651 * first arg: dump that one provider 11652 * - the first arg isn't the flattened component name of an existing provider: 11653 * dump all providers whose component contains the first arg as a substring 11654 */ 11655 protected boolean dumpProvider(FileDescriptor fd, PrintWriter pw, String name, String[] args, 11656 int opti, boolean dumpAll) { 11657 return mProviderMap.dumpProvider(fd, pw, name, args, opti, dumpAll); 11658 } 11659 11660 static class ItemMatcher { 11661 ArrayList<ComponentName> components; 11662 ArrayList<String> strings; 11663 ArrayList<Integer> objects; 11664 boolean all; 11665 11666 ItemMatcher() { 11667 all = true; 11668 } 11669 11670 void build(String name) { 11671 ComponentName componentName = ComponentName.unflattenFromString(name); 11672 if (componentName != null) { 11673 if (components == null) { 11674 components = new ArrayList<ComponentName>(); 11675 } 11676 components.add(componentName); 11677 all = false; 11678 } else { 11679 int objectId = 0; 11680 // Not a '/' separated full component name; maybe an object ID? 11681 try { 11682 objectId = Integer.parseInt(name, 16); 11683 if (objects == null) { 11684 objects = new ArrayList<Integer>(); 11685 } 11686 objects.add(objectId); 11687 all = false; 11688 } catch (RuntimeException e) { 11689 // Not an integer; just do string match. 11690 if (strings == null) { 11691 strings = new ArrayList<String>(); 11692 } 11693 strings.add(name); 11694 all = false; 11695 } 11696 } 11697 } 11698 11699 int build(String[] args, int opti) { 11700 for (; opti<args.length; opti++) { 11701 String name = args[opti]; 11702 if ("--".equals(name)) { 11703 return opti+1; 11704 } 11705 build(name); 11706 } 11707 return opti; 11708 } 11709 11710 boolean match(Object object, ComponentName comp) { 11711 if (all) { 11712 return true; 11713 } 11714 if (components != null) { 11715 for (int i=0; i<components.size(); i++) { 11716 if (components.get(i).equals(comp)) { 11717 return true; 11718 } 11719 } 11720 } 11721 if (objects != null) { 11722 for (int i=0; i<objects.size(); i++) { 11723 if (System.identityHashCode(object) == objects.get(i)) { 11724 return true; 11725 } 11726 } 11727 } 11728 if (strings != null) { 11729 String flat = comp.flattenToString(); 11730 for (int i=0; i<strings.size(); i++) { 11731 if (flat.contains(strings.get(i))) { 11732 return true; 11733 } 11734 } 11735 } 11736 return false; 11737 } 11738 } 11739 11740 /** 11741 * There are three things that cmd can be: 11742 * - a flattened component name that matches an existing activity 11743 * - the cmd arg isn't the flattened component name of an existing activity: 11744 * dump all activity whose component contains the cmd as a substring 11745 * - A hex number of the ActivityRecord object instance. 11746 */ 11747 protected boolean dumpActivity(FileDescriptor fd, PrintWriter pw, String name, String[] args, 11748 int opti, boolean dumpAll) { 11749 ArrayList<ActivityRecord> activities; 11750 11751 synchronized (this) { 11752 activities = mStackSupervisor.getDumpActivitiesLocked(name); 11753 } 11754 11755 if (activities.size() <= 0) { 11756 return false; 11757 } 11758 11759 String[] newArgs = new String[args.length - opti]; 11760 System.arraycopy(args, opti, newArgs, 0, args.length - opti); 11761 11762 TaskRecord lastTask = null; 11763 boolean needSep = false; 11764 for (int i=activities.size()-1; i>=0; i--) { 11765 ActivityRecord r = activities.get(i); 11766 if (needSep) { 11767 pw.println(); 11768 } 11769 needSep = true; 11770 synchronized (this) { 11771 if (lastTask != r.task) { 11772 lastTask = r.task; 11773 pw.print("TASK "); pw.print(lastTask.affinity); 11774 pw.print(" id="); pw.println(lastTask.taskId); 11775 if (dumpAll) { 11776 lastTask.dump(pw, " "); 11777 } 11778 } 11779 } 11780 dumpActivity(" ", fd, pw, activities.get(i), newArgs, dumpAll); 11781 } 11782 return true; 11783 } 11784 11785 /** 11786 * Invokes IApplicationThread.dumpActivity() on the thread of the specified activity if 11787 * there is a thread associated with the activity. 11788 */ 11789 private void dumpActivity(String prefix, FileDescriptor fd, PrintWriter pw, 11790 final ActivityRecord r, String[] args, boolean dumpAll) { 11791 String innerPrefix = prefix + " "; 11792 synchronized (this) { 11793 pw.print(prefix); pw.print("ACTIVITY "); pw.print(r.shortComponentName); 11794 pw.print(" "); pw.print(Integer.toHexString(System.identityHashCode(r))); 11795 pw.print(" pid="); 11796 if (r.app != null) pw.println(r.app.pid); 11797 else pw.println("(not running)"); 11798 if (dumpAll) { 11799 r.dump(pw, innerPrefix); 11800 } 11801 } 11802 if (r.app != null && r.app.thread != null) { 11803 // flush anything that is already in the PrintWriter since the thread is going 11804 // to write to the file descriptor directly 11805 pw.flush(); 11806 try { 11807 TransferPipe tp = new TransferPipe(); 11808 try { 11809 r.app.thread.dumpActivity(tp.getWriteFd().getFileDescriptor(), 11810 r.appToken, innerPrefix, args); 11811 tp.go(fd); 11812 } finally { 11813 tp.kill(); 11814 } 11815 } catch (IOException e) { 11816 pw.println(innerPrefix + "Failure while dumping the activity: " + e); 11817 } catch (RemoteException e) { 11818 pw.println(innerPrefix + "Got a RemoteException while dumping the activity"); 11819 } 11820 } 11821 } 11822 11823 void dumpBroadcastsLocked(FileDescriptor fd, PrintWriter pw, String[] args, 11824 int opti, boolean dumpAll, String dumpPackage) { 11825 boolean needSep = false; 11826 boolean onlyHistory = false; 11827 boolean printedAnything = false; 11828 11829 if ("history".equals(dumpPackage)) { 11830 if (opti < args.length && "-s".equals(args[opti])) { 11831 dumpAll = false; 11832 } 11833 onlyHistory = true; 11834 dumpPackage = null; 11835 } 11836 11837 pw.println("ACTIVITY MANAGER BROADCAST STATE (dumpsys activity broadcasts)"); 11838 if (!onlyHistory && dumpAll) { 11839 if (mRegisteredReceivers.size() > 0) { 11840 boolean printed = false; 11841 Iterator it = mRegisteredReceivers.values().iterator(); 11842 while (it.hasNext()) { 11843 ReceiverList r = (ReceiverList)it.next(); 11844 if (dumpPackage != null && (r.app == null || 11845 !dumpPackage.equals(r.app.info.packageName))) { 11846 continue; 11847 } 11848 if (!printed) { 11849 pw.println(" Registered Receivers:"); 11850 needSep = true; 11851 printed = true; 11852 printedAnything = true; 11853 } 11854 pw.print(" * "); pw.println(r); 11855 r.dump(pw, " "); 11856 } 11857 } 11858 11859 if (mReceiverResolver.dump(pw, needSep ? 11860 "\n Receiver Resolver Table:" : " Receiver Resolver Table:", 11861 " ", dumpPackage, false)) { 11862 needSep = true; 11863 printedAnything = true; 11864 } 11865 } 11866 11867 for (BroadcastQueue q : mBroadcastQueues) { 11868 needSep = q.dumpLocked(fd, pw, args, opti, dumpAll, dumpPackage, needSep); 11869 printedAnything |= needSep; 11870 } 11871 11872 needSep = true; 11873 11874 if (!onlyHistory && mStickyBroadcasts != null && dumpPackage == null) { 11875 for (int user=0; user<mStickyBroadcasts.size(); user++) { 11876 if (needSep) { 11877 pw.println(); 11878 } 11879 needSep = true; 11880 printedAnything = true; 11881 pw.print(" Sticky broadcasts for user "); 11882 pw.print(mStickyBroadcasts.keyAt(user)); pw.println(":"); 11883 StringBuilder sb = new StringBuilder(128); 11884 for (Map.Entry<String, ArrayList<Intent>> ent 11885 : mStickyBroadcasts.valueAt(user).entrySet()) { 11886 pw.print(" * Sticky action "); pw.print(ent.getKey()); 11887 if (dumpAll) { 11888 pw.println(":"); 11889 ArrayList<Intent> intents = ent.getValue(); 11890 final int N = intents.size(); 11891 for (int i=0; i<N; i++) { 11892 sb.setLength(0); 11893 sb.append(" Intent: "); 11894 intents.get(i).toShortString(sb, false, true, false, false); 11895 pw.println(sb.toString()); 11896 Bundle bundle = intents.get(i).getExtras(); 11897 if (bundle != null) { 11898 pw.print(" "); 11899 pw.println(bundle.toString()); 11900 } 11901 } 11902 } else { 11903 pw.println(""); 11904 } 11905 } 11906 } 11907 } 11908 11909 if (!onlyHistory && dumpAll) { 11910 pw.println(); 11911 for (BroadcastQueue queue : mBroadcastQueues) { 11912 pw.println(" mBroadcastsScheduled [" + queue.mQueueName + "]=" 11913 + queue.mBroadcastsScheduled); 11914 } 11915 pw.println(" mHandler:"); 11916 mHandler.dump(new PrintWriterPrinter(pw), " "); 11917 needSep = true; 11918 printedAnything = true; 11919 } 11920 11921 if (!printedAnything) { 11922 pw.println(" (nothing)"); 11923 } 11924 } 11925 11926 void dumpProvidersLocked(FileDescriptor fd, PrintWriter pw, String[] args, 11927 int opti, boolean dumpAll, String dumpPackage) { 11928 boolean needSep; 11929 boolean printedAnything = false; 11930 11931 ItemMatcher matcher = new ItemMatcher(); 11932 matcher.build(args, opti); 11933 11934 pw.println("ACTIVITY MANAGER CONTENT PROVIDERS (dumpsys activity providers)"); 11935 11936 needSep = mProviderMap.dumpProvidersLocked(pw, dumpAll, dumpPackage); 11937 printedAnything |= needSep; 11938 11939 if (mLaunchingProviders.size() > 0) { 11940 boolean printed = false; 11941 for (int i=mLaunchingProviders.size()-1; i>=0; i--) { 11942 ContentProviderRecord r = mLaunchingProviders.get(i); 11943 if (dumpPackage != null && !dumpPackage.equals(r.name.getPackageName())) { 11944 continue; 11945 } 11946 if (!printed) { 11947 if (needSep) pw.println(); 11948 needSep = true; 11949 pw.println(" Launching content providers:"); 11950 printed = true; 11951 printedAnything = true; 11952 } 11953 pw.print(" Launching #"); pw.print(i); pw.print(": "); 11954 pw.println(r); 11955 } 11956 } 11957 11958 if (mGrantedUriPermissions.size() > 0) { 11959 boolean printed = false; 11960 int dumpUid = -2; 11961 if (dumpPackage != null) { 11962 try { 11963 dumpUid = mContext.getPackageManager().getPackageUid(dumpPackage, 0); 11964 } catch (NameNotFoundException e) { 11965 dumpUid = -1; 11966 } 11967 } 11968 for (int i=0; i<mGrantedUriPermissions.size(); i++) { 11969 int uid = mGrantedUriPermissions.keyAt(i); 11970 if (dumpUid >= -1 && UserHandle.getAppId(uid) != dumpUid) { 11971 continue; 11972 } 11973 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i); 11974 if (!printed) { 11975 if (needSep) pw.println(); 11976 needSep = true; 11977 pw.println(" Granted Uri Permissions:"); 11978 printed = true; 11979 printedAnything = true; 11980 } 11981 pw.print(" * UID "); pw.print(uid); pw.println(" holds:"); 11982 for (UriPermission perm : perms.values()) { 11983 pw.print(" "); pw.println(perm); 11984 if (dumpAll) { 11985 perm.dump(pw, " "); 11986 } 11987 } 11988 } 11989 } 11990 11991 if (!printedAnything) { 11992 pw.println(" (nothing)"); 11993 } 11994 } 11995 11996 void dumpPendingIntentsLocked(FileDescriptor fd, PrintWriter pw, String[] args, 11997 int opti, boolean dumpAll, String dumpPackage) { 11998 boolean printed = false; 11999 12000 pw.println("ACTIVITY MANAGER PENDING INTENTS (dumpsys activity intents)"); 12001 12002 if (mIntentSenderRecords.size() > 0) { 12003 Iterator<WeakReference<PendingIntentRecord>> it 12004 = mIntentSenderRecords.values().iterator(); 12005 while (it.hasNext()) { 12006 WeakReference<PendingIntentRecord> ref = it.next(); 12007 PendingIntentRecord rec = ref != null ? ref.get(): null; 12008 if (dumpPackage != null && (rec == null 12009 || !dumpPackage.equals(rec.key.packageName))) { 12010 continue; 12011 } 12012 printed = true; 12013 if (rec != null) { 12014 pw.print(" * "); pw.println(rec); 12015 if (dumpAll) { 12016 rec.dump(pw, " "); 12017 } 12018 } else { 12019 pw.print(" * "); pw.println(ref); 12020 } 12021 } 12022 } 12023 12024 if (!printed) { 12025 pw.println(" (nothing)"); 12026 } 12027 } 12028 12029 private static final int dumpProcessList(PrintWriter pw, 12030 ActivityManagerService service, List list, 12031 String prefix, String normalLabel, String persistentLabel, 12032 String dumpPackage) { 12033 int numPers = 0; 12034 final int N = list.size()-1; 12035 for (int i=N; i>=0; i--) { 12036 ProcessRecord r = (ProcessRecord)list.get(i); 12037 if (dumpPackage != null && !dumpPackage.equals(r.info.packageName)) { 12038 continue; 12039 } 12040 pw.println(String.format("%s%s #%2d: %s", 12041 prefix, (r.persistent ? persistentLabel : normalLabel), 12042 i, r.toString())); 12043 if (r.persistent) { 12044 numPers++; 12045 } 12046 } 12047 return numPers; 12048 } 12049 12050 private static final boolean dumpProcessOomList(PrintWriter pw, 12051 ActivityManagerService service, List<ProcessRecord> origList, 12052 String prefix, String normalLabel, String persistentLabel, 12053 boolean inclDetails, String dumpPackage) { 12054 12055 ArrayList<Pair<ProcessRecord, Integer>> list 12056 = new ArrayList<Pair<ProcessRecord, Integer>>(origList.size()); 12057 for (int i=0; i<origList.size(); i++) { 12058 ProcessRecord r = origList.get(i); 12059 if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) { 12060 continue; 12061 } 12062 list.add(new Pair<ProcessRecord, Integer>(origList.get(i), i)); 12063 } 12064 12065 if (list.size() <= 0) { 12066 return false; 12067 } 12068 12069 Comparator<Pair<ProcessRecord, Integer>> comparator 12070 = new Comparator<Pair<ProcessRecord, Integer>>() { 12071 @Override 12072 public int compare(Pair<ProcessRecord, Integer> object1, 12073 Pair<ProcessRecord, Integer> object2) { 12074 if (object1.first.setAdj != object2.first.setAdj) { 12075 return object1.first.setAdj > object2.first.setAdj ? -1 : 1; 12076 } 12077 if (object1.second.intValue() != object2.second.intValue()) { 12078 return object1.second.intValue() > object2.second.intValue() ? -1 : 1; 12079 } 12080 return 0; 12081 } 12082 }; 12083 12084 Collections.sort(list, comparator); 12085 12086 final long curRealtime = SystemClock.elapsedRealtime(); 12087 final long realtimeSince = curRealtime - service.mLastPowerCheckRealtime; 12088 final long curUptime = SystemClock.uptimeMillis(); 12089 final long uptimeSince = curUptime - service.mLastPowerCheckUptime; 12090 12091 for (int i=list.size()-1; i>=0; i--) { 12092 ProcessRecord r = list.get(i).first; 12093 String oomAdj = ProcessList.makeOomAdjString(r.setAdj); 12094 char schedGroup; 12095 switch (r.setSchedGroup) { 12096 case Process.THREAD_GROUP_BG_NONINTERACTIVE: 12097 schedGroup = 'B'; 12098 break; 12099 case Process.THREAD_GROUP_DEFAULT: 12100 schedGroup = 'F'; 12101 break; 12102 default: 12103 schedGroup = '?'; 12104 break; 12105 } 12106 char foreground; 12107 if (r.foregroundActivities) { 12108 foreground = 'A'; 12109 } else if (r.foregroundServices) { 12110 foreground = 'S'; 12111 } else { 12112 foreground = ' '; 12113 } 12114 String procState = ProcessList.makeProcStateString(r.curProcState); 12115 pw.print(prefix); 12116 pw.print(r.persistent ? persistentLabel : normalLabel); 12117 pw.print(" #"); 12118 int num = (origList.size()-1)-list.get(i).second; 12119 if (num < 10) pw.print(' '); 12120 pw.print(num); 12121 pw.print(": "); 12122 pw.print(oomAdj); 12123 pw.print(' '); 12124 pw.print(schedGroup); 12125 pw.print('/'); 12126 pw.print(foreground); 12127 pw.print('/'); 12128 pw.print(procState); 12129 pw.print(" trm:"); 12130 if (r.trimMemoryLevel < 10) pw.print(' '); 12131 pw.print(r.trimMemoryLevel); 12132 pw.print(' '); 12133 pw.print(r.toShortString()); 12134 pw.print(" ("); 12135 pw.print(r.adjType); 12136 pw.println(')'); 12137 if (r.adjSource != null || r.adjTarget != null) { 12138 pw.print(prefix); 12139 pw.print(" "); 12140 if (r.adjTarget instanceof ComponentName) { 12141 pw.print(((ComponentName)r.adjTarget).flattenToShortString()); 12142 } else if (r.adjTarget != null) { 12143 pw.print(r.adjTarget.toString()); 12144 } else { 12145 pw.print("{null}"); 12146 } 12147 pw.print("<="); 12148 if (r.adjSource instanceof ProcessRecord) { 12149 pw.print("Proc{"); 12150 pw.print(((ProcessRecord)r.adjSource).toShortString()); 12151 pw.println("}"); 12152 } else if (r.adjSource != null) { 12153 pw.println(r.adjSource.toString()); 12154 } else { 12155 pw.println("{null}"); 12156 } 12157 } 12158 if (inclDetails) { 12159 pw.print(prefix); 12160 pw.print(" "); 12161 pw.print("oom: max="); pw.print(r.maxAdj); 12162 pw.print(" curRaw="); pw.print(r.curRawAdj); 12163 pw.print(" setRaw="); pw.print(r.setRawAdj); 12164 pw.print(" cur="); pw.print(r.curAdj); 12165 pw.print(" set="); pw.println(r.setAdj); 12166 pw.print(prefix); 12167 pw.print(" "); 12168 pw.print("state: cur="); pw.print(ProcessList.makeProcStateString(r.curProcState)); 12169 pw.print(" set="); pw.print(ProcessList.makeProcStateString(r.setProcState)); 12170 pw.print(" lastPss="); pw.print(r.lastPss); 12171 pw.print(" lastCachedPss="); pw.println(r.lastCachedPss); 12172 pw.print(prefix); 12173 pw.print(" "); 12174 pw.print("keeping="); pw.print(r.keeping); 12175 pw.print(" cached="); pw.print(r.cached); 12176 pw.print(" empty="); pw.print(r.empty); 12177 pw.print(" hasAboveClient="); pw.println(r.hasAboveClient); 12178 12179 if (!r.keeping) { 12180 if (r.lastWakeTime != 0) { 12181 long wtime; 12182 BatteryStatsImpl stats = service.mBatteryStatsService.getActiveStatistics(); 12183 synchronized (stats) { 12184 wtime = stats.getProcessWakeTime(r.info.uid, 12185 r.pid, curRealtime); 12186 } 12187 long timeUsed = wtime - r.lastWakeTime; 12188 pw.print(prefix); 12189 pw.print(" "); 12190 pw.print("keep awake over "); 12191 TimeUtils.formatDuration(realtimeSince, pw); 12192 pw.print(" used "); 12193 TimeUtils.formatDuration(timeUsed, pw); 12194 pw.print(" ("); 12195 pw.print((timeUsed*100)/realtimeSince); 12196 pw.println("%)"); 12197 } 12198 if (r.lastCpuTime != 0) { 12199 long timeUsed = r.curCpuTime - r.lastCpuTime; 12200 pw.print(prefix); 12201 pw.print(" "); 12202 pw.print("run cpu over "); 12203 TimeUtils.formatDuration(uptimeSince, pw); 12204 pw.print(" used "); 12205 TimeUtils.formatDuration(timeUsed, pw); 12206 pw.print(" ("); 12207 pw.print((timeUsed*100)/uptimeSince); 12208 pw.println("%)"); 12209 } 12210 } 12211 } 12212 } 12213 return true; 12214 } 12215 12216 ArrayList<ProcessRecord> collectProcesses(PrintWriter pw, int start, String[] args) { 12217 ArrayList<ProcessRecord> procs; 12218 synchronized (this) { 12219 if (args != null && args.length > start 12220 && args[start].charAt(0) != '-') { 12221 procs = new ArrayList<ProcessRecord>(); 12222 int pid = -1; 12223 try { 12224 pid = Integer.parseInt(args[start]); 12225 } catch (NumberFormatException e) { 12226 } 12227 for (int i=mLruProcesses.size()-1; i>=0; i--) { 12228 ProcessRecord proc = mLruProcesses.get(i); 12229 if (proc.pid == pid) { 12230 procs.add(proc); 12231 } else if (proc.processName.equals(args[start])) { 12232 procs.add(proc); 12233 } 12234 } 12235 if (procs.size() <= 0) { 12236 return null; 12237 } 12238 } else { 12239 procs = new ArrayList<ProcessRecord>(mLruProcesses); 12240 } 12241 } 12242 return procs; 12243 } 12244 12245 final void dumpGraphicsHardwareUsage(FileDescriptor fd, 12246 PrintWriter pw, String[] args) { 12247 ArrayList<ProcessRecord> procs = collectProcesses(pw, 0, args); 12248 if (procs == null) { 12249 pw.println("No process found for: " + args[0]); 12250 return; 12251 } 12252 12253 long uptime = SystemClock.uptimeMillis(); 12254 long realtime = SystemClock.elapsedRealtime(); 12255 pw.println("Applications Graphics Acceleration Info:"); 12256 pw.println("Uptime: " + uptime + " Realtime: " + realtime); 12257 12258 for (int i = procs.size() - 1 ; i >= 0 ; i--) { 12259 ProcessRecord r = procs.get(i); 12260 if (r.thread != null) { 12261 pw.println("\n** Graphics info for pid " + r.pid + " [" + r.processName + "] **"); 12262 pw.flush(); 12263 try { 12264 TransferPipe tp = new TransferPipe(); 12265 try { 12266 r.thread.dumpGfxInfo(tp.getWriteFd().getFileDescriptor(), args); 12267 tp.go(fd); 12268 } finally { 12269 tp.kill(); 12270 } 12271 } catch (IOException e) { 12272 pw.println("Failure while dumping the app: " + r); 12273 pw.flush(); 12274 } catch (RemoteException e) { 12275 pw.println("Got a RemoteException while dumping the app " + r); 12276 pw.flush(); 12277 } 12278 } 12279 } 12280 } 12281 12282 final void dumpDbInfo(FileDescriptor fd, PrintWriter pw, String[] args) { 12283 ArrayList<ProcessRecord> procs = collectProcesses(pw, 0, args); 12284 if (procs == null) { 12285 pw.println("No process found for: " + args[0]); 12286 return; 12287 } 12288 12289 pw.println("Applications Database Info:"); 12290 12291 for (int i = procs.size() - 1 ; i >= 0 ; i--) { 12292 ProcessRecord r = procs.get(i); 12293 if (r.thread != null) { 12294 pw.println("\n** Database info for pid " + r.pid + " [" + r.processName + "] **"); 12295 pw.flush(); 12296 try { 12297 TransferPipe tp = new TransferPipe(); 12298 try { 12299 r.thread.dumpDbInfo(tp.getWriteFd().getFileDescriptor(), args); 12300 tp.go(fd); 12301 } finally { 12302 tp.kill(); 12303 } 12304 } catch (IOException e) { 12305 pw.println("Failure while dumping the app: " + r); 12306 pw.flush(); 12307 } catch (RemoteException e) { 12308 pw.println("Got a RemoteException while dumping the app " + r); 12309 pw.flush(); 12310 } 12311 } 12312 } 12313 } 12314 12315 final static class MemItem { 12316 final boolean isProc; 12317 final String label; 12318 final String shortLabel; 12319 final long pss; 12320 final int id; 12321 final boolean hasActivities; 12322 ArrayList<MemItem> subitems; 12323 12324 public MemItem(String _label, String _shortLabel, long _pss, int _id, 12325 boolean _hasActivities) { 12326 isProc = true; 12327 label = _label; 12328 shortLabel = _shortLabel; 12329 pss = _pss; 12330 id = _id; 12331 hasActivities = _hasActivities; 12332 } 12333 12334 public MemItem(String _label, String _shortLabel, long _pss, int _id) { 12335 isProc = false; 12336 label = _label; 12337 shortLabel = _shortLabel; 12338 pss = _pss; 12339 id = _id; 12340 hasActivities = false; 12341 } 12342 } 12343 12344 static final void dumpMemItems(PrintWriter pw, String prefix, String tag, 12345 ArrayList<MemItem> items, boolean sort, boolean isCompact) { 12346 if (sort && !isCompact) { 12347 Collections.sort(items, new Comparator<MemItem>() { 12348 @Override 12349 public int compare(MemItem lhs, MemItem rhs) { 12350 if (lhs.pss < rhs.pss) { 12351 return 1; 12352 } else if (lhs.pss > rhs.pss) { 12353 return -1; 12354 } 12355 return 0; 12356 } 12357 }); 12358 } 12359 12360 for (int i=0; i<items.size(); i++) { 12361 MemItem mi = items.get(i); 12362 if (!isCompact) { 12363 pw.print(prefix); pw.printf("%7d kB: ", mi.pss); pw.println(mi.label); 12364 } else if (mi.isProc) { 12365 pw.print("proc,"); pw.print(tag); pw.print(","); pw.print(mi.shortLabel); 12366 pw.print(","); pw.print(mi.id); pw.print(","); pw.print(mi.pss); 12367 pw.println(mi.hasActivities ? ",a" : ",e"); 12368 } else { 12369 pw.print(tag); pw.print(","); pw.print(mi.shortLabel); pw.print(","); 12370 pw.println(mi.pss); 12371 } 12372 if (mi.subitems != null) { 12373 dumpMemItems(pw, prefix + " ", mi.shortLabel, mi.subitems, 12374 true, isCompact); 12375 } 12376 } 12377 } 12378 12379 // These are in KB. 12380 static final long[] DUMP_MEM_BUCKETS = new long[] { 12381 5*1024, 7*1024, 10*1024, 15*1024, 20*1024, 30*1024, 40*1024, 80*1024, 12382 120*1024, 160*1024, 200*1024, 12383 250*1024, 300*1024, 350*1024, 400*1024, 500*1024, 600*1024, 800*1024, 12384 1*1024*1024, 2*1024*1024, 5*1024*1024, 10*1024*1024, 20*1024*1024 12385 }; 12386 12387 static final void appendMemBucket(StringBuilder out, long memKB, String label, 12388 boolean stackLike) { 12389 int start = label.lastIndexOf('.'); 12390 if (start >= 0) start++; 12391 else start = 0; 12392 int end = label.length(); 12393 for (int i=0; i<DUMP_MEM_BUCKETS.length; i++) { 12394 if (DUMP_MEM_BUCKETS[i] >= memKB) { 12395 long bucket = DUMP_MEM_BUCKETS[i]/1024; 12396 out.append(bucket); 12397 out.append(stackLike ? "MB." : "MB "); 12398 out.append(label, start, end); 12399 return; 12400 } 12401 } 12402 out.append(memKB/1024); 12403 out.append(stackLike ? "MB." : "MB "); 12404 out.append(label, start, end); 12405 } 12406 12407 static final int[] DUMP_MEM_OOM_ADJ = new int[] { 12408 ProcessList.NATIVE_ADJ, 12409 ProcessList.SYSTEM_ADJ, ProcessList.PERSISTENT_PROC_ADJ, ProcessList.FOREGROUND_APP_ADJ, 12410 ProcessList.VISIBLE_APP_ADJ, ProcessList.PERCEPTIBLE_APP_ADJ, 12411 ProcessList.BACKUP_APP_ADJ, ProcessList.HEAVY_WEIGHT_APP_ADJ, 12412 ProcessList.SERVICE_ADJ, ProcessList.HOME_APP_ADJ, 12413 ProcessList.PREVIOUS_APP_ADJ, ProcessList.SERVICE_B_ADJ, ProcessList.CACHED_APP_MAX_ADJ 12414 }; 12415 static final String[] DUMP_MEM_OOM_LABEL = new String[] { 12416 "Native", 12417 "System", "Persistent", "Foreground", 12418 "Visible", "Perceptible", 12419 "Heavy Weight", "Backup", 12420 "A Services", "Home", 12421 "Previous", "B Services", "Cached" 12422 }; 12423 static final String[] DUMP_MEM_OOM_COMPACT_LABEL = new String[] { 12424 "native", 12425 "sys", "pers", "fore", 12426 "vis", "percept", 12427 "heavy", "backup", 12428 "servicea", "home", 12429 "prev", "serviceb", "cached" 12430 }; 12431 12432 private final void dumpApplicationMemoryUsageHeader(PrintWriter pw, long uptime, 12433 long realtime, boolean isCheckinRequest, boolean isCompact) { 12434 if (isCheckinRequest || isCompact) { 12435 // short checkin version 12436 pw.print("time,"); pw.print(uptime); pw.print(","); pw.println(realtime); 12437 } else { 12438 pw.println("Applications Memory Usage (kB):"); 12439 pw.println("Uptime: " + uptime + " Realtime: " + realtime); 12440 } 12441 } 12442 12443 final void dumpApplicationMemoryUsage(FileDescriptor fd, 12444 PrintWriter pw, String prefix, String[] args, boolean brief, PrintWriter categoryPw) { 12445 boolean dumpDetails = false; 12446 boolean dumpFullDetails = false; 12447 boolean dumpDalvik = false; 12448 boolean oomOnly = false; 12449 boolean isCompact = false; 12450 boolean localOnly = false; 12451 12452 int opti = 0; 12453 while (opti < args.length) { 12454 String opt = args[opti]; 12455 if (opt == null || opt.length() <= 0 || opt.charAt(0) != '-') { 12456 break; 12457 } 12458 opti++; 12459 if ("-a".equals(opt)) { 12460 dumpDetails = true; 12461 dumpFullDetails = true; 12462 dumpDalvik = true; 12463 } else if ("-d".equals(opt)) { 12464 dumpDalvik = true; 12465 } else if ("-c".equals(opt)) { 12466 isCompact = true; 12467 } else if ("--oom".equals(opt)) { 12468 oomOnly = true; 12469 } else if ("--local".equals(opt)) { 12470 localOnly = true; 12471 } else if ("-h".equals(opt)) { 12472 pw.println("meminfo dump options: [-a] [-d] [-c] [--oom] [process]"); 12473 pw.println(" -a: include all available information for each process."); 12474 pw.println(" -d: include dalvik details when dumping process details."); 12475 pw.println(" -c: dump in a compact machine-parseable representation."); 12476 pw.println(" --oom: only show processes organized by oom adj."); 12477 pw.println(" --local: only collect details locally, don't call process."); 12478 pw.println("If [process] is specified it can be the name or "); 12479 pw.println("pid of a specific process to dump."); 12480 return; 12481 } else { 12482 pw.println("Unknown argument: " + opt + "; use -h for help"); 12483 } 12484 } 12485 12486 final boolean isCheckinRequest = scanArgs(args, "--checkin"); 12487 long uptime = SystemClock.uptimeMillis(); 12488 long realtime = SystemClock.elapsedRealtime(); 12489 final long[] tmpLong = new long[1]; 12490 12491 ArrayList<ProcessRecord> procs = collectProcesses(pw, opti, args); 12492 if (procs == null) { 12493 // No Java processes. Maybe they want to print a native process. 12494 if (args != null && args.length > opti 12495 && args[opti].charAt(0) != '-') { 12496 ArrayList<ProcessCpuTracker.Stats> nativeProcs 12497 = new ArrayList<ProcessCpuTracker.Stats>(); 12498 updateCpuStatsNow(); 12499 int findPid = -1; 12500 try { 12501 findPid = Integer.parseInt(args[opti]); 12502 } catch (NumberFormatException e) { 12503 } 12504 synchronized (mProcessCpuThread) { 12505 final int N = mProcessCpuTracker.countStats(); 12506 for (int i=0; i<N; i++) { 12507 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(i); 12508 if (st.pid == findPid || (st.baseName != null 12509 && st.baseName.equals(args[opti]))) { 12510 nativeProcs.add(st); 12511 } 12512 } 12513 } 12514 if (nativeProcs.size() > 0) { 12515 dumpApplicationMemoryUsageHeader(pw, uptime, realtime, isCheckinRequest, 12516 isCompact); 12517 Debug.MemoryInfo mi = null; 12518 for (int i = nativeProcs.size() - 1 ; i >= 0 ; i--) { 12519 final ProcessCpuTracker.Stats r = nativeProcs.get(i); 12520 final int pid = r.pid; 12521 if (!isCheckinRequest && dumpDetails) { 12522 pw.println("\n** MEMINFO in pid " + pid + " [" + r.baseName + "] **"); 12523 } 12524 if (mi == null) { 12525 mi = new Debug.MemoryInfo(); 12526 } 12527 if (dumpDetails || (!brief && !oomOnly)) { 12528 Debug.getMemoryInfo(pid, mi); 12529 } else { 12530 mi.dalvikPss = (int)Debug.getPss(pid, tmpLong); 12531 mi.dalvikPrivateDirty = (int)tmpLong[0]; 12532 } 12533 ActivityThread.dumpMemInfoTable(pw, mi, isCheckinRequest, dumpFullDetails, 12534 dumpDalvik, pid, r.baseName, 0, 0, 0, 0, 0, 0); 12535 if (isCheckinRequest) { 12536 pw.println(); 12537 } 12538 } 12539 return; 12540 } 12541 } 12542 pw.println("No process found for: " + args[opti]); 12543 return; 12544 } 12545 12546 if (!brief && !oomOnly && (procs.size() == 1 || isCheckinRequest)) { 12547 dumpDetails = true; 12548 } 12549 12550 dumpApplicationMemoryUsageHeader(pw, uptime, realtime, isCheckinRequest, isCompact); 12551 12552 String[] innerArgs = new String[args.length-opti]; 12553 System.arraycopy(args, opti, innerArgs, 0, args.length-opti); 12554 12555 ArrayList<MemItem> procMems = new ArrayList<MemItem>(); 12556 final SparseArray<MemItem> procMemsMap = new SparseArray<MemItem>(); 12557 long nativePss=0, dalvikPss=0, otherPss=0; 12558 long[] miscPss = new long[Debug.MemoryInfo.NUM_OTHER_STATS]; 12559 12560 long oomPss[] = new long[DUMP_MEM_OOM_LABEL.length]; 12561 ArrayList<MemItem>[] oomProcs = (ArrayList<MemItem>[]) 12562 new ArrayList[DUMP_MEM_OOM_LABEL.length]; 12563 12564 long totalPss = 0; 12565 long cachedPss = 0; 12566 12567 Debug.MemoryInfo mi = null; 12568 for (int i = procs.size() - 1 ; i >= 0 ; i--) { 12569 final ProcessRecord r = procs.get(i); 12570 final IApplicationThread thread; 12571 final int pid; 12572 final int oomAdj; 12573 final boolean hasActivities; 12574 synchronized (this) { 12575 thread = r.thread; 12576 pid = r.pid; 12577 oomAdj = r.getSetAdjWithServices(); 12578 hasActivities = r.activities.size() > 0; 12579 } 12580 if (thread != null) { 12581 if (!isCheckinRequest && dumpDetails) { 12582 pw.println("\n** MEMINFO in pid " + pid + " [" + r.processName + "] **"); 12583 } 12584 if (mi == null) { 12585 mi = new Debug.MemoryInfo(); 12586 } 12587 if (dumpDetails || (!brief && !oomOnly)) { 12588 Debug.getMemoryInfo(pid, mi); 12589 } else { 12590 mi.dalvikPss = (int)Debug.getPss(pid, tmpLong); 12591 mi.dalvikPrivateDirty = (int)tmpLong[0]; 12592 } 12593 if (dumpDetails) { 12594 if (localOnly) { 12595 ActivityThread.dumpMemInfoTable(pw, mi, isCheckinRequest, dumpFullDetails, 12596 dumpDalvik, pid, r.processName, 0, 0, 0, 0, 0, 0); 12597 if (isCheckinRequest) { 12598 pw.println(); 12599 } 12600 } else { 12601 try { 12602 pw.flush(); 12603 thread.dumpMemInfo(fd, mi, isCheckinRequest, dumpFullDetails, 12604 dumpDalvik, innerArgs); 12605 } catch (RemoteException e) { 12606 if (!isCheckinRequest) { 12607 pw.println("Got RemoteException!"); 12608 pw.flush(); 12609 } 12610 } 12611 } 12612 } 12613 12614 final long myTotalPss = mi.getTotalPss(); 12615 final long myTotalUss = mi.getTotalUss(); 12616 12617 synchronized (this) { 12618 if (r.thread != null && oomAdj == r.getSetAdjWithServices()) { 12619 // Record this for posterity if the process has been stable. 12620 r.baseProcessTracker.addPss(myTotalPss, myTotalUss, true, r.pkgList); 12621 } 12622 } 12623 12624 if (!isCheckinRequest && mi != null) { 12625 totalPss += myTotalPss; 12626 MemItem pssItem = new MemItem(r.processName + " (pid " + pid + 12627 (hasActivities ? " / activities)" : ")"), 12628 r.processName, myTotalPss, pid, hasActivities); 12629 procMems.add(pssItem); 12630 procMemsMap.put(pid, pssItem); 12631 12632 nativePss += mi.nativePss; 12633 dalvikPss += mi.dalvikPss; 12634 otherPss += mi.otherPss; 12635 for (int j=0; j<Debug.MemoryInfo.NUM_OTHER_STATS; j++) { 12636 long mem = mi.getOtherPss(j); 12637 miscPss[j] += mem; 12638 otherPss -= mem; 12639 } 12640 12641 if (oomAdj >= ProcessList.CACHED_APP_MIN_ADJ) { 12642 cachedPss += myTotalPss; 12643 } 12644 12645 for (int oomIndex=0; oomIndex<oomPss.length; oomIndex++) { 12646 if (oomAdj <= DUMP_MEM_OOM_ADJ[oomIndex] 12647 || oomIndex == (oomPss.length-1)) { 12648 oomPss[oomIndex] += myTotalPss; 12649 if (oomProcs[oomIndex] == null) { 12650 oomProcs[oomIndex] = new ArrayList<MemItem>(); 12651 } 12652 oomProcs[oomIndex].add(pssItem); 12653 break; 12654 } 12655 } 12656 } 12657 } 12658 } 12659 12660 if (!isCheckinRequest && procs.size() > 1) { 12661 // If we are showing aggregations, also look for native processes to 12662 // include so that our aggregations are more accurate. 12663 updateCpuStatsNow(); 12664 synchronized (mProcessCpuThread) { 12665 final int N = mProcessCpuTracker.countStats(); 12666 for (int i=0; i<N; i++) { 12667 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(i); 12668 if (st.vsize > 0 && procMemsMap.indexOfKey(st.pid) < 0) { 12669 if (mi == null) { 12670 mi = new Debug.MemoryInfo(); 12671 } 12672 if (!brief && !oomOnly) { 12673 Debug.getMemoryInfo(st.pid, mi); 12674 } else { 12675 mi.nativePss = (int)Debug.getPss(st.pid, tmpLong); 12676 mi.nativePrivateDirty = (int)tmpLong[0]; 12677 } 12678 12679 final long myTotalPss = mi.getTotalPss(); 12680 totalPss += myTotalPss; 12681 12682 MemItem pssItem = new MemItem(st.name + " (pid " + st.pid + ")", 12683 st.name, myTotalPss, st.pid, false); 12684 procMems.add(pssItem); 12685 12686 nativePss += mi.nativePss; 12687 dalvikPss += mi.dalvikPss; 12688 otherPss += mi.otherPss; 12689 for (int j=0; j<Debug.MemoryInfo.NUM_OTHER_STATS; j++) { 12690 long mem = mi.getOtherPss(j); 12691 miscPss[j] += mem; 12692 otherPss -= mem; 12693 } 12694 oomPss[0] += myTotalPss; 12695 if (oomProcs[0] == null) { 12696 oomProcs[0] = new ArrayList<MemItem>(); 12697 } 12698 oomProcs[0].add(pssItem); 12699 } 12700 } 12701 } 12702 12703 ArrayList<MemItem> catMems = new ArrayList<MemItem>(); 12704 12705 catMems.add(new MemItem("Native", "Native", nativePss, -1)); 12706 catMems.add(new MemItem("Dalvik", "Dalvik", dalvikPss, -2)); 12707 catMems.add(new MemItem("Unknown", "Unknown", otherPss, -3)); 12708 for (int j=0; j<Debug.MemoryInfo.NUM_OTHER_STATS; j++) { 12709 String label = Debug.MemoryInfo.getOtherLabel(j); 12710 catMems.add(new MemItem(label, label, miscPss[j], j)); 12711 } 12712 12713 ArrayList<MemItem> oomMems = new ArrayList<MemItem>(); 12714 for (int j=0; j<oomPss.length; j++) { 12715 if (oomPss[j] != 0) { 12716 String label = isCompact ? DUMP_MEM_OOM_COMPACT_LABEL[j] 12717 : DUMP_MEM_OOM_LABEL[j]; 12718 MemItem item = new MemItem(label, label, oomPss[j], 12719 DUMP_MEM_OOM_ADJ[j]); 12720 item.subitems = oomProcs[j]; 12721 oomMems.add(item); 12722 } 12723 } 12724 12725 if (!brief && !oomOnly && !isCompact) { 12726 pw.println(); 12727 pw.println("Total PSS by process:"); 12728 dumpMemItems(pw, " ", "proc", procMems, true, isCompact); 12729 pw.println(); 12730 } 12731 if (!isCompact) { 12732 pw.println("Total PSS by OOM adjustment:"); 12733 } 12734 dumpMemItems(pw, " ", "oom", oomMems, false, isCompact); 12735 if (!brief && !oomOnly) { 12736 PrintWriter out = categoryPw != null ? categoryPw : pw; 12737 if (!isCompact) { 12738 out.println(); 12739 out.println("Total PSS by category:"); 12740 } 12741 dumpMemItems(out, " ", "cat", catMems, true, isCompact); 12742 } 12743 if (!isCompact) { 12744 pw.println(); 12745 } 12746 MemInfoReader memInfo = new MemInfoReader(); 12747 memInfo.readMemInfo(); 12748 if (!brief) { 12749 if (!isCompact) { 12750 pw.print("Total RAM: "); pw.print(memInfo.getTotalSizeKb()); 12751 pw.print(" kB (status "); 12752 switch (mLastMemoryLevel) { 12753 case ProcessStats.ADJ_MEM_FACTOR_NORMAL: 12754 pw.println("normal)"); 12755 break; 12756 case ProcessStats.ADJ_MEM_FACTOR_MODERATE: 12757 pw.println("moderate)"); 12758 break; 12759 case ProcessStats.ADJ_MEM_FACTOR_LOW: 12760 pw.println("low)"); 12761 break; 12762 case ProcessStats.ADJ_MEM_FACTOR_CRITICAL: 12763 pw.println("critical)"); 12764 break; 12765 default: 12766 pw.print(mLastMemoryLevel); 12767 pw.println(")"); 12768 break; 12769 } 12770 pw.print(" Free RAM: "); pw.print(cachedPss + memInfo.getCachedSizeKb() 12771 + memInfo.getFreeSizeKb()); pw.print(" kB ("); 12772 pw.print(cachedPss); pw.print(" cached pss + "); 12773 pw.print(memInfo.getCachedSizeKb()); pw.print(" cached + "); 12774 pw.print(memInfo.getFreeSizeKb()); pw.println(" free)"); 12775 } else { 12776 pw.print("ram,"); pw.print(memInfo.getTotalSizeKb()); pw.print(","); 12777 pw.print(cachedPss + memInfo.getCachedSizeKb() 12778 + memInfo.getFreeSizeKb()); pw.print(","); 12779 pw.println(totalPss - cachedPss); 12780 } 12781 } 12782 if (!isCompact) { 12783 pw.print(" Used RAM: "); pw.print(totalPss - cachedPss 12784 + memInfo.getBuffersSizeKb() + memInfo.getShmemSizeKb() 12785 + memInfo.getSlabSizeKb()); pw.print(" kB ("); 12786 pw.print(totalPss - cachedPss); pw.print(" used pss + "); 12787 pw.print(memInfo.getBuffersSizeKb()); pw.print(" buffers + "); 12788 pw.print(memInfo.getShmemSizeKb()); pw.print(" shmem + "); 12789 pw.print(memInfo.getSlabSizeKb()); pw.println(" slab)"); 12790 pw.print(" Lost RAM: "); pw.print(memInfo.getTotalSizeKb() 12791 - totalPss - memInfo.getFreeSizeKb() - memInfo.getCachedSizeKb() 12792 - memInfo.getBuffersSizeKb() - memInfo.getShmemSizeKb() 12793 - memInfo.getSlabSizeKb()); pw.println(" kB"); 12794 } 12795 if (!brief) { 12796 if (memInfo.getZramTotalSizeKb() != 0) { 12797 if (!isCompact) { 12798 pw.print(" ZRAM: "); pw.print(memInfo.getZramTotalSizeKb()); 12799 pw.print(" kB physical used for "); 12800 pw.print(memInfo.getSwapTotalSizeKb() 12801 - memInfo.getSwapFreeSizeKb()); 12802 pw.print(" kB in swap ("); 12803 pw.print(memInfo.getSwapTotalSizeKb()); 12804 pw.println(" kB total swap)"); 12805 } else { 12806 pw.print("zram,"); pw.print(memInfo.getZramTotalSizeKb()); pw.print(","); 12807 pw.print(memInfo.getSwapTotalSizeKb()); pw.print(","); 12808 pw.println(memInfo.getSwapFreeSizeKb()); 12809 } 12810 } 12811 final int[] SINGLE_LONG_FORMAT = new int[] { 12812 Process.PROC_SPACE_TERM|Process.PROC_OUT_LONG 12813 }; 12814 long[] longOut = new long[1]; 12815 Process.readProcFile("/sys/kernel/mm/ksm/pages_shared", 12816 SINGLE_LONG_FORMAT, null, longOut, null); 12817 long shared = longOut[0] * ProcessList.PAGE_SIZE / 1024; 12818 longOut[0] = 0; 12819 Process.readProcFile("/sys/kernel/mm/ksm/pages_sharing", 12820 SINGLE_LONG_FORMAT, null, longOut, null); 12821 long sharing = longOut[0] * ProcessList.PAGE_SIZE / 1024; 12822 longOut[0] = 0; 12823 Process.readProcFile("/sys/kernel/mm/ksm/pages_unshared", 12824 SINGLE_LONG_FORMAT, null, longOut, null); 12825 long unshared = longOut[0] * ProcessList.PAGE_SIZE / 1024; 12826 longOut[0] = 0; 12827 Process.readProcFile("/sys/kernel/mm/ksm/pages_volatile", 12828 SINGLE_LONG_FORMAT, null, longOut, null); 12829 long voltile = longOut[0] * ProcessList.PAGE_SIZE / 1024; 12830 if (!isCompact) { 12831 if (sharing != 0 || shared != 0 || unshared != 0 || voltile != 0) { 12832 pw.print(" KSM: "); pw.print(sharing); 12833 pw.print(" kB saved from shared "); 12834 pw.print(shared); pw.println(" kB"); 12835 pw.print(" "); pw.print(unshared); pw.print(" kB unshared; "); 12836 pw.print(voltile); pw.println(" kB volatile"); 12837 } 12838 pw.print(" Tuning: "); 12839 pw.print(ActivityManager.staticGetMemoryClass()); 12840 pw.print(" (large "); 12841 pw.print(ActivityManager.staticGetLargeMemoryClass()); 12842 pw.print("), oom "); 12843 pw.print(mProcessList.getMemLevel(ProcessList.CACHED_APP_MAX_ADJ)/1024); 12844 pw.print(" kB"); 12845 pw.print(", restore limit "); 12846 pw.print(mProcessList.getCachedRestoreThresholdKb()); 12847 pw.print(" kB"); 12848 if (ActivityManager.isLowRamDeviceStatic()) { 12849 pw.print(" (low-ram)"); 12850 } 12851 if (ActivityManager.isHighEndGfx()) { 12852 pw.print(" (high-end-gfx)"); 12853 } 12854 pw.println(); 12855 } else { 12856 pw.print("ksm,"); pw.print(sharing); pw.print(","); 12857 pw.print(shared); pw.print(","); pw.print(unshared); pw.print(","); 12858 pw.println(voltile); 12859 pw.print("tuning,"); 12860 pw.print(ActivityManager.staticGetMemoryClass()); 12861 pw.print(','); 12862 pw.print(ActivityManager.staticGetLargeMemoryClass()); 12863 pw.print(','); 12864 pw.print(mProcessList.getMemLevel(ProcessList.CACHED_APP_MAX_ADJ)/1024); 12865 if (ActivityManager.isLowRamDeviceStatic()) { 12866 pw.print(",low-ram"); 12867 } 12868 if (ActivityManager.isHighEndGfx()) { 12869 pw.print(",high-end-gfx"); 12870 } 12871 pw.println(); 12872 } 12873 } 12874 } 12875 } 12876 12877 /** 12878 * Searches array of arguments for the specified string 12879 * @param args array of argument strings 12880 * @param value value to search for 12881 * @return true if the value is contained in the array 12882 */ 12883 private static boolean scanArgs(String[] args, String value) { 12884 if (args != null) { 12885 for (String arg : args) { 12886 if (value.equals(arg)) { 12887 return true; 12888 } 12889 } 12890 } 12891 return false; 12892 } 12893 12894 private final boolean removeDyingProviderLocked(ProcessRecord proc, 12895 ContentProviderRecord cpr, boolean always) { 12896 final boolean inLaunching = mLaunchingProviders.contains(cpr); 12897 12898 if (!inLaunching || always) { 12899 synchronized (cpr) { 12900 cpr.launchingApp = null; 12901 cpr.notifyAll(); 12902 } 12903 mProviderMap.removeProviderByClass(cpr.name, UserHandle.getUserId(cpr.uid)); 12904 String names[] = cpr.info.authority.split(";"); 12905 for (int j = 0; j < names.length; j++) { 12906 mProviderMap.removeProviderByName(names[j], UserHandle.getUserId(cpr.uid)); 12907 } 12908 } 12909 12910 for (int i=0; i<cpr.connections.size(); i++) { 12911 ContentProviderConnection conn = cpr.connections.get(i); 12912 if (conn.waiting) { 12913 // If this connection is waiting for the provider, then we don't 12914 // need to mess with its process unless we are always removing 12915 // or for some reason the provider is not currently launching. 12916 if (inLaunching && !always) { 12917 continue; 12918 } 12919 } 12920 ProcessRecord capp = conn.client; 12921 conn.dead = true; 12922 if (conn.stableCount > 0) { 12923 if (!capp.persistent && capp.thread != null 12924 && capp.pid != 0 12925 && capp.pid != MY_PID) { 12926 killUnneededProcessLocked(capp, "depends on provider " 12927 + cpr.name.flattenToShortString() 12928 + " in dying proc " + (proc != null ? proc.processName : "??")); 12929 } 12930 } else if (capp.thread != null && conn.provider.provider != null) { 12931 try { 12932 capp.thread.unstableProviderDied(conn.provider.provider.asBinder()); 12933 } catch (RemoteException e) { 12934 } 12935 // In the protocol here, we don't expect the client to correctly 12936 // clean up this connection, we'll just remove it. 12937 cpr.connections.remove(i); 12938 conn.client.conProviders.remove(conn); 12939 } 12940 } 12941 12942 if (inLaunching && always) { 12943 mLaunchingProviders.remove(cpr); 12944 } 12945 return inLaunching; 12946 } 12947 12948 /** 12949 * Main code for cleaning up a process when it has gone away. This is 12950 * called both as a result of the process dying, or directly when stopping 12951 * a process when running in single process mode. 12952 */ 12953 private final void cleanUpApplicationRecordLocked(ProcessRecord app, 12954 boolean restarting, boolean allowRestart, int index) { 12955 if (index >= 0) { 12956 removeLruProcessLocked(app); 12957 ProcessList.remove(app.pid); 12958 } 12959 12960 mProcessesToGc.remove(app); 12961 mPendingPssProcesses.remove(app); 12962 12963 // Dismiss any open dialogs. 12964 if (app.crashDialog != null && !app.forceCrashReport) { 12965 app.crashDialog.dismiss(); 12966 app.crashDialog = null; 12967 } 12968 if (app.anrDialog != null) { 12969 app.anrDialog.dismiss(); 12970 app.anrDialog = null; 12971 } 12972 if (app.waitDialog != null) { 12973 app.waitDialog.dismiss(); 12974 app.waitDialog = null; 12975 } 12976 12977 app.crashing = false; 12978 app.notResponding = false; 12979 12980 app.resetPackageList(mProcessStats); 12981 app.unlinkDeathRecipient(); 12982 app.makeInactive(mProcessStats); 12983 app.forcingToForeground = null; 12984 updateProcessForegroundLocked(app, false, false); 12985 app.foregroundActivities = false; 12986 app.hasShownUi = false; 12987 app.treatLikeActivity = false; 12988 app.hasAboveClient = false; 12989 app.hasClientActivities = false; 12990 12991 mServices.killServicesLocked(app, allowRestart); 12992 12993 boolean restart = false; 12994 12995 // Remove published content providers. 12996 for (int i=app.pubProviders.size()-1; i>=0; i--) { 12997 ContentProviderRecord cpr = app.pubProviders.valueAt(i); 12998 final boolean always = app.bad || !allowRestart; 12999 if (removeDyingProviderLocked(app, cpr, always) || always) { 13000 // We left the provider in the launching list, need to 13001 // restart it. 13002 restart = true; 13003 } 13004 13005 cpr.provider = null; 13006 cpr.proc = null; 13007 } 13008 app.pubProviders.clear(); 13009 13010 // Take care of any launching providers waiting for this process. 13011 if (checkAppInLaunchingProvidersLocked(app, false)) { 13012 restart = true; 13013 } 13014 13015 // Unregister from connected content providers. 13016 if (!app.conProviders.isEmpty()) { 13017 for (int i=0; i<app.conProviders.size(); i++) { 13018 ContentProviderConnection conn = app.conProviders.get(i); 13019 conn.provider.connections.remove(conn); 13020 } 13021 app.conProviders.clear(); 13022 } 13023 13024 // At this point there may be remaining entries in mLaunchingProviders 13025 // where we were the only one waiting, so they are no longer of use. 13026 // Look for these and clean up if found. 13027 // XXX Commented out for now. Trying to figure out a way to reproduce 13028 // the actual situation to identify what is actually going on. 13029 if (false) { 13030 for (int i=0; i<mLaunchingProviders.size(); i++) { 13031 ContentProviderRecord cpr = (ContentProviderRecord) 13032 mLaunchingProviders.get(i); 13033 if (cpr.connections.size() <= 0 && !cpr.hasExternalProcessHandles()) { 13034 synchronized (cpr) { 13035 cpr.launchingApp = null; 13036 cpr.notifyAll(); 13037 } 13038 } 13039 } 13040 } 13041 13042 skipCurrentReceiverLocked(app); 13043 13044 // Unregister any receivers. 13045 for (int i=app.receivers.size()-1; i>=0; i--) { 13046 removeReceiverLocked(app.receivers.valueAt(i)); 13047 } 13048 app.receivers.clear(); 13049 13050 // If the app is undergoing backup, tell the backup manager about it 13051 if (mBackupTarget != null && app.pid == mBackupTarget.app.pid) { 13052 if (DEBUG_BACKUP || DEBUG_CLEANUP) Slog.d(TAG, "App " 13053 + mBackupTarget.appInfo + " died during backup"); 13054 try { 13055 IBackupManager bm = IBackupManager.Stub.asInterface( 13056 ServiceManager.getService(Context.BACKUP_SERVICE)); 13057 bm.agentDisconnected(app.info.packageName); 13058 } catch (RemoteException e) { 13059 // can't happen; backup manager is local 13060 } 13061 } 13062 13063 for (int i = mPendingProcessChanges.size()-1; i>=0; i--) { 13064 ProcessChangeItem item = mPendingProcessChanges.get(i); 13065 if (item.pid == app.pid) { 13066 mPendingProcessChanges.remove(i); 13067 mAvailProcessChanges.add(item); 13068 } 13069 } 13070 mHandler.obtainMessage(DISPATCH_PROCESS_DIED, app.pid, app.info.uid, null).sendToTarget(); 13071 13072 // If the caller is restarting this app, then leave it in its 13073 // current lists and let the caller take care of it. 13074 if (restarting) { 13075 return; 13076 } 13077 13078 if (!app.persistent || app.isolated) { 13079 if (DEBUG_PROCESSES || DEBUG_CLEANUP) Slog.v(TAG, 13080 "Removing non-persistent process during cleanup: " + app); 13081 mProcessNames.remove(app.processName, app.uid); 13082 mIsolatedProcesses.remove(app.uid); 13083 if (mHeavyWeightProcess == app) { 13084 mHandler.sendMessage(mHandler.obtainMessage(CANCEL_HEAVY_NOTIFICATION_MSG, 13085 mHeavyWeightProcess.userId, 0)); 13086 mHeavyWeightProcess = null; 13087 } 13088 } else if (!app.removed) { 13089 // This app is persistent, so we need to keep its record around. 13090 // If it is not already on the pending app list, add it there 13091 // and start a new process for it. 13092 if (mPersistentStartingProcesses.indexOf(app) < 0) { 13093 mPersistentStartingProcesses.add(app); 13094 restart = true; 13095 } 13096 } 13097 if ((DEBUG_PROCESSES || DEBUG_CLEANUP) && mProcessesOnHold.contains(app)) Slog.v(TAG, 13098 "Clean-up removing on hold: " + app); 13099 mProcessesOnHold.remove(app); 13100 13101 if (app == mHomeProcess) { 13102 mHomeProcess = null; 13103 } 13104 if (app == mPreviousProcess) { 13105 mPreviousProcess = null; 13106 } 13107 13108 if (restart && !app.isolated) { 13109 // We have components that still need to be running in the 13110 // process, so re-launch it. 13111 mProcessNames.put(app.processName, app.uid, app); 13112 startProcessLocked(app, "restart", app.processName, null /* ABI override */); 13113 } else if (app.pid > 0 && app.pid != MY_PID) { 13114 // Goodbye! 13115 boolean removed; 13116 synchronized (mPidsSelfLocked) { 13117 mPidsSelfLocked.remove(app.pid); 13118 mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app); 13119 } 13120 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_PROC_FINISH, 13121 app.processName, app.info.uid); 13122 if (app.isolated) { 13123 mBatteryStatsService.removeIsolatedUid(app.uid, app.info.uid); 13124 } 13125 app.setPid(0); 13126 } 13127 } 13128 13129 boolean checkAppInLaunchingProvidersLocked(ProcessRecord app, boolean alwaysBad) { 13130 // Look through the content providers we are waiting to have launched, 13131 // and if any run in this process then either schedule a restart of 13132 // the process or kill the client waiting for it if this process has 13133 // gone bad. 13134 int NL = mLaunchingProviders.size(); 13135 boolean restart = false; 13136 for (int i=0; i<NL; i++) { 13137 ContentProviderRecord cpr = mLaunchingProviders.get(i); 13138 if (cpr.launchingApp == app) { 13139 if (!alwaysBad && !app.bad) { 13140 restart = true; 13141 } else { 13142 removeDyingProviderLocked(app, cpr, true); 13143 // cpr should have been removed from mLaunchingProviders 13144 NL = mLaunchingProviders.size(); 13145 i--; 13146 } 13147 } 13148 } 13149 return restart; 13150 } 13151 13152 // ========================================================= 13153 // SERVICES 13154 // ========================================================= 13155 13156 public List<ActivityManager.RunningServiceInfo> getServices(int maxNum, 13157 int flags) { 13158 enforceNotIsolatedCaller("getServices"); 13159 synchronized (this) { 13160 return mServices.getRunningServiceInfoLocked(maxNum, flags); 13161 } 13162 } 13163 13164 public PendingIntent getRunningServiceControlPanel(ComponentName name) { 13165 enforceNotIsolatedCaller("getRunningServiceControlPanel"); 13166 synchronized (this) { 13167 return mServices.getRunningServiceControlPanelLocked(name); 13168 } 13169 } 13170 13171 public ComponentName startService(IApplicationThread caller, Intent service, 13172 String resolvedType, int userId) { 13173 enforceNotIsolatedCaller("startService"); 13174 // Refuse possible leaked file descriptors 13175 if (service != null && service.hasFileDescriptors() == true) { 13176 throw new IllegalArgumentException("File descriptors passed in Intent"); 13177 } 13178 13179 if (DEBUG_SERVICE) 13180 Slog.v(TAG, "startService: " + service + " type=" + resolvedType); 13181 synchronized(this) { 13182 final int callingPid = Binder.getCallingPid(); 13183 final int callingUid = Binder.getCallingUid(); 13184 final long origId = Binder.clearCallingIdentity(); 13185 ComponentName res = mServices.startServiceLocked(caller, service, 13186 resolvedType, callingPid, callingUid, userId); 13187 Binder.restoreCallingIdentity(origId); 13188 return res; 13189 } 13190 } 13191 13192 ComponentName startServiceInPackage(int uid, 13193 Intent service, String resolvedType, int userId) { 13194 synchronized(this) { 13195 if (DEBUG_SERVICE) 13196 Slog.v(TAG, "startServiceInPackage: " + service + " type=" + resolvedType); 13197 final long origId = Binder.clearCallingIdentity(); 13198 ComponentName res = mServices.startServiceLocked(null, service, 13199 resolvedType, -1, uid, userId); 13200 Binder.restoreCallingIdentity(origId); 13201 return res; 13202 } 13203 } 13204 13205 public int stopService(IApplicationThread caller, Intent service, 13206 String resolvedType, int userId) { 13207 enforceNotIsolatedCaller("stopService"); 13208 // Refuse possible leaked file descriptors 13209 if (service != null && service.hasFileDescriptors() == true) { 13210 throw new IllegalArgumentException("File descriptors passed in Intent"); 13211 } 13212 13213 synchronized(this) { 13214 return mServices.stopServiceLocked(caller, service, resolvedType, userId); 13215 } 13216 } 13217 13218 public IBinder peekService(Intent service, String resolvedType) { 13219 enforceNotIsolatedCaller("peekService"); 13220 // Refuse possible leaked file descriptors 13221 if (service != null && service.hasFileDescriptors() == true) { 13222 throw new IllegalArgumentException("File descriptors passed in Intent"); 13223 } 13224 synchronized(this) { 13225 return mServices.peekServiceLocked(service, resolvedType); 13226 } 13227 } 13228 13229 public boolean stopServiceToken(ComponentName className, IBinder token, 13230 int startId) { 13231 synchronized(this) { 13232 return mServices.stopServiceTokenLocked(className, token, startId); 13233 } 13234 } 13235 13236 public void setServiceForeground(ComponentName className, IBinder token, 13237 int id, Notification notification, boolean removeNotification) { 13238 synchronized(this) { 13239 mServices.setServiceForegroundLocked(className, token, id, notification, 13240 removeNotification); 13241 } 13242 } 13243 13244 public int handleIncomingUser(int callingPid, int callingUid, int userId, boolean allowAll, 13245 boolean requireFull, String name, String callerPackage) { 13246 final int callingUserId = UserHandle.getUserId(callingUid); 13247 if (callingUserId != userId) { 13248 if (callingUid != 0 && callingUid != Process.SYSTEM_UID) { 13249 if ((requireFull || checkComponentPermission( 13250 android.Manifest.permission.INTERACT_ACROSS_USERS, 13251 callingPid, callingUid, -1, true) != PackageManager.PERMISSION_GRANTED) 13252 && checkComponentPermission(INTERACT_ACROSS_USERS_FULL, 13253 callingPid, callingUid, -1, true) 13254 != PackageManager.PERMISSION_GRANTED) { 13255 if (userId == UserHandle.USER_CURRENT_OR_SELF) { 13256 // In this case, they would like to just execute as their 13257 // owner user instead of failing. 13258 userId = callingUserId; 13259 } else { 13260 StringBuilder builder = new StringBuilder(128); 13261 builder.append("Permission Denial: "); 13262 builder.append(name); 13263 if (callerPackage != null) { 13264 builder.append(" from "); 13265 builder.append(callerPackage); 13266 } 13267 builder.append(" asks to run as user "); 13268 builder.append(userId); 13269 builder.append(" but is calling from user "); 13270 builder.append(UserHandle.getUserId(callingUid)); 13271 builder.append("; this requires "); 13272 builder.append(INTERACT_ACROSS_USERS_FULL); 13273 if (!requireFull) { 13274 builder.append(" or "); 13275 builder.append(android.Manifest.permission.INTERACT_ACROSS_USERS); 13276 } 13277 String msg = builder.toString(); 13278 Slog.w(TAG, msg); 13279 throw new SecurityException(msg); 13280 } 13281 } 13282 } 13283 if (userId == UserHandle.USER_CURRENT 13284 || userId == UserHandle.USER_CURRENT_OR_SELF) { 13285 // Note that we may be accessing this outside of a lock... 13286 // shouldn't be a big deal, if this is being called outside 13287 // of a locked context there is intrinsically a race with 13288 // the value the caller will receive and someone else changing it. 13289 userId = mCurrentUserId; 13290 } 13291 if (!allowAll && userId < 0) { 13292 throw new IllegalArgumentException( 13293 "Call does not support special user #" + userId); 13294 } 13295 } 13296 return userId; 13297 } 13298 13299 boolean isSingleton(String componentProcessName, ApplicationInfo aInfo, 13300 String className, int flags) { 13301 boolean result = false; 13302 // For apps that don't have pre-defined UIDs, check for permission 13303 if (UserHandle.getAppId(aInfo.uid) >= Process.FIRST_APPLICATION_UID) { 13304 if ((flags & ServiceInfo.FLAG_SINGLE_USER) != 0) { 13305 if (ActivityManager.checkUidPermission( 13306 android.Manifest.permission.INTERACT_ACROSS_USERS, 13307 aInfo.uid) != PackageManager.PERMISSION_GRANTED) { 13308 ComponentName comp = new ComponentName(aInfo.packageName, className); 13309 String msg = "Permission Denial: Component " + comp.flattenToShortString() 13310 + " requests FLAG_SINGLE_USER, but app does not hold " 13311 + android.Manifest.permission.INTERACT_ACROSS_USERS; 13312 Slog.w(TAG, msg); 13313 throw new SecurityException(msg); 13314 } 13315 // Permission passed 13316 result = true; 13317 } 13318 } else if ("system".equals(componentProcessName)) { 13319 result = true; 13320 } else { 13321 // App with pre-defined UID, check if it's a persistent app 13322 result = (aInfo.flags & ApplicationInfo.FLAG_PERSISTENT) != 0; 13323 } 13324 if (DEBUG_MU) { 13325 Slog.v(TAG, "isSingleton(" + componentProcessName + ", " + aInfo 13326 + ", " + className + ", 0x" + Integer.toHexString(flags) + ") = " + result); 13327 } 13328 return result; 13329 } 13330 13331 /** 13332 * Checks to see if the caller is in the same app as the singleton 13333 * component, or the component is in a special app. It allows special apps 13334 * to export singleton components but prevents exporting singleton 13335 * components for regular apps. 13336 */ 13337 boolean isValidSingletonCall(int callingUid, int componentUid) { 13338 int componentAppId = UserHandle.getAppId(componentUid); 13339 return UserHandle.isSameApp(callingUid, componentUid) 13340 || componentAppId == Process.SYSTEM_UID 13341 || componentAppId == Process.PHONE_UID 13342 || ActivityManager.checkUidPermission(INTERACT_ACROSS_USERS_FULL, componentUid) 13343 == PackageManager.PERMISSION_GRANTED; 13344 } 13345 13346 public int bindService(IApplicationThread caller, IBinder token, 13347 Intent service, String resolvedType, 13348 IServiceConnection connection, int flags, int userId) { 13349 enforceNotIsolatedCaller("bindService"); 13350 // Refuse possible leaked file descriptors 13351 if (service != null && service.hasFileDescriptors() == true) { 13352 throw new IllegalArgumentException("File descriptors passed in Intent"); 13353 } 13354 13355 synchronized(this) { 13356 return mServices.bindServiceLocked(caller, token, service, resolvedType, 13357 connection, flags, userId); 13358 } 13359 } 13360 13361 public boolean unbindService(IServiceConnection connection) { 13362 synchronized (this) { 13363 return mServices.unbindServiceLocked(connection); 13364 } 13365 } 13366 13367 public void publishService(IBinder token, Intent intent, IBinder service) { 13368 // Refuse possible leaked file descriptors 13369 if (intent != null && intent.hasFileDescriptors() == true) { 13370 throw new IllegalArgumentException("File descriptors passed in Intent"); 13371 } 13372 13373 synchronized(this) { 13374 if (!(token instanceof ServiceRecord)) { 13375 throw new IllegalArgumentException("Invalid service token"); 13376 } 13377 mServices.publishServiceLocked((ServiceRecord)token, intent, service); 13378 } 13379 } 13380 13381 public void unbindFinished(IBinder token, Intent intent, boolean doRebind) { 13382 // Refuse possible leaked file descriptors 13383 if (intent != null && intent.hasFileDescriptors() == true) { 13384 throw new IllegalArgumentException("File descriptors passed in Intent"); 13385 } 13386 13387 synchronized(this) { 13388 mServices.unbindFinishedLocked((ServiceRecord)token, intent, doRebind); 13389 } 13390 } 13391 13392 public void serviceDoneExecuting(IBinder token, int type, int startId, int res) { 13393 synchronized(this) { 13394 if (!(token instanceof ServiceRecord)) { 13395 throw new IllegalArgumentException("Invalid service token"); 13396 } 13397 mServices.serviceDoneExecutingLocked((ServiceRecord)token, type, startId, res); 13398 } 13399 } 13400 13401 // ========================================================= 13402 // BACKUP AND RESTORE 13403 // ========================================================= 13404 13405 // Cause the target app to be launched if necessary and its backup agent 13406 // instantiated. The backup agent will invoke backupAgentCreated() on the 13407 // activity manager to announce its creation. 13408 public boolean bindBackupAgent(ApplicationInfo app, int backupMode) { 13409 if (DEBUG_BACKUP) Slog.v(TAG, "bindBackupAgent: app=" + app + " mode=" + backupMode); 13410 enforceCallingPermission("android.permission.BACKUP", "bindBackupAgent"); 13411 13412 synchronized(this) { 13413 // !!! TODO: currently no check here that we're already bound 13414 BatteryStatsImpl.Uid.Pkg.Serv ss = null; 13415 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 13416 synchronized (stats) { 13417 ss = stats.getServiceStatsLocked(app.uid, app.packageName, app.name); 13418 } 13419 13420 // Backup agent is now in use, its package can't be stopped. 13421 try { 13422 AppGlobals.getPackageManager().setPackageStoppedState( 13423 app.packageName, false, UserHandle.getUserId(app.uid)); 13424 } catch (RemoteException e) { 13425 } catch (IllegalArgumentException e) { 13426 Slog.w(TAG, "Failed trying to unstop package " 13427 + app.packageName + ": " + e); 13428 } 13429 13430 BackupRecord r = new BackupRecord(ss, app, backupMode); 13431 ComponentName hostingName = (backupMode == IApplicationThread.BACKUP_MODE_INCREMENTAL) 13432 ? new ComponentName(app.packageName, app.backupAgentName) 13433 : new ComponentName("android", "FullBackupAgent"); 13434 // startProcessLocked() returns existing proc's record if it's already running 13435 ProcessRecord proc = startProcessLocked(app.processName, app, 13436 false, 0, "backup", hostingName, false, false, false); 13437 if (proc == null) { 13438 Slog.e(TAG, "Unable to start backup agent process " + r); 13439 return false; 13440 } 13441 13442 r.app = proc; 13443 mBackupTarget = r; 13444 mBackupAppName = app.packageName; 13445 13446 // Try not to kill the process during backup 13447 updateOomAdjLocked(proc); 13448 13449 // If the process is already attached, schedule the creation of the backup agent now. 13450 // If it is not yet live, this will be done when it attaches to the framework. 13451 if (proc.thread != null) { 13452 if (DEBUG_BACKUP) Slog.v(TAG, "Agent proc already running: " + proc); 13453 try { 13454 proc.thread.scheduleCreateBackupAgent(app, 13455 compatibilityInfoForPackageLocked(app), backupMode); 13456 } catch (RemoteException e) { 13457 // Will time out on the backup manager side 13458 } 13459 } else { 13460 if (DEBUG_BACKUP) Slog.v(TAG, "Agent proc not running, waiting for attach"); 13461 } 13462 // Invariants: at this point, the target app process exists and the application 13463 // is either already running or in the process of coming up. mBackupTarget and 13464 // mBackupAppName describe the app, so that when it binds back to the AM we 13465 // know that it's scheduled for a backup-agent operation. 13466 } 13467 13468 return true; 13469 } 13470 13471 @Override 13472 public void clearPendingBackup() { 13473 if (DEBUG_BACKUP) Slog.v(TAG, "clearPendingBackup"); 13474 enforceCallingPermission("android.permission.BACKUP", "clearPendingBackup"); 13475 13476 synchronized (this) { 13477 mBackupTarget = null; 13478 mBackupAppName = null; 13479 } 13480 } 13481 13482 // A backup agent has just come up 13483 public void backupAgentCreated(String agentPackageName, IBinder agent) { 13484 if (DEBUG_BACKUP) Slog.v(TAG, "backupAgentCreated: " + agentPackageName 13485 + " = " + agent); 13486 13487 synchronized(this) { 13488 if (!agentPackageName.equals(mBackupAppName)) { 13489 Slog.e(TAG, "Backup agent created for " + agentPackageName + " but not requested!"); 13490 return; 13491 } 13492 } 13493 13494 long oldIdent = Binder.clearCallingIdentity(); 13495 try { 13496 IBackupManager bm = IBackupManager.Stub.asInterface( 13497 ServiceManager.getService(Context.BACKUP_SERVICE)); 13498 bm.agentConnected(agentPackageName, agent); 13499 } catch (RemoteException e) { 13500 // can't happen; the backup manager service is local 13501 } catch (Exception e) { 13502 Slog.w(TAG, "Exception trying to deliver BackupAgent binding: "); 13503 e.printStackTrace(); 13504 } finally { 13505 Binder.restoreCallingIdentity(oldIdent); 13506 } 13507 } 13508 13509 // done with this agent 13510 public void unbindBackupAgent(ApplicationInfo appInfo) { 13511 if (DEBUG_BACKUP) Slog.v(TAG, "unbindBackupAgent: " + appInfo); 13512 if (appInfo == null) { 13513 Slog.w(TAG, "unbind backup agent for null app"); 13514 return; 13515 } 13516 13517 synchronized(this) { 13518 try { 13519 if (mBackupAppName == null) { 13520 Slog.w(TAG, "Unbinding backup agent with no active backup"); 13521 return; 13522 } 13523 13524 if (!mBackupAppName.equals(appInfo.packageName)) { 13525 Slog.e(TAG, "Unbind of " + appInfo + " but is not the current backup target"); 13526 return; 13527 } 13528 13529 // Not backing this app up any more; reset its OOM adjustment 13530 final ProcessRecord proc = mBackupTarget.app; 13531 updateOomAdjLocked(proc); 13532 13533 // If the app crashed during backup, 'thread' will be null here 13534 if (proc.thread != null) { 13535 try { 13536 proc.thread.scheduleDestroyBackupAgent(appInfo, 13537 compatibilityInfoForPackageLocked(appInfo)); 13538 } catch (Exception e) { 13539 Slog.e(TAG, "Exception when unbinding backup agent:"); 13540 e.printStackTrace(); 13541 } 13542 } 13543 } finally { 13544 mBackupTarget = null; 13545 mBackupAppName = null; 13546 } 13547 } 13548 } 13549 // ========================================================= 13550 // BROADCASTS 13551 // ========================================================= 13552 13553 private final List getStickiesLocked(String action, IntentFilter filter, 13554 List cur, int userId) { 13555 final ContentResolver resolver = mContext.getContentResolver(); 13556 ArrayMap<String, ArrayList<Intent>> stickies = mStickyBroadcasts.get(userId); 13557 if (stickies == null) { 13558 return cur; 13559 } 13560 final ArrayList<Intent> list = stickies.get(action); 13561 if (list == null) { 13562 return cur; 13563 } 13564 int N = list.size(); 13565 for (int i=0; i<N; i++) { 13566 Intent intent = list.get(i); 13567 if (filter.match(resolver, intent, true, TAG) >= 0) { 13568 if (cur == null) { 13569 cur = new ArrayList<Intent>(); 13570 } 13571 cur.add(intent); 13572 } 13573 } 13574 return cur; 13575 } 13576 13577 boolean isPendingBroadcastProcessLocked(int pid) { 13578 return mFgBroadcastQueue.isPendingBroadcastProcessLocked(pid) 13579 || mBgBroadcastQueue.isPendingBroadcastProcessLocked(pid); 13580 } 13581 13582 void skipPendingBroadcastLocked(int pid) { 13583 Slog.w(TAG, "Unattached app died before broadcast acknowledged, skipping"); 13584 for (BroadcastQueue queue : mBroadcastQueues) { 13585 queue.skipPendingBroadcastLocked(pid); 13586 } 13587 } 13588 13589 // The app just attached; send any pending broadcasts that it should receive 13590 boolean sendPendingBroadcastsLocked(ProcessRecord app) { 13591 boolean didSomething = false; 13592 for (BroadcastQueue queue : mBroadcastQueues) { 13593 didSomething |= queue.sendPendingBroadcastsLocked(app); 13594 } 13595 return didSomething; 13596 } 13597 13598 public Intent registerReceiver(IApplicationThread caller, String callerPackage, 13599 IIntentReceiver receiver, IntentFilter filter, String permission, int userId) { 13600 enforceNotIsolatedCaller("registerReceiver"); 13601 int callingUid; 13602 int callingPid; 13603 synchronized(this) { 13604 ProcessRecord callerApp = null; 13605 if (caller != null) { 13606 callerApp = getRecordForAppLocked(caller); 13607 if (callerApp == null) { 13608 throw new SecurityException( 13609 "Unable to find app for caller " + caller 13610 + " (pid=" + Binder.getCallingPid() 13611 + ") when registering receiver " + receiver); 13612 } 13613 if (callerApp.info.uid != Process.SYSTEM_UID && 13614 !callerApp.pkgList.containsKey(callerPackage) && 13615 !"android".equals(callerPackage)) { 13616 throw new SecurityException("Given caller package " + callerPackage 13617 + " is not running in process " + callerApp); 13618 } 13619 callingUid = callerApp.info.uid; 13620 callingPid = callerApp.pid; 13621 } else { 13622 callerPackage = null; 13623 callingUid = Binder.getCallingUid(); 13624 callingPid = Binder.getCallingPid(); 13625 } 13626 13627 userId = this.handleIncomingUser(callingPid, callingUid, userId, 13628 true, true, "registerReceiver", callerPackage); 13629 13630 List allSticky = null; 13631 13632 // Look for any matching sticky broadcasts... 13633 Iterator actions = filter.actionsIterator(); 13634 if (actions != null) { 13635 while (actions.hasNext()) { 13636 String action = (String)actions.next(); 13637 allSticky = getStickiesLocked(action, filter, allSticky, 13638 UserHandle.USER_ALL); 13639 allSticky = getStickiesLocked(action, filter, allSticky, 13640 UserHandle.getUserId(callingUid)); 13641 } 13642 } else { 13643 allSticky = getStickiesLocked(null, filter, allSticky, 13644 UserHandle.USER_ALL); 13645 allSticky = getStickiesLocked(null, filter, allSticky, 13646 UserHandle.getUserId(callingUid)); 13647 } 13648 13649 // The first sticky in the list is returned directly back to 13650 // the client. 13651 Intent sticky = allSticky != null ? (Intent)allSticky.get(0) : null; 13652 13653 if (DEBUG_BROADCAST) Slog.v(TAG, "Register receiver " + filter 13654 + ": " + sticky); 13655 13656 if (receiver == null) { 13657 return sticky; 13658 } 13659 13660 ReceiverList rl 13661 = (ReceiverList)mRegisteredReceivers.get(receiver.asBinder()); 13662 if (rl == null) { 13663 rl = new ReceiverList(this, callerApp, callingPid, callingUid, 13664 userId, receiver); 13665 if (rl.app != null) { 13666 rl.app.receivers.add(rl); 13667 } else { 13668 try { 13669 receiver.asBinder().linkToDeath(rl, 0); 13670 } catch (RemoteException e) { 13671 return sticky; 13672 } 13673 rl.linkedToDeath = true; 13674 } 13675 mRegisteredReceivers.put(receiver.asBinder(), rl); 13676 } else if (rl.uid != callingUid) { 13677 throw new IllegalArgumentException( 13678 "Receiver requested to register for uid " + callingUid 13679 + " was previously registered for uid " + rl.uid); 13680 } else if (rl.pid != callingPid) { 13681 throw new IllegalArgumentException( 13682 "Receiver requested to register for pid " + callingPid 13683 + " was previously registered for pid " + rl.pid); 13684 } else if (rl.userId != userId) { 13685 throw new IllegalArgumentException( 13686 "Receiver requested to register for user " + userId 13687 + " was previously registered for user " + rl.userId); 13688 } 13689 BroadcastFilter bf = new BroadcastFilter(filter, rl, callerPackage, 13690 permission, callingUid, userId); 13691 rl.add(bf); 13692 if (!bf.debugCheck()) { 13693 Slog.w(TAG, "==> For Dynamic broadast"); 13694 } 13695 mReceiverResolver.addFilter(bf); 13696 13697 // Enqueue broadcasts for all existing stickies that match 13698 // this filter. 13699 if (allSticky != null) { 13700 ArrayList receivers = new ArrayList(); 13701 receivers.add(bf); 13702 13703 int N = allSticky.size(); 13704 for (int i=0; i<N; i++) { 13705 Intent intent = (Intent)allSticky.get(i); 13706 BroadcastQueue queue = broadcastQueueForIntent(intent); 13707 BroadcastRecord r = new BroadcastRecord(queue, intent, null, 13708 null, -1, -1, null, null, AppOpsManager.OP_NONE, receivers, null, 0, 13709 null, null, false, true, true, -1); 13710 queue.enqueueParallelBroadcastLocked(r); 13711 queue.scheduleBroadcastsLocked(); 13712 } 13713 } 13714 13715 return sticky; 13716 } 13717 } 13718 13719 public void unregisterReceiver(IIntentReceiver receiver) { 13720 if (DEBUG_BROADCAST) Slog.v(TAG, "Unregister receiver: " + receiver); 13721 13722 final long origId = Binder.clearCallingIdentity(); 13723 try { 13724 boolean doTrim = false; 13725 13726 synchronized(this) { 13727 ReceiverList rl = mRegisteredReceivers.get(receiver.asBinder()); 13728 if (rl != null) { 13729 if (rl.curBroadcast != null) { 13730 BroadcastRecord r = rl.curBroadcast; 13731 final boolean doNext = finishReceiverLocked( 13732 receiver.asBinder(), r.resultCode, r.resultData, 13733 r.resultExtras, r.resultAbort); 13734 if (doNext) { 13735 doTrim = true; 13736 r.queue.processNextBroadcast(false); 13737 } 13738 } 13739 13740 if (rl.app != null) { 13741 rl.app.receivers.remove(rl); 13742 } 13743 removeReceiverLocked(rl); 13744 if (rl.linkedToDeath) { 13745 rl.linkedToDeath = false; 13746 rl.receiver.asBinder().unlinkToDeath(rl, 0); 13747 } 13748 } 13749 } 13750 13751 // If we actually concluded any broadcasts, we might now be able 13752 // to trim the recipients' apps from our working set 13753 if (doTrim) { 13754 trimApplications(); 13755 return; 13756 } 13757 13758 } finally { 13759 Binder.restoreCallingIdentity(origId); 13760 } 13761 } 13762 13763 void removeReceiverLocked(ReceiverList rl) { 13764 mRegisteredReceivers.remove(rl.receiver.asBinder()); 13765 int N = rl.size(); 13766 for (int i=0; i<N; i++) { 13767 mReceiverResolver.removeFilter(rl.get(i)); 13768 } 13769 } 13770 13771 private final void sendPackageBroadcastLocked(int cmd, String[] packages, int userId) { 13772 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 13773 ProcessRecord r = mLruProcesses.get(i); 13774 if (r.thread != null && (userId == UserHandle.USER_ALL || r.userId == userId)) { 13775 try { 13776 r.thread.dispatchPackageBroadcast(cmd, packages); 13777 } catch (RemoteException ex) { 13778 } 13779 } 13780 } 13781 } 13782 13783 private List<ResolveInfo> collectReceiverComponents(Intent intent, String resolvedType, 13784 int[] users) { 13785 List<ResolveInfo> receivers = null; 13786 try { 13787 HashSet<ComponentName> singleUserReceivers = null; 13788 boolean scannedFirstReceivers = false; 13789 for (int user : users) { 13790 List<ResolveInfo> newReceivers = AppGlobals.getPackageManager() 13791 .queryIntentReceivers(intent, resolvedType, STOCK_PM_FLAGS, user); 13792 if (user != 0 && newReceivers != null) { 13793 // If this is not the primary user, we need to check for 13794 // any receivers that should be filtered out. 13795 for (int i=0; i<newReceivers.size(); i++) { 13796 ResolveInfo ri = newReceivers.get(i); 13797 if ((ri.activityInfo.flags&ActivityInfo.FLAG_PRIMARY_USER_ONLY) != 0) { 13798 newReceivers.remove(i); 13799 i--; 13800 } 13801 } 13802 } 13803 if (newReceivers != null && newReceivers.size() == 0) { 13804 newReceivers = null; 13805 } 13806 if (receivers == null) { 13807 receivers = newReceivers; 13808 } else if (newReceivers != null) { 13809 // We need to concatenate the additional receivers 13810 // found with what we have do far. This would be easy, 13811 // but we also need to de-dup any receivers that are 13812 // singleUser. 13813 if (!scannedFirstReceivers) { 13814 // Collect any single user receivers we had already retrieved. 13815 scannedFirstReceivers = true; 13816 for (int i=0; i<receivers.size(); i++) { 13817 ResolveInfo ri = receivers.get(i); 13818 if ((ri.activityInfo.flags&ActivityInfo.FLAG_SINGLE_USER) != 0) { 13819 ComponentName cn = new ComponentName( 13820 ri.activityInfo.packageName, ri.activityInfo.name); 13821 if (singleUserReceivers == null) { 13822 singleUserReceivers = new HashSet<ComponentName>(); 13823 } 13824 singleUserReceivers.add(cn); 13825 } 13826 } 13827 } 13828 // Add the new results to the existing results, tracking 13829 // and de-dupping single user receivers. 13830 for (int i=0; i<newReceivers.size(); i++) { 13831 ResolveInfo ri = newReceivers.get(i); 13832 if ((ri.activityInfo.flags&ActivityInfo.FLAG_SINGLE_USER) != 0) { 13833 ComponentName cn = new ComponentName( 13834 ri.activityInfo.packageName, ri.activityInfo.name); 13835 if (singleUserReceivers == null) { 13836 singleUserReceivers = new HashSet<ComponentName>(); 13837 } 13838 if (!singleUserReceivers.contains(cn)) { 13839 singleUserReceivers.add(cn); 13840 receivers.add(ri); 13841 } 13842 } else { 13843 receivers.add(ri); 13844 } 13845 } 13846 } 13847 } 13848 } catch (RemoteException ex) { 13849 // pm is in same process, this will never happen. 13850 } 13851 return receivers; 13852 } 13853 13854 private final int broadcastIntentLocked(ProcessRecord callerApp, 13855 String callerPackage, Intent intent, String resolvedType, 13856 IIntentReceiver resultTo, int resultCode, String resultData, 13857 Bundle map, String requiredPermission, int appOp, 13858 boolean ordered, boolean sticky, int callingPid, int callingUid, 13859 int userId) { 13860 intent = new Intent(intent); 13861 13862 // By default broadcasts do not go to stopped apps. 13863 intent.addFlags(Intent.FLAG_EXCLUDE_STOPPED_PACKAGES); 13864 13865 if (DEBUG_BROADCAST_LIGHT) Slog.v( 13866 TAG, (sticky ? "Broadcast sticky: ": "Broadcast: ") + intent 13867 + " ordered=" + ordered + " userid=" + userId); 13868 if ((resultTo != null) && !ordered) { 13869 Slog.w(TAG, "Broadcast " + intent + " not ordered but result callback requested!"); 13870 } 13871 13872 userId = handleIncomingUser(callingPid, callingUid, userId, 13873 true, false, "broadcast", callerPackage); 13874 13875 // Make sure that the user who is receiving this broadcast is started. 13876 // If not, we will just skip it. 13877 if (userId != UserHandle.USER_ALL && mStartedUsers.get(userId) == null) { 13878 if (callingUid != Process.SYSTEM_UID || (intent.getFlags() 13879 & Intent.FLAG_RECEIVER_BOOT_UPGRADE) == 0) { 13880 Slog.w(TAG, "Skipping broadcast of " + intent 13881 + ": user " + userId + " is stopped"); 13882 return ActivityManager.BROADCAST_SUCCESS; 13883 } 13884 } 13885 13886 /* 13887 * Prevent non-system code (defined here to be non-persistent 13888 * processes) from sending protected broadcasts. 13889 */ 13890 int callingAppId = UserHandle.getAppId(callingUid); 13891 if (callingAppId == Process.SYSTEM_UID || callingAppId == Process.PHONE_UID 13892 || callingAppId == Process.SHELL_UID || callingAppId == Process.BLUETOOTH_UID 13893 || callingUid == 0) { 13894 // Always okay. 13895 } else if (callerApp == null || !callerApp.persistent) { 13896 try { 13897 if (AppGlobals.getPackageManager().isProtectedBroadcast( 13898 intent.getAction())) { 13899 String msg = "Permission Denial: not allowed to send broadcast " 13900 + intent.getAction() + " from pid=" 13901 + callingPid + ", uid=" + callingUid; 13902 Slog.w(TAG, msg); 13903 throw new SecurityException(msg); 13904 } else if (AppWidgetManager.ACTION_APPWIDGET_CONFIGURE.equals(intent.getAction())) { 13905 // Special case for compatibility: we don't want apps to send this, 13906 // but historically it has not been protected and apps may be using it 13907 // to poke their own app widget. So, instead of making it protected, 13908 // just limit it to the caller. 13909 if (callerApp == null) { 13910 String msg = "Permission Denial: not allowed to send broadcast " 13911 + intent.getAction() + " from unknown caller."; 13912 Slog.w(TAG, msg); 13913 throw new SecurityException(msg); 13914 } else if (intent.getComponent() != null) { 13915 // They are good enough to send to an explicit component... verify 13916 // it is being sent to the calling app. 13917 if (!intent.getComponent().getPackageName().equals( 13918 callerApp.info.packageName)) { 13919 String msg = "Permission Denial: not allowed to send broadcast " 13920 + intent.getAction() + " to " 13921 + intent.getComponent().getPackageName() + " from " 13922 + callerApp.info.packageName; 13923 Slog.w(TAG, msg); 13924 throw new SecurityException(msg); 13925 } 13926 } else { 13927 // Limit broadcast to their own package. 13928 intent.setPackage(callerApp.info.packageName); 13929 } 13930 } 13931 } catch (RemoteException e) { 13932 Slog.w(TAG, "Remote exception", e); 13933 return ActivityManager.BROADCAST_SUCCESS; 13934 } 13935 } 13936 13937 // Handle special intents: if this broadcast is from the package 13938 // manager about a package being removed, we need to remove all of 13939 // its activities from the history stack. 13940 final boolean uidRemoved = Intent.ACTION_UID_REMOVED.equals( 13941 intent.getAction()); 13942 if (Intent.ACTION_PACKAGE_REMOVED.equals(intent.getAction()) 13943 || Intent.ACTION_PACKAGE_CHANGED.equals(intent.getAction()) 13944 || Intent.ACTION_EXTERNAL_APPLICATIONS_UNAVAILABLE.equals(intent.getAction()) 13945 || uidRemoved) { 13946 if (checkComponentPermission( 13947 android.Manifest.permission.BROADCAST_PACKAGE_REMOVED, 13948 callingPid, callingUid, -1, true) 13949 == PackageManager.PERMISSION_GRANTED) { 13950 if (uidRemoved) { 13951 final Bundle intentExtras = intent.getExtras(); 13952 final int uid = intentExtras != null 13953 ? intentExtras.getInt(Intent.EXTRA_UID) : -1; 13954 if (uid >= 0) { 13955 BatteryStatsImpl bs = mBatteryStatsService.getActiveStatistics(); 13956 synchronized (bs) { 13957 bs.removeUidStatsLocked(uid); 13958 } 13959 mAppOpsService.uidRemoved(uid); 13960 } 13961 } else { 13962 // If resources are unavailable just force stop all 13963 // those packages and flush the attribute cache as well. 13964 if (Intent.ACTION_EXTERNAL_APPLICATIONS_UNAVAILABLE.equals(intent.getAction())) { 13965 String list[] = intent.getStringArrayExtra(Intent.EXTRA_CHANGED_PACKAGE_LIST); 13966 if (list != null && (list.length > 0)) { 13967 for (String pkg : list) { 13968 forceStopPackageLocked(pkg, -1, false, true, true, false, false, userId, 13969 "storage unmount"); 13970 } 13971 sendPackageBroadcastLocked( 13972 IApplicationThread.EXTERNAL_STORAGE_UNAVAILABLE, list, userId); 13973 } 13974 } else { 13975 Uri data = intent.getData(); 13976 String ssp; 13977 if (data != null && (ssp=data.getSchemeSpecificPart()) != null) { 13978 boolean removed = Intent.ACTION_PACKAGE_REMOVED.equals( 13979 intent.getAction()); 13980 boolean fullUninstall = removed && 13981 !intent.getBooleanExtra(Intent.EXTRA_REPLACING, false); 13982 if (!intent.getBooleanExtra(Intent.EXTRA_DONT_KILL_APP, false)) { 13983 forceStopPackageLocked(ssp, UserHandle.getAppId( 13984 intent.getIntExtra(Intent.EXTRA_UID, -1)), false, true, true, 13985 false, fullUninstall, userId, 13986 removed ? "pkg removed" : "pkg changed"); 13987 } 13988 if (removed) { 13989 sendPackageBroadcastLocked(IApplicationThread.PACKAGE_REMOVED, 13990 new String[] {ssp}, userId); 13991 if (!intent.getBooleanExtra(Intent.EXTRA_REPLACING, false)) { 13992 mAppOpsService.packageRemoved( 13993 intent.getIntExtra(Intent.EXTRA_UID, -1), ssp); 13994 13995 // Remove all permissions granted from/to this package 13996 removeUriPermissionsForPackageLocked(ssp, userId, true); 13997 } 13998 } 13999 } 14000 } 14001 } 14002 } else { 14003 String msg = "Permission Denial: " + intent.getAction() 14004 + " broadcast from " + callerPackage + " (pid=" + callingPid 14005 + ", uid=" + callingUid + ")" 14006 + " requires " 14007 + android.Manifest.permission.BROADCAST_PACKAGE_REMOVED; 14008 Slog.w(TAG, msg); 14009 throw new SecurityException(msg); 14010 } 14011 14012 // Special case for adding a package: by default turn on compatibility 14013 // mode. 14014 } else if (Intent.ACTION_PACKAGE_ADDED.equals(intent.getAction())) { 14015 Uri data = intent.getData(); 14016 String ssp; 14017 if (data != null && (ssp=data.getSchemeSpecificPart()) != null) { 14018 mCompatModePackages.handlePackageAddedLocked(ssp, 14019 intent.getBooleanExtra(Intent.EXTRA_REPLACING, false)); 14020 } 14021 } 14022 14023 /* 14024 * If this is the time zone changed action, queue up a message that will reset the timezone 14025 * of all currently running processes. This message will get queued up before the broadcast 14026 * happens. 14027 */ 14028 if (Intent.ACTION_TIMEZONE_CHANGED.equals(intent.getAction())) { 14029 mHandler.sendEmptyMessage(UPDATE_TIME_ZONE); 14030 } 14031 14032 /* 14033 * If the user set the time, let all running processes know. 14034 */ 14035 if (Intent.ACTION_TIME_CHANGED.equals(intent.getAction())) { 14036 final int is24Hour = intent.getBooleanExtra( 14037 Intent.EXTRA_TIME_PREF_24_HOUR_FORMAT, false) ? 1 : 0; 14038 mHandler.sendMessage(mHandler.obtainMessage(UPDATE_TIME, is24Hour, 0)); 14039 } 14040 14041 if (Intent.ACTION_CLEAR_DNS_CACHE.equals(intent.getAction())) { 14042 mHandler.sendEmptyMessage(CLEAR_DNS_CACHE_MSG); 14043 } 14044 14045 if (Proxy.PROXY_CHANGE_ACTION.equals(intent.getAction())) { 14046 ProxyInfo proxy = intent.getParcelableExtra(Proxy.EXTRA_PROXY_INFO); 14047 mHandler.sendMessage(mHandler.obtainMessage(UPDATE_HTTP_PROXY_MSG, proxy)); 14048 } 14049 14050 // Add to the sticky list if requested. 14051 if (sticky) { 14052 if (checkPermission(android.Manifest.permission.BROADCAST_STICKY, 14053 callingPid, callingUid) 14054 != PackageManager.PERMISSION_GRANTED) { 14055 String msg = "Permission Denial: broadcastIntent() requesting a sticky broadcast from pid=" 14056 + callingPid + ", uid=" + callingUid 14057 + " requires " + android.Manifest.permission.BROADCAST_STICKY; 14058 Slog.w(TAG, msg); 14059 throw new SecurityException(msg); 14060 } 14061 if (requiredPermission != null) { 14062 Slog.w(TAG, "Can't broadcast sticky intent " + intent 14063 + " and enforce permission " + requiredPermission); 14064 return ActivityManager.BROADCAST_STICKY_CANT_HAVE_PERMISSION; 14065 } 14066 if (intent.getComponent() != null) { 14067 throw new SecurityException( 14068 "Sticky broadcasts can't target a specific component"); 14069 } 14070 // We use userId directly here, since the "all" target is maintained 14071 // as a separate set of sticky broadcasts. 14072 if (userId != UserHandle.USER_ALL) { 14073 // But first, if this is not a broadcast to all users, then 14074 // make sure it doesn't conflict with an existing broadcast to 14075 // all users. 14076 ArrayMap<String, ArrayList<Intent>> stickies = mStickyBroadcasts.get( 14077 UserHandle.USER_ALL); 14078 if (stickies != null) { 14079 ArrayList<Intent> list = stickies.get(intent.getAction()); 14080 if (list != null) { 14081 int N = list.size(); 14082 int i; 14083 for (i=0; i<N; i++) { 14084 if (intent.filterEquals(list.get(i))) { 14085 throw new IllegalArgumentException( 14086 "Sticky broadcast " + intent + " for user " 14087 + userId + " conflicts with existing global broadcast"); 14088 } 14089 } 14090 } 14091 } 14092 } 14093 ArrayMap<String, ArrayList<Intent>> stickies = mStickyBroadcasts.get(userId); 14094 if (stickies == null) { 14095 stickies = new ArrayMap<String, ArrayList<Intent>>(); 14096 mStickyBroadcasts.put(userId, stickies); 14097 } 14098 ArrayList<Intent> list = stickies.get(intent.getAction()); 14099 if (list == null) { 14100 list = new ArrayList<Intent>(); 14101 stickies.put(intent.getAction(), list); 14102 } 14103 int N = list.size(); 14104 int i; 14105 for (i=0; i<N; i++) { 14106 if (intent.filterEquals(list.get(i))) { 14107 // This sticky already exists, replace it. 14108 list.set(i, new Intent(intent)); 14109 break; 14110 } 14111 } 14112 if (i >= N) { 14113 list.add(new Intent(intent)); 14114 } 14115 } 14116 14117 int[] users; 14118 if (userId == UserHandle.USER_ALL) { 14119 // Caller wants broadcast to go to all started users. 14120 users = mStartedUserArray; 14121 } else { 14122 // Caller wants broadcast to go to one specific user. 14123 users = new int[] {userId}; 14124 } 14125 14126 // Figure out who all will receive this broadcast. 14127 List receivers = null; 14128 List<BroadcastFilter> registeredReceivers = null; 14129 // Need to resolve the intent to interested receivers... 14130 if ((intent.getFlags()&Intent.FLAG_RECEIVER_REGISTERED_ONLY) 14131 == 0) { 14132 receivers = collectReceiverComponents(intent, resolvedType, users); 14133 } 14134 if (intent.getComponent() == null) { 14135 registeredReceivers = mReceiverResolver.queryIntent(intent, 14136 resolvedType, false, userId); 14137 } 14138 14139 final boolean replacePending = 14140 (intent.getFlags()&Intent.FLAG_RECEIVER_REPLACE_PENDING) != 0; 14141 14142 if (DEBUG_BROADCAST) Slog.v(TAG, "Enqueing broadcast: " + intent.getAction() 14143 + " replacePending=" + replacePending); 14144 14145 int NR = registeredReceivers != null ? registeredReceivers.size() : 0; 14146 if (!ordered && NR > 0) { 14147 // If we are not serializing this broadcast, then send the 14148 // registered receivers separately so they don't wait for the 14149 // components to be launched. 14150 final BroadcastQueue queue = broadcastQueueForIntent(intent); 14151 BroadcastRecord r = new BroadcastRecord(queue, intent, callerApp, 14152 callerPackage, callingPid, callingUid, resolvedType, requiredPermission, 14153 appOp, registeredReceivers, resultTo, resultCode, resultData, map, 14154 ordered, sticky, false, userId); 14155 if (DEBUG_BROADCAST) Slog.v( 14156 TAG, "Enqueueing parallel broadcast " + r); 14157 final boolean replaced = replacePending && queue.replaceParallelBroadcastLocked(r); 14158 if (!replaced) { 14159 queue.enqueueParallelBroadcastLocked(r); 14160 queue.scheduleBroadcastsLocked(); 14161 } 14162 registeredReceivers = null; 14163 NR = 0; 14164 } 14165 14166 // Merge into one list. 14167 int ir = 0; 14168 if (receivers != null) { 14169 // A special case for PACKAGE_ADDED: do not allow the package 14170 // being added to see this broadcast. This prevents them from 14171 // using this as a back door to get run as soon as they are 14172 // installed. Maybe in the future we want to have a special install 14173 // broadcast or such for apps, but we'd like to deliberately make 14174 // this decision. 14175 String skipPackages[] = null; 14176 if (Intent.ACTION_PACKAGE_ADDED.equals(intent.getAction()) 14177 || Intent.ACTION_PACKAGE_RESTARTED.equals(intent.getAction()) 14178 || Intent.ACTION_PACKAGE_DATA_CLEARED.equals(intent.getAction())) { 14179 Uri data = intent.getData(); 14180 if (data != null) { 14181 String pkgName = data.getSchemeSpecificPart(); 14182 if (pkgName != null) { 14183 skipPackages = new String[] { pkgName }; 14184 } 14185 } 14186 } else if (Intent.ACTION_EXTERNAL_APPLICATIONS_AVAILABLE.equals(intent.getAction())) { 14187 skipPackages = intent.getStringArrayExtra(Intent.EXTRA_CHANGED_PACKAGE_LIST); 14188 } 14189 if (skipPackages != null && (skipPackages.length > 0)) { 14190 for (String skipPackage : skipPackages) { 14191 if (skipPackage != null) { 14192 int NT = receivers.size(); 14193 for (int it=0; it<NT; it++) { 14194 ResolveInfo curt = (ResolveInfo)receivers.get(it); 14195 if (curt.activityInfo.packageName.equals(skipPackage)) { 14196 receivers.remove(it); 14197 it--; 14198 NT--; 14199 } 14200 } 14201 } 14202 } 14203 } 14204 14205 int NT = receivers != null ? receivers.size() : 0; 14206 int it = 0; 14207 ResolveInfo curt = null; 14208 BroadcastFilter curr = null; 14209 while (it < NT && ir < NR) { 14210 if (curt == null) { 14211 curt = (ResolveInfo)receivers.get(it); 14212 } 14213 if (curr == null) { 14214 curr = registeredReceivers.get(ir); 14215 } 14216 if (curr.getPriority() >= curt.priority) { 14217 // Insert this broadcast record into the final list. 14218 receivers.add(it, curr); 14219 ir++; 14220 curr = null; 14221 it++; 14222 NT++; 14223 } else { 14224 // Skip to the next ResolveInfo in the final list. 14225 it++; 14226 curt = null; 14227 } 14228 } 14229 } 14230 while (ir < NR) { 14231 if (receivers == null) { 14232 receivers = new ArrayList(); 14233 } 14234 receivers.add(registeredReceivers.get(ir)); 14235 ir++; 14236 } 14237 14238 if ((receivers != null && receivers.size() > 0) 14239 || resultTo != null) { 14240 BroadcastQueue queue = broadcastQueueForIntent(intent); 14241 BroadcastRecord r = new BroadcastRecord(queue, intent, callerApp, 14242 callerPackage, callingPid, callingUid, resolvedType, 14243 requiredPermission, appOp, receivers, resultTo, resultCode, 14244 resultData, map, ordered, sticky, false, userId); 14245 if (DEBUG_BROADCAST) Slog.v( 14246 TAG, "Enqueueing ordered broadcast " + r 14247 + ": prev had " + queue.mOrderedBroadcasts.size()); 14248 if (DEBUG_BROADCAST) { 14249 int seq = r.intent.getIntExtra("seq", -1); 14250 Slog.i(TAG, "Enqueueing broadcast " + r.intent.getAction() + " seq=" + seq); 14251 } 14252 boolean replaced = replacePending && queue.replaceOrderedBroadcastLocked(r); 14253 if (!replaced) { 14254 queue.enqueueOrderedBroadcastLocked(r); 14255 queue.scheduleBroadcastsLocked(); 14256 } 14257 } 14258 14259 return ActivityManager.BROADCAST_SUCCESS; 14260 } 14261 14262 final Intent verifyBroadcastLocked(Intent intent) { 14263 // Refuse possible leaked file descriptors 14264 if (intent != null && intent.hasFileDescriptors() == true) { 14265 throw new IllegalArgumentException("File descriptors passed in Intent"); 14266 } 14267 14268 int flags = intent.getFlags(); 14269 14270 if (!mProcessesReady) { 14271 // if the caller really truly claims to know what they're doing, go 14272 // ahead and allow the broadcast without launching any receivers 14273 if ((flags&Intent.FLAG_RECEIVER_REGISTERED_ONLY_BEFORE_BOOT) != 0) { 14274 intent = new Intent(intent); 14275 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 14276 } else if ((flags&Intent.FLAG_RECEIVER_REGISTERED_ONLY) == 0) { 14277 Slog.e(TAG, "Attempt to launch receivers of broadcast intent " + intent 14278 + " before boot completion"); 14279 throw new IllegalStateException("Cannot broadcast before boot completed"); 14280 } 14281 } 14282 14283 if ((flags&Intent.FLAG_RECEIVER_BOOT_UPGRADE) != 0) { 14284 throw new IllegalArgumentException( 14285 "Can't use FLAG_RECEIVER_BOOT_UPGRADE here"); 14286 } 14287 14288 return intent; 14289 } 14290 14291 public final int broadcastIntent(IApplicationThread caller, 14292 Intent intent, String resolvedType, IIntentReceiver resultTo, 14293 int resultCode, String resultData, Bundle map, 14294 String requiredPermission, int appOp, boolean serialized, boolean sticky, int userId) { 14295 enforceNotIsolatedCaller("broadcastIntent"); 14296 synchronized(this) { 14297 intent = verifyBroadcastLocked(intent); 14298 14299 final ProcessRecord callerApp = getRecordForAppLocked(caller); 14300 final int callingPid = Binder.getCallingPid(); 14301 final int callingUid = Binder.getCallingUid(); 14302 final long origId = Binder.clearCallingIdentity(); 14303 int res = broadcastIntentLocked(callerApp, 14304 callerApp != null ? callerApp.info.packageName : null, 14305 intent, resolvedType, resultTo, 14306 resultCode, resultData, map, requiredPermission, appOp, serialized, sticky, 14307 callingPid, callingUid, userId); 14308 Binder.restoreCallingIdentity(origId); 14309 return res; 14310 } 14311 } 14312 14313 int broadcastIntentInPackage(String packageName, int uid, 14314 Intent intent, String resolvedType, IIntentReceiver resultTo, 14315 int resultCode, String resultData, Bundle map, 14316 String requiredPermission, boolean serialized, boolean sticky, int userId) { 14317 synchronized(this) { 14318 intent = verifyBroadcastLocked(intent); 14319 14320 final long origId = Binder.clearCallingIdentity(); 14321 int res = broadcastIntentLocked(null, packageName, intent, resolvedType, 14322 resultTo, resultCode, resultData, map, requiredPermission, 14323 AppOpsManager.OP_NONE, serialized, sticky, -1, uid, userId); 14324 Binder.restoreCallingIdentity(origId); 14325 return res; 14326 } 14327 } 14328 14329 public final void unbroadcastIntent(IApplicationThread caller, Intent intent, int userId) { 14330 // Refuse possible leaked file descriptors 14331 if (intent != null && intent.hasFileDescriptors() == true) { 14332 throw new IllegalArgumentException("File descriptors passed in Intent"); 14333 } 14334 14335 userId = handleIncomingUser(Binder.getCallingPid(), 14336 Binder.getCallingUid(), userId, true, false, "removeStickyBroadcast", null); 14337 14338 synchronized(this) { 14339 if (checkCallingPermission(android.Manifest.permission.BROADCAST_STICKY) 14340 != PackageManager.PERMISSION_GRANTED) { 14341 String msg = "Permission Denial: unbroadcastIntent() from pid=" 14342 + Binder.getCallingPid() 14343 + ", uid=" + Binder.getCallingUid() 14344 + " requires " + android.Manifest.permission.BROADCAST_STICKY; 14345 Slog.w(TAG, msg); 14346 throw new SecurityException(msg); 14347 } 14348 ArrayMap<String, ArrayList<Intent>> stickies = mStickyBroadcasts.get(userId); 14349 if (stickies != null) { 14350 ArrayList<Intent> list = stickies.get(intent.getAction()); 14351 if (list != null) { 14352 int N = list.size(); 14353 int i; 14354 for (i=0; i<N; i++) { 14355 if (intent.filterEquals(list.get(i))) { 14356 list.remove(i); 14357 break; 14358 } 14359 } 14360 if (list.size() <= 0) { 14361 stickies.remove(intent.getAction()); 14362 } 14363 } 14364 if (stickies.size() <= 0) { 14365 mStickyBroadcasts.remove(userId); 14366 } 14367 } 14368 } 14369 } 14370 14371 private final boolean finishReceiverLocked(IBinder receiver, int resultCode, 14372 String resultData, Bundle resultExtras, boolean resultAbort) { 14373 final BroadcastRecord r = broadcastRecordForReceiverLocked(receiver); 14374 if (r == null) { 14375 Slog.w(TAG, "finishReceiver called but not found on queue"); 14376 return false; 14377 } 14378 14379 return r.queue.finishReceiverLocked(r, resultCode, resultData, resultExtras, resultAbort, false); 14380 } 14381 14382 void backgroundServicesFinishedLocked(int userId) { 14383 for (BroadcastQueue queue : mBroadcastQueues) { 14384 queue.backgroundServicesFinishedLocked(userId); 14385 } 14386 } 14387 14388 public void finishReceiver(IBinder who, int resultCode, String resultData, 14389 Bundle resultExtras, boolean resultAbort) { 14390 if (DEBUG_BROADCAST) Slog.v(TAG, "Finish receiver: " + who); 14391 14392 // Refuse possible leaked file descriptors 14393 if (resultExtras != null && resultExtras.hasFileDescriptors()) { 14394 throw new IllegalArgumentException("File descriptors passed in Bundle"); 14395 } 14396 14397 final long origId = Binder.clearCallingIdentity(); 14398 try { 14399 boolean doNext = false; 14400 BroadcastRecord r; 14401 14402 synchronized(this) { 14403 r = broadcastRecordForReceiverLocked(who); 14404 if (r != null) { 14405 doNext = r.queue.finishReceiverLocked(r, resultCode, 14406 resultData, resultExtras, resultAbort, true); 14407 } 14408 } 14409 14410 if (doNext) { 14411 r.queue.processNextBroadcast(false); 14412 } 14413 trimApplications(); 14414 } finally { 14415 Binder.restoreCallingIdentity(origId); 14416 } 14417 } 14418 14419 // ========================================================= 14420 // INSTRUMENTATION 14421 // ========================================================= 14422 14423 public boolean startInstrumentation(ComponentName className, 14424 String profileFile, int flags, Bundle arguments, 14425 IInstrumentationWatcher watcher, IUiAutomationConnection uiAutomationConnection, 14426 int userId, String abiOverride) { 14427 enforceNotIsolatedCaller("startInstrumentation"); 14428 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 14429 userId, false, true, "startInstrumentation", null); 14430 // Refuse possible leaked file descriptors 14431 if (arguments != null && arguments.hasFileDescriptors()) { 14432 throw new IllegalArgumentException("File descriptors passed in Bundle"); 14433 } 14434 14435 synchronized(this) { 14436 InstrumentationInfo ii = null; 14437 ApplicationInfo ai = null; 14438 try { 14439 ii = mContext.getPackageManager().getInstrumentationInfo( 14440 className, STOCK_PM_FLAGS); 14441 ai = AppGlobals.getPackageManager().getApplicationInfo( 14442 ii.targetPackage, STOCK_PM_FLAGS, userId); 14443 } catch (PackageManager.NameNotFoundException e) { 14444 } catch (RemoteException e) { 14445 } 14446 if (ii == null) { 14447 reportStartInstrumentationFailure(watcher, className, 14448 "Unable to find instrumentation info for: " + className); 14449 return false; 14450 } 14451 if (ai == null) { 14452 reportStartInstrumentationFailure(watcher, className, 14453 "Unable to find instrumentation target package: " + ii.targetPackage); 14454 return false; 14455 } 14456 14457 int match = mContext.getPackageManager().checkSignatures( 14458 ii.targetPackage, ii.packageName); 14459 if (match < 0 && match != PackageManager.SIGNATURE_FIRST_NOT_SIGNED) { 14460 String msg = "Permission Denial: starting instrumentation " 14461 + className + " from pid=" 14462 + Binder.getCallingPid() 14463 + ", uid=" + Binder.getCallingPid() 14464 + " not allowed because package " + ii.packageName 14465 + " does not have a signature matching the target " 14466 + ii.targetPackage; 14467 reportStartInstrumentationFailure(watcher, className, msg); 14468 throw new SecurityException(msg); 14469 } 14470 14471 final long origId = Binder.clearCallingIdentity(); 14472 // Instrumentation can kill and relaunch even persistent processes 14473 forceStopPackageLocked(ii.targetPackage, -1, true, false, true, true, false, userId, 14474 "start instr"); 14475 ProcessRecord app = addAppLocked(ai, false, abiOverride); 14476 app.instrumentationClass = className; 14477 app.instrumentationInfo = ai; 14478 app.instrumentationProfileFile = profileFile; 14479 app.instrumentationArguments = arguments; 14480 app.instrumentationWatcher = watcher; 14481 app.instrumentationUiAutomationConnection = uiAutomationConnection; 14482 app.instrumentationResultClass = className; 14483 Binder.restoreCallingIdentity(origId); 14484 } 14485 14486 return true; 14487 } 14488 14489 /** 14490 * Report errors that occur while attempting to start Instrumentation. Always writes the 14491 * error to the logs, but if somebody is watching, send the report there too. This enables 14492 * the "am" command to report errors with more information. 14493 * 14494 * @param watcher The IInstrumentationWatcher. Null if there isn't one. 14495 * @param cn The component name of the instrumentation. 14496 * @param report The error report. 14497 */ 14498 private void reportStartInstrumentationFailure(IInstrumentationWatcher watcher, 14499 ComponentName cn, String report) { 14500 Slog.w(TAG, report); 14501 try { 14502 if (watcher != null) { 14503 Bundle results = new Bundle(); 14504 results.putString(Instrumentation.REPORT_KEY_IDENTIFIER, "ActivityManagerService"); 14505 results.putString("Error", report); 14506 watcher.instrumentationStatus(cn, -1, results); 14507 } 14508 } catch (RemoteException e) { 14509 Slog.w(TAG, e); 14510 } 14511 } 14512 14513 void finishInstrumentationLocked(ProcessRecord app, int resultCode, Bundle results) { 14514 if (app.instrumentationWatcher != null) { 14515 try { 14516 // NOTE: IInstrumentationWatcher *must* be oneway here 14517 app.instrumentationWatcher.instrumentationFinished( 14518 app.instrumentationClass, 14519 resultCode, 14520 results); 14521 } catch (RemoteException e) { 14522 } 14523 } 14524 if (app.instrumentationUiAutomationConnection != null) { 14525 try { 14526 app.instrumentationUiAutomationConnection.shutdown(); 14527 } catch (RemoteException re) { 14528 /* ignore */ 14529 } 14530 // Only a UiAutomation can set this flag and now that 14531 // it is finished we make sure it is reset to its default. 14532 mUserIsMonkey = false; 14533 } 14534 app.instrumentationWatcher = null; 14535 app.instrumentationUiAutomationConnection = null; 14536 app.instrumentationClass = null; 14537 app.instrumentationInfo = null; 14538 app.instrumentationProfileFile = null; 14539 app.instrumentationArguments = null; 14540 14541 forceStopPackageLocked(app.info.packageName, -1, false, false, true, true, false, app.userId, 14542 "finished inst"); 14543 } 14544 14545 public void finishInstrumentation(IApplicationThread target, 14546 int resultCode, Bundle results) { 14547 int userId = UserHandle.getCallingUserId(); 14548 // Refuse possible leaked file descriptors 14549 if (results != null && results.hasFileDescriptors()) { 14550 throw new IllegalArgumentException("File descriptors passed in Intent"); 14551 } 14552 14553 synchronized(this) { 14554 ProcessRecord app = getRecordForAppLocked(target); 14555 if (app == null) { 14556 Slog.w(TAG, "finishInstrumentation: no app for " + target); 14557 return; 14558 } 14559 final long origId = Binder.clearCallingIdentity(); 14560 finishInstrumentationLocked(app, resultCode, results); 14561 Binder.restoreCallingIdentity(origId); 14562 } 14563 } 14564 14565 // ========================================================= 14566 // CONFIGURATION 14567 // ========================================================= 14568 14569 public ConfigurationInfo getDeviceConfigurationInfo() { 14570 ConfigurationInfo config = new ConfigurationInfo(); 14571 synchronized (this) { 14572 config.reqTouchScreen = mConfiguration.touchscreen; 14573 config.reqKeyboardType = mConfiguration.keyboard; 14574 config.reqNavigation = mConfiguration.navigation; 14575 if (mConfiguration.navigation == Configuration.NAVIGATION_DPAD 14576 || mConfiguration.navigation == Configuration.NAVIGATION_TRACKBALL) { 14577 config.reqInputFeatures |= ConfigurationInfo.INPUT_FEATURE_FIVE_WAY_NAV; 14578 } 14579 if (mConfiguration.keyboard != Configuration.KEYBOARD_UNDEFINED 14580 && mConfiguration.keyboard != Configuration.KEYBOARD_NOKEYS) { 14581 config.reqInputFeatures |= ConfigurationInfo.INPUT_FEATURE_HARD_KEYBOARD; 14582 } 14583 config.reqGlEsVersion = GL_ES_VERSION; 14584 } 14585 return config; 14586 } 14587 14588 ActivityStack getFocusedStack() { 14589 return mStackSupervisor.getFocusedStack(); 14590 } 14591 14592 public Configuration getConfiguration() { 14593 Configuration ci; 14594 synchronized(this) { 14595 ci = new Configuration(mConfiguration); 14596 } 14597 return ci; 14598 } 14599 14600 public void updatePersistentConfiguration(Configuration values) { 14601 enforceCallingPermission(android.Manifest.permission.CHANGE_CONFIGURATION, 14602 "updateConfiguration()"); 14603 enforceCallingPermission(android.Manifest.permission.WRITE_SETTINGS, 14604 "updateConfiguration()"); 14605 if (values == null) { 14606 throw new NullPointerException("Configuration must not be null"); 14607 } 14608 14609 synchronized(this) { 14610 final long origId = Binder.clearCallingIdentity(); 14611 updateConfigurationLocked(values, null, true, false); 14612 Binder.restoreCallingIdentity(origId); 14613 } 14614 } 14615 14616 public void updateConfiguration(Configuration values) { 14617 enforceCallingPermission(android.Manifest.permission.CHANGE_CONFIGURATION, 14618 "updateConfiguration()"); 14619 14620 synchronized(this) { 14621 if (values == null && mWindowManager != null) { 14622 // sentinel: fetch the current configuration from the window manager 14623 values = mWindowManager.computeNewConfiguration(); 14624 } 14625 14626 if (mWindowManager != null) { 14627 mProcessList.applyDisplaySize(mWindowManager); 14628 } 14629 14630 final long origId = Binder.clearCallingIdentity(); 14631 if (values != null) { 14632 Settings.System.clearConfiguration(values); 14633 } 14634 updateConfigurationLocked(values, null, false, false); 14635 Binder.restoreCallingIdentity(origId); 14636 } 14637 } 14638 14639 /** 14640 * Do either or both things: (1) change the current configuration, and (2) 14641 * make sure the given activity is running with the (now) current 14642 * configuration. Returns true if the activity has been left running, or 14643 * false if <var>starting</var> is being destroyed to match the new 14644 * configuration. 14645 * @param persistent TODO 14646 */ 14647 boolean updateConfigurationLocked(Configuration values, 14648 ActivityRecord starting, boolean persistent, boolean initLocale) { 14649 int changes = 0; 14650 14651 if (values != null) { 14652 Configuration newConfig = new Configuration(mConfiguration); 14653 changes = newConfig.updateFrom(values); 14654 if (changes != 0) { 14655 if (DEBUG_SWITCH || DEBUG_CONFIGURATION) { 14656 Slog.i(TAG, "Updating configuration to: " + values); 14657 } 14658 14659 EventLog.writeEvent(EventLogTags.CONFIGURATION_CHANGED, changes); 14660 14661 if (values.locale != null && !initLocale) { 14662 saveLocaleLocked(values.locale, 14663 !values.locale.equals(mConfiguration.locale), 14664 values.userSetLocale); 14665 } 14666 14667 mConfigurationSeq++; 14668 if (mConfigurationSeq <= 0) { 14669 mConfigurationSeq = 1; 14670 } 14671 newConfig.seq = mConfigurationSeq; 14672 mConfiguration = newConfig; 14673 Slog.i(TAG, "Config changes=" + Integer.toHexString(changes) + " " + newConfig); 14674 mUsageStatsService.noteStartConfig(newConfig); 14675 14676 final Configuration configCopy = new Configuration(mConfiguration); 14677 14678 // TODO: If our config changes, should we auto dismiss any currently 14679 // showing dialogs? 14680 mShowDialogs = shouldShowDialogs(newConfig); 14681 14682 AttributeCache ac = AttributeCache.instance(); 14683 if (ac != null) { 14684 ac.updateConfiguration(configCopy); 14685 } 14686 14687 // Make sure all resources in our process are updated 14688 // right now, so that anyone who is going to retrieve 14689 // resource values after we return will be sure to get 14690 // the new ones. This is especially important during 14691 // boot, where the first config change needs to guarantee 14692 // all resources have that config before following boot 14693 // code is executed. 14694 mSystemThread.applyConfigurationToResources(configCopy); 14695 14696 if (persistent && Settings.System.hasInterestingConfigurationChanges(changes)) { 14697 Message msg = mHandler.obtainMessage(UPDATE_CONFIGURATION_MSG); 14698 msg.obj = new Configuration(configCopy); 14699 mHandler.sendMessage(msg); 14700 } 14701 14702 for (int i=mLruProcesses.size()-1; i>=0; i--) { 14703 ProcessRecord app = mLruProcesses.get(i); 14704 try { 14705 if (app.thread != null) { 14706 if (DEBUG_CONFIGURATION) Slog.v(TAG, "Sending to proc " 14707 + app.processName + " new config " + mConfiguration); 14708 app.thread.scheduleConfigurationChanged(configCopy); 14709 } 14710 } catch (Exception e) { 14711 } 14712 } 14713 Intent intent = new Intent(Intent.ACTION_CONFIGURATION_CHANGED); 14714 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 14715 | Intent.FLAG_RECEIVER_REPLACE_PENDING 14716 | Intent.FLAG_RECEIVER_FOREGROUND); 14717 broadcastIntentLocked(null, null, intent, null, null, 0, null, null, 14718 null, AppOpsManager.OP_NONE, false, false, MY_PID, 14719 Process.SYSTEM_UID, UserHandle.USER_ALL); 14720 if ((changes&ActivityInfo.CONFIG_LOCALE) != 0) { 14721 intent = new Intent(Intent.ACTION_LOCALE_CHANGED); 14722 intent.addFlags(Intent.FLAG_RECEIVER_FOREGROUND); 14723 broadcastIntentLocked(null, null, intent, 14724 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 14725 false, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 14726 } 14727 } 14728 } 14729 14730 boolean kept = true; 14731 final ActivityStack mainStack = mStackSupervisor.getFocusedStack(); 14732 // mainStack is null during startup. 14733 if (mainStack != null) { 14734 if (changes != 0 && starting == null) { 14735 // If the configuration changed, and the caller is not already 14736 // in the process of starting an activity, then find the top 14737 // activity to check if its configuration needs to change. 14738 starting = mainStack.topRunningActivityLocked(null); 14739 } 14740 14741 if (starting != null) { 14742 kept = mainStack.ensureActivityConfigurationLocked(starting, changes); 14743 // And we need to make sure at this point that all other activities 14744 // are made visible with the correct configuration. 14745 mStackSupervisor.ensureActivitiesVisibleLocked(starting, changes); 14746 } 14747 } 14748 14749 if (values != null && mWindowManager != null) { 14750 mWindowManager.setNewConfiguration(mConfiguration); 14751 } 14752 14753 return kept; 14754 } 14755 14756 /** 14757 * Decide based on the configuration whether we should shouw the ANR, 14758 * crash, etc dialogs. The idea is that if there is no affordnace to 14759 * press the on-screen buttons, we shouldn't show the dialog. 14760 * 14761 * A thought: SystemUI might also want to get told about this, the Power 14762 * dialog / global actions also might want different behaviors. 14763 */ 14764 private static final boolean shouldShowDialogs(Configuration config) { 14765 return !(config.keyboard == Configuration.KEYBOARD_NOKEYS 14766 && config.touchscreen == Configuration.TOUCHSCREEN_NOTOUCH); 14767 } 14768 14769 /** 14770 * Save the locale. You must be inside a synchronized (this) block. 14771 */ 14772 private void saveLocaleLocked(Locale l, boolean isDiff, boolean isPersist) { 14773 if(isDiff) { 14774 SystemProperties.set("user.language", l.getLanguage()); 14775 SystemProperties.set("user.region", l.getCountry()); 14776 } 14777 14778 if(isPersist) { 14779 SystemProperties.set("persist.sys.language", l.getLanguage()); 14780 SystemProperties.set("persist.sys.country", l.getCountry()); 14781 SystemProperties.set("persist.sys.localevar", l.getVariant()); 14782 } 14783 } 14784 14785 @Override 14786 public boolean targetTaskAffinityMatchesActivity(IBinder token, String destAffinity) { 14787 ActivityRecord srec = ActivityRecord.forToken(token); 14788 return srec != null && srec.task.affinity != null && 14789 srec.task.affinity.equals(destAffinity); 14790 } 14791 14792 public boolean navigateUpTo(IBinder token, Intent destIntent, int resultCode, 14793 Intent resultData) { 14794 14795 synchronized (this) { 14796 final ActivityStack stack = ActivityRecord.getStackLocked(token); 14797 if (stack != null) { 14798 return stack.navigateUpToLocked(token, destIntent, resultCode, resultData); 14799 } 14800 return false; 14801 } 14802 } 14803 14804 public int getLaunchedFromUid(IBinder activityToken) { 14805 ActivityRecord srec = ActivityRecord.forToken(activityToken); 14806 if (srec == null) { 14807 return -1; 14808 } 14809 return srec.launchedFromUid; 14810 } 14811 14812 public String getLaunchedFromPackage(IBinder activityToken) { 14813 ActivityRecord srec = ActivityRecord.forToken(activityToken); 14814 if (srec == null) { 14815 return null; 14816 } 14817 return srec.launchedFromPackage; 14818 } 14819 14820 // ========================================================= 14821 // LIFETIME MANAGEMENT 14822 // ========================================================= 14823 14824 // Returns which broadcast queue the app is the current [or imminent] receiver 14825 // on, or 'null' if the app is not an active broadcast recipient. 14826 private BroadcastQueue isReceivingBroadcast(ProcessRecord app) { 14827 BroadcastRecord r = app.curReceiver; 14828 if (r != null) { 14829 return r.queue; 14830 } 14831 14832 // It's not the current receiver, but it might be starting up to become one 14833 synchronized (this) { 14834 for (BroadcastQueue queue : mBroadcastQueues) { 14835 r = queue.mPendingBroadcast; 14836 if (r != null && r.curApp == app) { 14837 // found it; report which queue it's in 14838 return queue; 14839 } 14840 } 14841 } 14842 14843 return null; 14844 } 14845 14846 private final int computeOomAdjLocked(ProcessRecord app, int cachedAdj, ProcessRecord TOP_APP, 14847 boolean doingAll, long now) { 14848 if (mAdjSeq == app.adjSeq) { 14849 // This adjustment has already been computed. 14850 return app.curRawAdj; 14851 } 14852 14853 if (app.thread == null) { 14854 app.adjSeq = mAdjSeq; 14855 app.curSchedGroup = Process.THREAD_GROUP_BG_NONINTERACTIVE; 14856 app.curProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 14857 return (app.curAdj=app.curRawAdj=ProcessList.CACHED_APP_MAX_ADJ); 14858 } 14859 14860 app.adjTypeCode = ActivityManager.RunningAppProcessInfo.REASON_UNKNOWN; 14861 app.adjSource = null; 14862 app.adjTarget = null; 14863 app.empty = false; 14864 app.cached = false; 14865 14866 final int activitiesSize = app.activities.size(); 14867 14868 if (app.maxAdj <= ProcessList.FOREGROUND_APP_ADJ) { 14869 // The max adjustment doesn't allow this app to be anything 14870 // below foreground, so it is not worth doing work for it. 14871 app.adjType = "fixed"; 14872 app.adjSeq = mAdjSeq; 14873 app.curRawAdj = app.maxAdj; 14874 app.foregroundActivities = false; 14875 app.keeping = true; 14876 app.curSchedGroup = Process.THREAD_GROUP_DEFAULT; 14877 app.curProcState = ActivityManager.PROCESS_STATE_PERSISTENT; 14878 // System processes can do UI, and when they do we want to have 14879 // them trim their memory after the user leaves the UI. To 14880 // facilitate this, here we need to determine whether or not it 14881 // is currently showing UI. 14882 app.systemNoUi = true; 14883 if (app == TOP_APP) { 14884 app.systemNoUi = false; 14885 } else if (activitiesSize > 0) { 14886 for (int j = 0; j < activitiesSize; j++) { 14887 final ActivityRecord r = app.activities.get(j); 14888 if (r.visible) { 14889 app.systemNoUi = false; 14890 } 14891 } 14892 } 14893 if (!app.systemNoUi) { 14894 app.curProcState = ActivityManager.PROCESS_STATE_PERSISTENT_UI; 14895 } 14896 return (app.curAdj=app.maxAdj); 14897 } 14898 14899 app.keeping = false; 14900 app.systemNoUi = false; 14901 14902 // Determine the importance of the process, starting with most 14903 // important to least, and assign an appropriate OOM adjustment. 14904 int adj; 14905 int schedGroup; 14906 int procState; 14907 boolean foregroundActivities = false; 14908 boolean interesting = false; 14909 BroadcastQueue queue; 14910 if (app == TOP_APP) { 14911 // The last app on the list is the foreground app. 14912 adj = ProcessList.FOREGROUND_APP_ADJ; 14913 schedGroup = Process.THREAD_GROUP_DEFAULT; 14914 app.adjType = "top-activity"; 14915 foregroundActivities = true; 14916 interesting = true; 14917 procState = ActivityManager.PROCESS_STATE_TOP; 14918 } else if (app.instrumentationClass != null) { 14919 // Don't want to kill running instrumentation. 14920 adj = ProcessList.FOREGROUND_APP_ADJ; 14921 schedGroup = Process.THREAD_GROUP_DEFAULT; 14922 app.adjType = "instrumentation"; 14923 interesting = true; 14924 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 14925 } else if ((queue = isReceivingBroadcast(app)) != null) { 14926 // An app that is currently receiving a broadcast also 14927 // counts as being in the foreground for OOM killer purposes. 14928 // It's placed in a sched group based on the nature of the 14929 // broadcast as reflected by which queue it's active in. 14930 adj = ProcessList.FOREGROUND_APP_ADJ; 14931 schedGroup = (queue == mFgBroadcastQueue) 14932 ? Process.THREAD_GROUP_DEFAULT : Process.THREAD_GROUP_BG_NONINTERACTIVE; 14933 app.adjType = "broadcast"; 14934 procState = ActivityManager.PROCESS_STATE_RECEIVER; 14935 } else if (app.executingServices.size() > 0) { 14936 // An app that is currently executing a service callback also 14937 // counts as being in the foreground. 14938 adj = ProcessList.FOREGROUND_APP_ADJ; 14939 schedGroup = app.execServicesFg ? 14940 Process.THREAD_GROUP_DEFAULT : Process.THREAD_GROUP_BG_NONINTERACTIVE; 14941 app.adjType = "exec-service"; 14942 procState = ActivityManager.PROCESS_STATE_SERVICE; 14943 //Slog.i(TAG, "EXEC " + (app.execServicesFg ? "FG" : "BG") + ": " + app); 14944 } else { 14945 // As far as we know the process is empty. We may change our mind later. 14946 schedGroup = Process.THREAD_GROUP_BG_NONINTERACTIVE; 14947 // At this point we don't actually know the adjustment. Use the cached adj 14948 // value that the caller wants us to. 14949 adj = cachedAdj; 14950 procState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 14951 app.cached = true; 14952 app.empty = true; 14953 app.adjType = "cch-empty"; 14954 } 14955 14956 // Examine all activities if not already foreground. 14957 if (!foregroundActivities && activitiesSize > 0) { 14958 for (int j = 0; j < activitiesSize; j++) { 14959 final ActivityRecord r = app.activities.get(j); 14960 if (r.app != app) { 14961 Slog.w(TAG, "Wtf, activity " + r + " in proc activity list not using proc " 14962 + app + "?!?"); 14963 continue; 14964 } 14965 if (r.visible) { 14966 // App has a visible activity; only upgrade adjustment. 14967 if (adj > ProcessList.VISIBLE_APP_ADJ) { 14968 adj = ProcessList.VISIBLE_APP_ADJ; 14969 app.adjType = "visible"; 14970 } 14971 if (procState > ActivityManager.PROCESS_STATE_TOP) { 14972 procState = ActivityManager.PROCESS_STATE_TOP; 14973 } 14974 schedGroup = Process.THREAD_GROUP_DEFAULT; 14975 app.cached = false; 14976 app.empty = false; 14977 foregroundActivities = true; 14978 break; 14979 } else if (r.state == ActivityState.PAUSING || r.state == ActivityState.PAUSED) { 14980 if (adj > ProcessList.PERCEPTIBLE_APP_ADJ) { 14981 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 14982 app.adjType = "pausing"; 14983 } 14984 if (procState > ActivityManager.PROCESS_STATE_TOP) { 14985 procState = ActivityManager.PROCESS_STATE_TOP; 14986 } 14987 schedGroup = Process.THREAD_GROUP_DEFAULT; 14988 app.cached = false; 14989 app.empty = false; 14990 foregroundActivities = true; 14991 } else if (r.state == ActivityState.STOPPING) { 14992 if (adj > ProcessList.PERCEPTIBLE_APP_ADJ) { 14993 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 14994 app.adjType = "stopping"; 14995 } 14996 // For the process state, we will at this point consider the 14997 // process to be cached. It will be cached either as an activity 14998 // or empty depending on whether the activity is finishing. We do 14999 // this so that we can treat the process as cached for purposes of 15000 // memory trimming (determing current memory level, trim command to 15001 // send to process) since there can be an arbitrary number of stopping 15002 // processes and they should soon all go into the cached state. 15003 if (!r.finishing) { 15004 if (procState > ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 15005 procState = ActivityManager.PROCESS_STATE_CACHED_ACTIVITY; 15006 } 15007 } 15008 app.cached = false; 15009 app.empty = false; 15010 foregroundActivities = true; 15011 } else { 15012 if (procState > ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 15013 procState = ActivityManager.PROCESS_STATE_CACHED_ACTIVITY; 15014 app.adjType = "cch-act"; 15015 } 15016 } 15017 } 15018 } 15019 15020 if (adj > ProcessList.PERCEPTIBLE_APP_ADJ) { 15021 if (app.foregroundServices) { 15022 // The user is aware of this app, so make it visible. 15023 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 15024 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 15025 app.cached = false; 15026 app.adjType = "fg-service"; 15027 schedGroup = Process.THREAD_GROUP_DEFAULT; 15028 } else if (app.forcingToForeground != null) { 15029 // The user is aware of this app, so make it visible. 15030 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 15031 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 15032 app.cached = false; 15033 app.adjType = "force-fg"; 15034 app.adjSource = app.forcingToForeground; 15035 schedGroup = Process.THREAD_GROUP_DEFAULT; 15036 } 15037 } 15038 15039 if (app.foregroundServices) { 15040 interesting = true; 15041 } 15042 15043 if (app == mHeavyWeightProcess) { 15044 if (adj > ProcessList.HEAVY_WEIGHT_APP_ADJ) { 15045 // We don't want to kill the current heavy-weight process. 15046 adj = ProcessList.HEAVY_WEIGHT_APP_ADJ; 15047 schedGroup = Process.THREAD_GROUP_BG_NONINTERACTIVE; 15048 app.cached = false; 15049 app.adjType = "heavy"; 15050 } 15051 if (procState > ActivityManager.PROCESS_STATE_HEAVY_WEIGHT) { 15052 procState = ActivityManager.PROCESS_STATE_HEAVY_WEIGHT; 15053 } 15054 } 15055 15056 if (app == mHomeProcess) { 15057 if (adj > ProcessList.HOME_APP_ADJ) { 15058 // This process is hosting what we currently consider to be the 15059 // home app, so we don't want to let it go into the background. 15060 adj = ProcessList.HOME_APP_ADJ; 15061 schedGroup = Process.THREAD_GROUP_BG_NONINTERACTIVE; 15062 app.cached = false; 15063 app.adjType = "home"; 15064 } 15065 if (procState > ActivityManager.PROCESS_STATE_HOME) { 15066 procState = ActivityManager.PROCESS_STATE_HOME; 15067 } 15068 } 15069 15070 if (app == mPreviousProcess && app.activities.size() > 0) { 15071 if (adj > ProcessList.PREVIOUS_APP_ADJ) { 15072 // This was the previous process that showed UI to the user. 15073 // We want to try to keep it around more aggressively, to give 15074 // a good experience around switching between two apps. 15075 adj = ProcessList.PREVIOUS_APP_ADJ; 15076 schedGroup = Process.THREAD_GROUP_BG_NONINTERACTIVE; 15077 app.cached = false; 15078 app.adjType = "previous"; 15079 } 15080 if (procState > ActivityManager.PROCESS_STATE_LAST_ACTIVITY) { 15081 procState = ActivityManager.PROCESS_STATE_LAST_ACTIVITY; 15082 } 15083 } 15084 15085 if (false) Slog.i(TAG, "OOM " + app + ": initial adj=" + adj 15086 + " reason=" + app.adjType); 15087 15088 // By default, we use the computed adjustment. It may be changed if 15089 // there are applications dependent on our services or providers, but 15090 // this gives us a baseline and makes sure we don't get into an 15091 // infinite recursion. 15092 app.adjSeq = mAdjSeq; 15093 app.curRawAdj = adj; 15094 app.hasStartedServices = false; 15095 15096 if (mBackupTarget != null && app == mBackupTarget.app) { 15097 // If possible we want to avoid killing apps while they're being backed up 15098 if (adj > ProcessList.BACKUP_APP_ADJ) { 15099 if (DEBUG_BACKUP) Slog.v(TAG, "oom BACKUP_APP_ADJ for " + app); 15100 adj = ProcessList.BACKUP_APP_ADJ; 15101 if (procState > ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND) { 15102 procState = ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND; 15103 } 15104 app.adjType = "backup"; 15105 app.cached = false; 15106 } 15107 if (procState > ActivityManager.PROCESS_STATE_BACKUP) { 15108 procState = ActivityManager.PROCESS_STATE_BACKUP; 15109 } 15110 } 15111 15112 boolean mayBeTop = false; 15113 15114 for (int is = app.services.size()-1; 15115 is >= 0 && (adj > ProcessList.FOREGROUND_APP_ADJ 15116 || schedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE 15117 || procState > ActivityManager.PROCESS_STATE_TOP); 15118 is--) { 15119 ServiceRecord s = app.services.valueAt(is); 15120 if (s.startRequested) { 15121 app.hasStartedServices = true; 15122 if (procState > ActivityManager.PROCESS_STATE_SERVICE) { 15123 procState = ActivityManager.PROCESS_STATE_SERVICE; 15124 } 15125 if (app.hasShownUi && app != mHomeProcess) { 15126 // If this process has shown some UI, let it immediately 15127 // go to the LRU list because it may be pretty heavy with 15128 // UI stuff. We'll tag it with a label just to help 15129 // debug and understand what is going on. 15130 if (adj > ProcessList.SERVICE_ADJ) { 15131 app.adjType = "cch-started-ui-services"; 15132 } 15133 } else { 15134 if (now < (s.lastActivity + ActiveServices.MAX_SERVICE_INACTIVITY)) { 15135 // This service has seen some activity within 15136 // recent memory, so we will keep its process ahead 15137 // of the background processes. 15138 if (adj > ProcessList.SERVICE_ADJ) { 15139 adj = ProcessList.SERVICE_ADJ; 15140 app.adjType = "started-services"; 15141 app.cached = false; 15142 } 15143 } 15144 // If we have let the service slide into the background 15145 // state, still have some text describing what it is doing 15146 // even though the service no longer has an impact. 15147 if (adj > ProcessList.SERVICE_ADJ) { 15148 app.adjType = "cch-started-services"; 15149 } 15150 } 15151 // Don't kill this process because it is doing work; it 15152 // has said it is doing work. 15153 app.keeping = true; 15154 } 15155 for (int conni = s.connections.size()-1; 15156 conni >= 0 && (adj > ProcessList.FOREGROUND_APP_ADJ 15157 || schedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE 15158 || procState > ActivityManager.PROCESS_STATE_TOP); 15159 conni--) { 15160 ArrayList<ConnectionRecord> clist = s.connections.valueAt(conni); 15161 for (int i = 0; 15162 i < clist.size() && (adj > ProcessList.FOREGROUND_APP_ADJ 15163 || schedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE 15164 || procState > ActivityManager.PROCESS_STATE_TOP); 15165 i++) { 15166 // XXX should compute this based on the max of 15167 // all connected clients. 15168 ConnectionRecord cr = clist.get(i); 15169 if (cr.binding.client == app) { 15170 // Binding to ourself is not interesting. 15171 continue; 15172 } 15173 if ((cr.flags&Context.BIND_WAIVE_PRIORITY) == 0) { 15174 ProcessRecord client = cr.binding.client; 15175 int clientAdj = computeOomAdjLocked(client, cachedAdj, 15176 TOP_APP, doingAll, now); 15177 int clientProcState = client.curProcState; 15178 if (clientProcState >= ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 15179 // If the other app is cached for any reason, for purposes here 15180 // we are going to consider it empty. The specific cached state 15181 // doesn't propagate except under certain conditions. 15182 clientProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 15183 } 15184 String adjType = null; 15185 if ((cr.flags&Context.BIND_ALLOW_OOM_MANAGEMENT) != 0) { 15186 // Not doing bind OOM management, so treat 15187 // this guy more like a started service. 15188 if (app.hasShownUi && app != mHomeProcess) { 15189 // If this process has shown some UI, let it immediately 15190 // go to the LRU list because it may be pretty heavy with 15191 // UI stuff. We'll tag it with a label just to help 15192 // debug and understand what is going on. 15193 if (adj > clientAdj) { 15194 adjType = "cch-bound-ui-services"; 15195 } 15196 app.cached = false; 15197 clientAdj = adj; 15198 clientProcState = procState; 15199 } else { 15200 if (now >= (s.lastActivity 15201 + ActiveServices.MAX_SERVICE_INACTIVITY)) { 15202 // This service has not seen activity within 15203 // recent memory, so allow it to drop to the 15204 // LRU list if there is no other reason to keep 15205 // it around. We'll also tag it with a label just 15206 // to help debug and undertand what is going on. 15207 if (adj > clientAdj) { 15208 adjType = "cch-bound-services"; 15209 } 15210 clientAdj = adj; 15211 } 15212 } 15213 } 15214 if (adj > clientAdj) { 15215 // If this process has recently shown UI, and 15216 // the process that is binding to it is less 15217 // important than being visible, then we don't 15218 // care about the binding as much as we care 15219 // about letting this process get into the LRU 15220 // list to be killed and restarted if needed for 15221 // memory. 15222 if (app.hasShownUi && app != mHomeProcess 15223 && clientAdj > ProcessList.PERCEPTIBLE_APP_ADJ) { 15224 adjType = "cch-bound-ui-services"; 15225 } else { 15226 if ((cr.flags&(Context.BIND_ABOVE_CLIENT 15227 |Context.BIND_IMPORTANT)) != 0) { 15228 adj = clientAdj; 15229 } else if ((cr.flags&Context.BIND_NOT_VISIBLE) != 0 15230 && clientAdj < ProcessList.PERCEPTIBLE_APP_ADJ 15231 && adj > ProcessList.PERCEPTIBLE_APP_ADJ) { 15232 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 15233 } else if (clientAdj > ProcessList.VISIBLE_APP_ADJ) { 15234 adj = clientAdj; 15235 } else { 15236 if (adj > ProcessList.VISIBLE_APP_ADJ) { 15237 adj = ProcessList.VISIBLE_APP_ADJ; 15238 } 15239 } 15240 if (!client.cached) { 15241 app.cached = false; 15242 } 15243 if (client.keeping) { 15244 app.keeping = true; 15245 } 15246 adjType = "service"; 15247 } 15248 } 15249 if ((cr.flags&Context.BIND_NOT_FOREGROUND) == 0) { 15250 if (client.curSchedGroup == Process.THREAD_GROUP_DEFAULT) { 15251 schedGroup = Process.THREAD_GROUP_DEFAULT; 15252 } 15253 if (clientProcState <= ActivityManager.PROCESS_STATE_TOP) { 15254 if (clientProcState == ActivityManager.PROCESS_STATE_TOP) { 15255 // Special handling of clients who are in the top state. 15256 // We *may* want to consider this process to be in the 15257 // top state as well, but only if there is not another 15258 // reason for it to be running. Being on the top is a 15259 // special state, meaning you are specifically running 15260 // for the current top app. If the process is already 15261 // running in the background for some other reason, it 15262 // is more important to continue considering it to be 15263 // in the background state. 15264 mayBeTop = true; 15265 clientProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 15266 } else { 15267 // Special handling for above-top states (persistent 15268 // processes). These should not bring the current process 15269 // into the top state, since they are not on top. Instead 15270 // give them the best state after that. 15271 clientProcState = 15272 ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 15273 } 15274 } 15275 } else { 15276 if (clientProcState < 15277 ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND) { 15278 clientProcState = 15279 ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND; 15280 } 15281 } 15282 if (procState > clientProcState) { 15283 procState = clientProcState; 15284 } 15285 if (procState < ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND 15286 && (cr.flags&Context.BIND_SHOWING_UI) != 0) { 15287 app.pendingUiClean = true; 15288 } 15289 if (adjType != null) { 15290 app.adjType = adjType; 15291 app.adjTypeCode = ActivityManager.RunningAppProcessInfo 15292 .REASON_SERVICE_IN_USE; 15293 app.adjSource = cr.binding.client; 15294 app.adjSourceOom = clientAdj; 15295 app.adjTarget = s.name; 15296 } 15297 } 15298 if ((cr.flags&Context.BIND_TREAT_LIKE_ACTIVITY) != 0) { 15299 app.treatLikeActivity = true; 15300 } 15301 final ActivityRecord a = cr.activity; 15302 if ((cr.flags&Context.BIND_ADJUST_WITH_ACTIVITY) != 0) { 15303 if (a != null && adj > ProcessList.FOREGROUND_APP_ADJ && 15304 (a.visible || a.state == ActivityState.RESUMED 15305 || a.state == ActivityState.PAUSING)) { 15306 adj = ProcessList.FOREGROUND_APP_ADJ; 15307 if ((cr.flags&Context.BIND_NOT_FOREGROUND) == 0) { 15308 schedGroup = Process.THREAD_GROUP_DEFAULT; 15309 } 15310 app.cached = false; 15311 app.adjType = "service"; 15312 app.adjTypeCode = ActivityManager.RunningAppProcessInfo 15313 .REASON_SERVICE_IN_USE; 15314 app.adjSource = a; 15315 app.adjSourceOom = adj; 15316 app.adjTarget = s.name; 15317 } 15318 } 15319 } 15320 } 15321 } 15322 15323 for (int provi = app.pubProviders.size()-1; 15324 provi >= 0 && (adj > ProcessList.FOREGROUND_APP_ADJ 15325 || schedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE 15326 || procState > ActivityManager.PROCESS_STATE_TOP); 15327 provi--) { 15328 ContentProviderRecord cpr = app.pubProviders.valueAt(provi); 15329 for (int i = cpr.connections.size()-1; 15330 i >= 0 && (adj > ProcessList.FOREGROUND_APP_ADJ 15331 || schedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE 15332 || procState > ActivityManager.PROCESS_STATE_TOP); 15333 i--) { 15334 ContentProviderConnection conn = cpr.connections.get(i); 15335 ProcessRecord client = conn.client; 15336 if (client == app) { 15337 // Being our own client is not interesting. 15338 continue; 15339 } 15340 int clientAdj = computeOomAdjLocked(client, cachedAdj, TOP_APP, doingAll, now); 15341 int clientProcState = client.curProcState; 15342 if (clientProcState >= ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 15343 // If the other app is cached for any reason, for purposes here 15344 // we are going to consider it empty. 15345 clientProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 15346 } 15347 if (adj > clientAdj) { 15348 if (app.hasShownUi && app != mHomeProcess 15349 && clientAdj > ProcessList.PERCEPTIBLE_APP_ADJ) { 15350 app.adjType = "cch-ui-provider"; 15351 } else { 15352 adj = clientAdj > ProcessList.FOREGROUND_APP_ADJ 15353 ? clientAdj : ProcessList.FOREGROUND_APP_ADJ; 15354 app.adjType = "provider"; 15355 } 15356 app.cached &= client.cached; 15357 app.keeping |= client.keeping; 15358 app.adjTypeCode = ActivityManager.RunningAppProcessInfo 15359 .REASON_PROVIDER_IN_USE; 15360 app.adjSource = client; 15361 app.adjSourceOom = clientAdj; 15362 app.adjTarget = cpr.name; 15363 } 15364 if (clientProcState <= ActivityManager.PROCESS_STATE_TOP) { 15365 if (clientProcState == ActivityManager.PROCESS_STATE_TOP) { 15366 // Special handling of clients who are in the top state. 15367 // We *may* want to consider this process to be in the 15368 // top state as well, but only if there is not another 15369 // reason for it to be running. Being on the top is a 15370 // special state, meaning you are specifically running 15371 // for the current top app. If the process is already 15372 // running in the background for some other reason, it 15373 // is more important to continue considering it to be 15374 // in the background state. 15375 mayBeTop = true; 15376 clientProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 15377 } else { 15378 // Special handling for above-top states (persistent 15379 // processes). These should not bring the current process 15380 // into the top state, since they are not on top. Instead 15381 // give them the best state after that. 15382 clientProcState = 15383 ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 15384 } 15385 } 15386 if (procState > clientProcState) { 15387 procState = clientProcState; 15388 } 15389 if (client.curSchedGroup == Process.THREAD_GROUP_DEFAULT) { 15390 schedGroup = Process.THREAD_GROUP_DEFAULT; 15391 } 15392 } 15393 // If the provider has external (non-framework) process 15394 // dependencies, ensure that its adjustment is at least 15395 // FOREGROUND_APP_ADJ. 15396 if (cpr.hasExternalProcessHandles()) { 15397 if (adj > ProcessList.FOREGROUND_APP_ADJ) { 15398 adj = ProcessList.FOREGROUND_APP_ADJ; 15399 schedGroup = Process.THREAD_GROUP_DEFAULT; 15400 app.cached = false; 15401 app.keeping = true; 15402 app.adjType = "provider"; 15403 app.adjTarget = cpr.name; 15404 } 15405 if (procState > ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND) { 15406 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 15407 } 15408 } 15409 } 15410 15411 if (mayBeTop && procState > ActivityManager.PROCESS_STATE_TOP) { 15412 // A client of one of our services or providers is in the top state. We 15413 // *may* want to be in the top state, but not if we are already running in 15414 // the background for some other reason. For the decision here, we are going 15415 // to pick out a few specific states that we want to remain in when a client 15416 // is top (states that tend to be longer-term) and otherwise allow it to go 15417 // to the top state. 15418 switch (procState) { 15419 case ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND: 15420 case ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND: 15421 case ActivityManager.PROCESS_STATE_SERVICE: 15422 // These all are longer-term states, so pull them up to the top 15423 // of the background states, but not all the way to the top state. 15424 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 15425 break; 15426 default: 15427 // Otherwise, top is a better choice, so take it. 15428 procState = ActivityManager.PROCESS_STATE_TOP; 15429 break; 15430 } 15431 } 15432 15433 if (procState >= ActivityManager.PROCESS_STATE_CACHED_EMPTY) { 15434 if (app.hasClientActivities) { 15435 // This is a cached process, but with client activities. Mark it so. 15436 procState = ActivityManager.PROCESS_STATE_CACHED_ACTIVITY_CLIENT; 15437 app.adjType = "cch-client-act"; 15438 } else if (app.treatLikeActivity) { 15439 // This is a cached process, but somebody wants us to treat it like it has 15440 // an activity, okay! 15441 procState = ActivityManager.PROCESS_STATE_CACHED_ACTIVITY; 15442 app.adjType = "cch-as-act"; 15443 } 15444 } 15445 15446 if (adj == ProcessList.SERVICE_ADJ) { 15447 if (doingAll) { 15448 app.serviceb = mNewNumAServiceProcs > (mNumServiceProcs/3); 15449 mNewNumServiceProcs++; 15450 //Slog.i(TAG, "ADJ " + app + " serviceb=" + app.serviceb); 15451 if (!app.serviceb) { 15452 // This service isn't far enough down on the LRU list to 15453 // normally be a B service, but if we are low on RAM and it 15454 // is large we want to force it down since we would prefer to 15455 // keep launcher over it. 15456 if (mLastMemoryLevel > ProcessStats.ADJ_MEM_FACTOR_NORMAL 15457 && app.lastPss >= mProcessList.getCachedRestoreThresholdKb()) { 15458 app.serviceHighRam = true; 15459 app.serviceb = true; 15460 //Slog.i(TAG, "ADJ " + app + " high ram!"); 15461 } else { 15462 mNewNumAServiceProcs++; 15463 //Slog.i(TAG, "ADJ " + app + " not high ram!"); 15464 } 15465 } else { 15466 app.serviceHighRam = false; 15467 } 15468 } 15469 if (app.serviceb) { 15470 adj = ProcessList.SERVICE_B_ADJ; 15471 } 15472 } 15473 15474 app.curRawAdj = adj; 15475 15476 //Slog.i(TAG, "OOM ADJ " + app + ": pid=" + app.pid + 15477 // " adj=" + adj + " curAdj=" + app.curAdj + " maxAdj=" + app.maxAdj); 15478 if (adj > app.maxAdj) { 15479 adj = app.maxAdj; 15480 if (app.maxAdj <= ProcessList.PERCEPTIBLE_APP_ADJ) { 15481 schedGroup = Process.THREAD_GROUP_DEFAULT; 15482 } 15483 } 15484 if (adj < ProcessList.CACHED_APP_MIN_ADJ) { 15485 app.keeping = true; 15486 } 15487 15488 // Do final modification to adj. Everything we do between here and applying 15489 // the final setAdj must be done in this function, because we will also use 15490 // it when computing the final cached adj later. Note that we don't need to 15491 // worry about this for max adj above, since max adj will always be used to 15492 // keep it out of the cached vaues. 15493 app.curAdj = app.modifyRawOomAdj(adj); 15494 app.curSchedGroup = schedGroup; 15495 app.curProcState = procState; 15496 app.foregroundActivities = foregroundActivities; 15497 15498 return app.curRawAdj; 15499 } 15500 15501 /** 15502 * Schedule PSS collection of a process. 15503 */ 15504 void requestPssLocked(ProcessRecord proc, int procState) { 15505 if (mPendingPssProcesses.contains(proc)) { 15506 return; 15507 } 15508 if (mPendingPssProcesses.size() == 0) { 15509 mBgHandler.sendEmptyMessage(COLLECT_PSS_BG_MSG); 15510 } 15511 if (DEBUG_PSS) Slog.d(TAG, "Requesting PSS of: " + proc); 15512 proc.pssProcState = procState; 15513 mPendingPssProcesses.add(proc); 15514 } 15515 15516 /** 15517 * Schedule PSS collection of all processes. 15518 */ 15519 void requestPssAllProcsLocked(long now, boolean always, boolean memLowered) { 15520 if (!always) { 15521 if (now < (mLastFullPssTime + 15522 (memLowered ? FULL_PSS_LOWERED_INTERVAL : FULL_PSS_MIN_INTERVAL))) { 15523 return; 15524 } 15525 } 15526 if (DEBUG_PSS) Slog.d(TAG, "Requesting PSS of all procs! memLowered=" + memLowered); 15527 mLastFullPssTime = now; 15528 mPendingPssProcesses.ensureCapacity(mLruProcesses.size()); 15529 mPendingPssProcesses.clear(); 15530 for (int i=mLruProcesses.size()-1; i>=0; i--) { 15531 ProcessRecord app = mLruProcesses.get(i); 15532 if (memLowered || now > (app.lastStateTime+ProcessList.PSS_ALL_INTERVAL)) { 15533 app.pssProcState = app.setProcState; 15534 app.nextPssTime = ProcessList.computeNextPssTime(app.curProcState, true, 15535 isSleeping(), now); 15536 mPendingPssProcesses.add(app); 15537 } 15538 } 15539 mBgHandler.sendEmptyMessage(COLLECT_PSS_BG_MSG); 15540 } 15541 15542 /** 15543 * Ask a given process to GC right now. 15544 */ 15545 final void performAppGcLocked(ProcessRecord app) { 15546 try { 15547 app.lastRequestedGc = SystemClock.uptimeMillis(); 15548 if (app.thread != null) { 15549 if (app.reportLowMemory) { 15550 app.reportLowMemory = false; 15551 app.thread.scheduleLowMemory(); 15552 } else { 15553 app.thread.processInBackground(); 15554 } 15555 } 15556 } catch (Exception e) { 15557 // whatever. 15558 } 15559 } 15560 15561 /** 15562 * Returns true if things are idle enough to perform GCs. 15563 */ 15564 private final boolean canGcNowLocked() { 15565 boolean processingBroadcasts = false; 15566 for (BroadcastQueue q : mBroadcastQueues) { 15567 if (q.mParallelBroadcasts.size() != 0 || q.mOrderedBroadcasts.size() != 0) { 15568 processingBroadcasts = true; 15569 } 15570 } 15571 return !processingBroadcasts 15572 && (isSleeping() || mStackSupervisor.allResumedActivitiesIdle()); 15573 } 15574 15575 /** 15576 * Perform GCs on all processes that are waiting for it, but only 15577 * if things are idle. 15578 */ 15579 final void performAppGcsLocked() { 15580 final int N = mProcessesToGc.size(); 15581 if (N <= 0) { 15582 return; 15583 } 15584 if (canGcNowLocked()) { 15585 while (mProcessesToGc.size() > 0) { 15586 ProcessRecord proc = mProcessesToGc.remove(0); 15587 if (proc.curRawAdj > ProcessList.PERCEPTIBLE_APP_ADJ || proc.reportLowMemory) { 15588 if ((proc.lastRequestedGc+GC_MIN_INTERVAL) 15589 <= SystemClock.uptimeMillis()) { 15590 // To avoid spamming the system, we will GC processes one 15591 // at a time, waiting a few seconds between each. 15592 performAppGcLocked(proc); 15593 scheduleAppGcsLocked(); 15594 return; 15595 } else { 15596 // It hasn't been long enough since we last GCed this 15597 // process... put it in the list to wait for its time. 15598 addProcessToGcListLocked(proc); 15599 break; 15600 } 15601 } 15602 } 15603 15604 scheduleAppGcsLocked(); 15605 } 15606 } 15607 15608 /** 15609 * If all looks good, perform GCs on all processes waiting for them. 15610 */ 15611 final void performAppGcsIfAppropriateLocked() { 15612 if (canGcNowLocked()) { 15613 performAppGcsLocked(); 15614 return; 15615 } 15616 // Still not idle, wait some more. 15617 scheduleAppGcsLocked(); 15618 } 15619 15620 /** 15621 * Schedule the execution of all pending app GCs. 15622 */ 15623 final void scheduleAppGcsLocked() { 15624 mHandler.removeMessages(GC_BACKGROUND_PROCESSES_MSG); 15625 15626 if (mProcessesToGc.size() > 0) { 15627 // Schedule a GC for the time to the next process. 15628 ProcessRecord proc = mProcessesToGc.get(0); 15629 Message msg = mHandler.obtainMessage(GC_BACKGROUND_PROCESSES_MSG); 15630 15631 long when = proc.lastRequestedGc + GC_MIN_INTERVAL; 15632 long now = SystemClock.uptimeMillis(); 15633 if (when < (now+GC_TIMEOUT)) { 15634 when = now + GC_TIMEOUT; 15635 } 15636 mHandler.sendMessageAtTime(msg, when); 15637 } 15638 } 15639 15640 /** 15641 * Add a process to the array of processes waiting to be GCed. Keeps the 15642 * list in sorted order by the last GC time. The process can't already be 15643 * on the list. 15644 */ 15645 final void addProcessToGcListLocked(ProcessRecord proc) { 15646 boolean added = false; 15647 for (int i=mProcessesToGc.size()-1; i>=0; i--) { 15648 if (mProcessesToGc.get(i).lastRequestedGc < 15649 proc.lastRequestedGc) { 15650 added = true; 15651 mProcessesToGc.add(i+1, proc); 15652 break; 15653 } 15654 } 15655 if (!added) { 15656 mProcessesToGc.add(0, proc); 15657 } 15658 } 15659 15660 /** 15661 * Set up to ask a process to GC itself. This will either do it 15662 * immediately, or put it on the list of processes to gc the next 15663 * time things are idle. 15664 */ 15665 final void scheduleAppGcLocked(ProcessRecord app) { 15666 long now = SystemClock.uptimeMillis(); 15667 if ((app.lastRequestedGc+GC_MIN_INTERVAL) > now) { 15668 return; 15669 } 15670 if (!mProcessesToGc.contains(app)) { 15671 addProcessToGcListLocked(app); 15672 scheduleAppGcsLocked(); 15673 } 15674 } 15675 15676 final void checkExcessivePowerUsageLocked(boolean doKills) { 15677 updateCpuStatsNow(); 15678 15679 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 15680 boolean doWakeKills = doKills; 15681 boolean doCpuKills = doKills; 15682 if (mLastPowerCheckRealtime == 0) { 15683 doWakeKills = false; 15684 } 15685 if (mLastPowerCheckUptime == 0) { 15686 doCpuKills = false; 15687 } 15688 if (stats.isScreenOn()) { 15689 doWakeKills = false; 15690 } 15691 final long curRealtime = SystemClock.elapsedRealtime(); 15692 final long realtimeSince = curRealtime - mLastPowerCheckRealtime; 15693 final long curUptime = SystemClock.uptimeMillis(); 15694 final long uptimeSince = curUptime - mLastPowerCheckUptime; 15695 mLastPowerCheckRealtime = curRealtime; 15696 mLastPowerCheckUptime = curUptime; 15697 if (realtimeSince < WAKE_LOCK_MIN_CHECK_DURATION) { 15698 doWakeKills = false; 15699 } 15700 if (uptimeSince < CPU_MIN_CHECK_DURATION) { 15701 doCpuKills = false; 15702 } 15703 int i = mLruProcesses.size(); 15704 while (i > 0) { 15705 i--; 15706 ProcessRecord app = mLruProcesses.get(i); 15707 if (!app.keeping) { 15708 long wtime; 15709 synchronized (stats) { 15710 wtime = stats.getProcessWakeTime(app.info.uid, 15711 app.pid, curRealtime); 15712 } 15713 long wtimeUsed = wtime - app.lastWakeTime; 15714 long cputimeUsed = app.curCpuTime - app.lastCpuTime; 15715 if (DEBUG_POWER) { 15716 StringBuilder sb = new StringBuilder(128); 15717 sb.append("Wake for "); 15718 app.toShortString(sb); 15719 sb.append(": over "); 15720 TimeUtils.formatDuration(realtimeSince, sb); 15721 sb.append(" used "); 15722 TimeUtils.formatDuration(wtimeUsed, sb); 15723 sb.append(" ("); 15724 sb.append((wtimeUsed*100)/realtimeSince); 15725 sb.append("%)"); 15726 Slog.i(TAG, sb.toString()); 15727 sb.setLength(0); 15728 sb.append("CPU for "); 15729 app.toShortString(sb); 15730 sb.append(": over "); 15731 TimeUtils.formatDuration(uptimeSince, sb); 15732 sb.append(" used "); 15733 TimeUtils.formatDuration(cputimeUsed, sb); 15734 sb.append(" ("); 15735 sb.append((cputimeUsed*100)/uptimeSince); 15736 sb.append("%)"); 15737 Slog.i(TAG, sb.toString()); 15738 } 15739 // If a process has held a wake lock for more 15740 // than 50% of the time during this period, 15741 // that sounds bad. Kill! 15742 if (doWakeKills && realtimeSince > 0 15743 && ((wtimeUsed*100)/realtimeSince) >= 50) { 15744 synchronized (stats) { 15745 stats.reportExcessiveWakeLocked(app.info.uid, app.processName, 15746 realtimeSince, wtimeUsed); 15747 } 15748 killUnneededProcessLocked(app, "excessive wake held " + wtimeUsed 15749 + " during " + realtimeSince); 15750 app.baseProcessTracker.reportExcessiveWake(app.pkgList); 15751 } else if (doCpuKills && uptimeSince > 0 15752 && ((cputimeUsed*100)/uptimeSince) >= 50) { 15753 synchronized (stats) { 15754 stats.reportExcessiveCpuLocked(app.info.uid, app.processName, 15755 uptimeSince, cputimeUsed); 15756 } 15757 killUnneededProcessLocked(app, "excessive cpu " + cputimeUsed 15758 + " during " + uptimeSince); 15759 app.baseProcessTracker.reportExcessiveCpu(app.pkgList); 15760 } else { 15761 app.lastWakeTime = wtime; 15762 app.lastCpuTime = app.curCpuTime; 15763 } 15764 } 15765 } 15766 } 15767 15768 private final boolean applyOomAdjLocked(ProcessRecord app, boolean wasKeeping, 15769 ProcessRecord TOP_APP, boolean doingAll, long now) { 15770 boolean success = true; 15771 15772 if (app.curRawAdj != app.setRawAdj) { 15773 if (wasKeeping && !app.keeping) { 15774 // This app is no longer something we want to keep. Note 15775 // its current wake lock time to later know to kill it if 15776 // it is not behaving well. 15777 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 15778 synchronized (stats) { 15779 app.lastWakeTime = stats.getProcessWakeTime(app.info.uid, 15780 app.pid, SystemClock.elapsedRealtime()); 15781 } 15782 app.lastCpuTime = app.curCpuTime; 15783 } 15784 15785 app.setRawAdj = app.curRawAdj; 15786 } 15787 15788 int changes = 0; 15789 15790 if (app.curAdj != app.setAdj) { 15791 ProcessList.setOomAdj(app.pid, app.curAdj); 15792 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v( 15793 TAG, "Set " + app.pid + " " + app.processName + 15794 " adj " + app.curAdj + ": " + app.adjType); 15795 app.setAdj = app.curAdj; 15796 } 15797 15798 if (app.setSchedGroup != app.curSchedGroup) { 15799 app.setSchedGroup = app.curSchedGroup; 15800 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 15801 "Setting process group of " + app.processName 15802 + " to " + app.curSchedGroup); 15803 if (app.waitingToKill != null && 15804 app.setSchedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE) { 15805 killUnneededProcessLocked(app, app.waitingToKill); 15806 success = false; 15807 } else { 15808 if (true) { 15809 long oldId = Binder.clearCallingIdentity(); 15810 try { 15811 Process.setProcessGroup(app.pid, app.curSchedGroup); 15812 } catch (Exception e) { 15813 Slog.w(TAG, "Failed setting process group of " + app.pid 15814 + " to " + app.curSchedGroup); 15815 e.printStackTrace(); 15816 } finally { 15817 Binder.restoreCallingIdentity(oldId); 15818 } 15819 } else { 15820 if (app.thread != null) { 15821 try { 15822 app.thread.setSchedulingGroup(app.curSchedGroup); 15823 } catch (RemoteException e) { 15824 } 15825 } 15826 } 15827 Process.setSwappiness(app.pid, 15828 app.curSchedGroup <= Process.THREAD_GROUP_BG_NONINTERACTIVE); 15829 } 15830 } 15831 if (app.repForegroundActivities != app.foregroundActivities) { 15832 app.repForegroundActivities = app.foregroundActivities; 15833 changes |= ProcessChangeItem.CHANGE_ACTIVITIES; 15834 } 15835 if (app.repProcState != app.curProcState) { 15836 app.repProcState = app.curProcState; 15837 changes |= ProcessChangeItem.CHANGE_PROCESS_STATE; 15838 if (app.thread != null) { 15839 try { 15840 if (false) { 15841 //RuntimeException h = new RuntimeException("here"); 15842 Slog.i(TAG, "Sending new process state " + app.repProcState 15843 + " to " + app /*, h*/); 15844 } 15845 app.thread.setProcessState(app.repProcState); 15846 } catch (RemoteException e) { 15847 } 15848 } 15849 } 15850 if (app.setProcState < 0 || ProcessList.procStatesDifferForMem(app.curProcState, 15851 app.setProcState)) { 15852 app.lastStateTime = now; 15853 app.nextPssTime = ProcessList.computeNextPssTime(app.curProcState, true, 15854 isSleeping(), now); 15855 if (DEBUG_PSS) Slog.d(TAG, "Process state change from " 15856 + ProcessList.makeProcStateString(app.setProcState) + " to " 15857 + ProcessList.makeProcStateString(app.curProcState) + " next pss in " 15858 + (app.nextPssTime-now) + ": " + app); 15859 } else { 15860 if (now > app.nextPssTime || (now > (app.lastPssTime+ProcessList.PSS_MAX_INTERVAL) 15861 && now > (app.lastStateTime+ProcessList.PSS_MIN_TIME_FROM_STATE_CHANGE))) { 15862 requestPssLocked(app, app.setProcState); 15863 app.nextPssTime = ProcessList.computeNextPssTime(app.curProcState, false, 15864 isSleeping(), now); 15865 } else if (false && DEBUG_PSS) { 15866 Slog.d(TAG, "Not requesting PSS of " + app + ": next=" + (app.nextPssTime-now)); 15867 } 15868 } 15869 if (app.setProcState != app.curProcState) { 15870 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 15871 "Proc state change of " + app.processName 15872 + " to " + app.curProcState); 15873 app.setProcState = app.curProcState; 15874 if (app.setProcState >= ActivityManager.PROCESS_STATE_HOME) { 15875 app.notCachedSinceIdle = false; 15876 } 15877 if (!doingAll) { 15878 setProcessTrackerState(app, mProcessStats.getMemFactorLocked(), now); 15879 } else { 15880 app.procStateChanged = true; 15881 } 15882 } 15883 15884 if (changes != 0) { 15885 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "Changes in " + app + ": " + changes); 15886 int i = mPendingProcessChanges.size()-1; 15887 ProcessChangeItem item = null; 15888 while (i >= 0) { 15889 item = mPendingProcessChanges.get(i); 15890 if (item.pid == app.pid) { 15891 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "Re-using existing item: " + item); 15892 break; 15893 } 15894 i--; 15895 } 15896 if (i < 0) { 15897 // No existing item in pending changes; need a new one. 15898 final int NA = mAvailProcessChanges.size(); 15899 if (NA > 0) { 15900 item = mAvailProcessChanges.remove(NA-1); 15901 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "Retreiving available item: " + item); 15902 } else { 15903 item = new ProcessChangeItem(); 15904 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "Allocating new item: " + item); 15905 } 15906 item.changes = 0; 15907 item.pid = app.pid; 15908 item.uid = app.info.uid; 15909 if (mPendingProcessChanges.size() == 0) { 15910 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, 15911 "*** Enqueueing dispatch processes changed!"); 15912 mHandler.obtainMessage(DISPATCH_PROCESSES_CHANGED).sendToTarget(); 15913 } 15914 mPendingProcessChanges.add(item); 15915 } 15916 item.changes |= changes; 15917 item.processState = app.repProcState; 15918 item.foregroundActivities = app.repForegroundActivities; 15919 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "Item " 15920 + Integer.toHexString(System.identityHashCode(item)) 15921 + " " + app.toShortString() + ": changes=" + item.changes 15922 + " procState=" + item.processState 15923 + " foreground=" + item.foregroundActivities 15924 + " type=" + app.adjType + " source=" + app.adjSource 15925 + " target=" + app.adjTarget); 15926 } 15927 15928 return success; 15929 } 15930 15931 private final void setProcessTrackerState(ProcessRecord proc, int memFactor, long now) { 15932 if (proc.thread != null && proc.baseProcessTracker != null) { 15933 proc.baseProcessTracker.setState(proc.repProcState, memFactor, now, proc.pkgList); 15934 } 15935 } 15936 15937 private final boolean updateOomAdjLocked(ProcessRecord app, int cachedAdj, 15938 ProcessRecord TOP_APP, boolean doingAll, long now) { 15939 if (app.thread == null) { 15940 return false; 15941 } 15942 15943 final boolean wasKeeping = app.keeping; 15944 15945 computeOomAdjLocked(app, cachedAdj, TOP_APP, doingAll, now); 15946 15947 return applyOomAdjLocked(app, wasKeeping, TOP_APP, doingAll, now); 15948 } 15949 15950 final void updateProcessForegroundLocked(ProcessRecord proc, boolean isForeground, 15951 boolean oomAdj) { 15952 if (isForeground != proc.foregroundServices) { 15953 proc.foregroundServices = isForeground; 15954 ArrayList<ProcessRecord> curProcs = mForegroundPackages.get(proc.info.packageName, 15955 proc.info.uid); 15956 if (isForeground) { 15957 if (curProcs == null) { 15958 curProcs = new ArrayList<ProcessRecord>(); 15959 mForegroundPackages.put(proc.info.packageName, proc.info.uid, curProcs); 15960 } 15961 if (!curProcs.contains(proc)) { 15962 curProcs.add(proc); 15963 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_FOREGROUND_START, 15964 proc.info.packageName, proc.info.uid); 15965 } 15966 } else { 15967 if (curProcs != null) { 15968 if (curProcs.remove(proc)) { 15969 mBatteryStatsService.noteEvent( 15970 BatteryStats.HistoryItem.EVENT_FOREGROUND_FINISH, 15971 proc.info.packageName, proc.info.uid); 15972 if (curProcs.size() <= 0) { 15973 mForegroundPackages.remove(proc.info.packageName, proc.info.uid); 15974 } 15975 } 15976 } 15977 } 15978 if (oomAdj) { 15979 updateOomAdjLocked(); 15980 } 15981 } 15982 } 15983 15984 private final ActivityRecord resumedAppLocked() { 15985 ActivityRecord act = mStackSupervisor.resumedAppLocked(); 15986 String pkg; 15987 int uid; 15988 if (act != null && !act.sleeping) { 15989 pkg = act.packageName; 15990 uid = act.info.applicationInfo.uid; 15991 } else { 15992 pkg = null; 15993 uid = -1; 15994 } 15995 // Has the UID or resumed package name changed? 15996 if (uid != mCurResumedUid || (pkg != mCurResumedPackage 15997 && (pkg == null || !pkg.equals(mCurResumedPackage)))) { 15998 if (mCurResumedPackage != null) { 15999 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_TOP_FINISH, 16000 mCurResumedPackage, mCurResumedUid); 16001 } 16002 mCurResumedPackage = pkg; 16003 mCurResumedUid = uid; 16004 if (mCurResumedPackage != null) { 16005 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_TOP_START, 16006 mCurResumedPackage, mCurResumedUid); 16007 } 16008 } 16009 return act; 16010 } 16011 16012 final boolean updateOomAdjLocked(ProcessRecord app) { 16013 final ActivityRecord TOP_ACT = resumedAppLocked(); 16014 final ProcessRecord TOP_APP = TOP_ACT != null ? TOP_ACT.app : null; 16015 final boolean wasCached = app.cached; 16016 16017 mAdjSeq++; 16018 16019 // This is the desired cached adjusment we want to tell it to use. 16020 // If our app is currently cached, we know it, and that is it. Otherwise, 16021 // we don't know it yet, and it needs to now be cached we will then 16022 // need to do a complete oom adj. 16023 final int cachedAdj = app.curRawAdj >= ProcessList.CACHED_APP_MIN_ADJ 16024 ? app.curRawAdj : ProcessList.UNKNOWN_ADJ; 16025 boolean success = updateOomAdjLocked(app, cachedAdj, TOP_APP, false, 16026 SystemClock.uptimeMillis()); 16027 if (wasCached != app.cached || app.curRawAdj == ProcessList.UNKNOWN_ADJ) { 16028 // Changed to/from cached state, so apps after it in the LRU 16029 // list may also be changed. 16030 updateOomAdjLocked(); 16031 } 16032 return success; 16033 } 16034 16035 final void updateOomAdjLocked() { 16036 final ActivityRecord TOP_ACT = resumedAppLocked(); 16037 final ProcessRecord TOP_APP = TOP_ACT != null ? TOP_ACT.app : null; 16038 final long now = SystemClock.uptimeMillis(); 16039 final long oldTime = now - ProcessList.MAX_EMPTY_TIME; 16040 final int N = mLruProcesses.size(); 16041 16042 if (false) { 16043 RuntimeException e = new RuntimeException(); 16044 e.fillInStackTrace(); 16045 Slog.i(TAG, "updateOomAdj: top=" + TOP_ACT, e); 16046 } 16047 16048 mAdjSeq++; 16049 mNewNumServiceProcs = 0; 16050 mNewNumAServiceProcs = 0; 16051 16052 final int emptyProcessLimit; 16053 final int cachedProcessLimit; 16054 if (mProcessLimit <= 0) { 16055 emptyProcessLimit = cachedProcessLimit = 0; 16056 } else if (mProcessLimit == 1) { 16057 emptyProcessLimit = 1; 16058 cachedProcessLimit = 0; 16059 } else { 16060 emptyProcessLimit = ProcessList.computeEmptyProcessLimit(mProcessLimit); 16061 cachedProcessLimit = mProcessLimit - emptyProcessLimit; 16062 } 16063 16064 // Let's determine how many processes we have running vs. 16065 // how many slots we have for background processes; we may want 16066 // to put multiple processes in a slot of there are enough of 16067 // them. 16068 int numSlots = (ProcessList.CACHED_APP_MAX_ADJ 16069 - ProcessList.CACHED_APP_MIN_ADJ + 1) / 2; 16070 int numEmptyProcs = N - mNumNonCachedProcs - mNumCachedHiddenProcs; 16071 if (numEmptyProcs > cachedProcessLimit) { 16072 // If there are more empty processes than our limit on cached 16073 // processes, then use the cached process limit for the factor. 16074 // This ensures that the really old empty processes get pushed 16075 // down to the bottom, so if we are running low on memory we will 16076 // have a better chance at keeping around more cached processes 16077 // instead of a gazillion empty processes. 16078 numEmptyProcs = cachedProcessLimit; 16079 } 16080 int emptyFactor = numEmptyProcs/numSlots; 16081 if (emptyFactor < 1) emptyFactor = 1; 16082 int cachedFactor = (mNumCachedHiddenProcs > 0 ? mNumCachedHiddenProcs : 1)/numSlots; 16083 if (cachedFactor < 1) cachedFactor = 1; 16084 int stepCached = 0; 16085 int stepEmpty = 0; 16086 int numCached = 0; 16087 int numEmpty = 0; 16088 int numTrimming = 0; 16089 16090 mNumNonCachedProcs = 0; 16091 mNumCachedHiddenProcs = 0; 16092 16093 // First update the OOM adjustment for each of the 16094 // application processes based on their current state. 16095 int curCachedAdj = ProcessList.CACHED_APP_MIN_ADJ; 16096 int nextCachedAdj = curCachedAdj+1; 16097 int curEmptyAdj = ProcessList.CACHED_APP_MIN_ADJ; 16098 int nextEmptyAdj = curEmptyAdj+2; 16099 for (int i=N-1; i>=0; i--) { 16100 ProcessRecord app = mLruProcesses.get(i); 16101 if (!app.killedByAm && app.thread != null) { 16102 app.procStateChanged = false; 16103 final boolean wasKeeping = app.keeping; 16104 computeOomAdjLocked(app, ProcessList.UNKNOWN_ADJ, TOP_APP, true, now); 16105 16106 // If we haven't yet assigned the final cached adj 16107 // to the process, do that now. 16108 if (app.curAdj >= ProcessList.UNKNOWN_ADJ) { 16109 switch (app.curProcState) { 16110 case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY: 16111 case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY_CLIENT: 16112 // This process is a cached process holding activities... 16113 // assign it the next cached value for that type, and then 16114 // step that cached level. 16115 app.curRawAdj = curCachedAdj; 16116 app.curAdj = app.modifyRawOomAdj(curCachedAdj); 16117 if (DEBUG_LRU && false) Slog.d(TAG, "Assigning activity LRU #" + i 16118 + " adj: " + app.curAdj + " (curCachedAdj=" + curCachedAdj 16119 + ")"); 16120 if (curCachedAdj != nextCachedAdj) { 16121 stepCached++; 16122 if (stepCached >= cachedFactor) { 16123 stepCached = 0; 16124 curCachedAdj = nextCachedAdj; 16125 nextCachedAdj += 2; 16126 if (nextCachedAdj > ProcessList.CACHED_APP_MAX_ADJ) { 16127 nextCachedAdj = ProcessList.CACHED_APP_MAX_ADJ; 16128 } 16129 } 16130 } 16131 break; 16132 default: 16133 // For everything else, assign next empty cached process 16134 // level and bump that up. Note that this means that 16135 // long-running services that have dropped down to the 16136 // cached level will be treated as empty (since their process 16137 // state is still as a service), which is what we want. 16138 app.curRawAdj = curEmptyAdj; 16139 app.curAdj = app.modifyRawOomAdj(curEmptyAdj); 16140 if (DEBUG_LRU && false) Slog.d(TAG, "Assigning empty LRU #" + i 16141 + " adj: " + app.curAdj + " (curEmptyAdj=" + curEmptyAdj 16142 + ")"); 16143 if (curEmptyAdj != nextEmptyAdj) { 16144 stepEmpty++; 16145 if (stepEmpty >= emptyFactor) { 16146 stepEmpty = 0; 16147 curEmptyAdj = nextEmptyAdj; 16148 nextEmptyAdj += 2; 16149 if (nextEmptyAdj > ProcessList.CACHED_APP_MAX_ADJ) { 16150 nextEmptyAdj = ProcessList.CACHED_APP_MAX_ADJ; 16151 } 16152 } 16153 } 16154 break; 16155 } 16156 } 16157 16158 applyOomAdjLocked(app, wasKeeping, TOP_APP, true, now); 16159 16160 // Count the number of process types. 16161 switch (app.curProcState) { 16162 case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY: 16163 case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY_CLIENT: 16164 mNumCachedHiddenProcs++; 16165 numCached++; 16166 if (numCached > cachedProcessLimit) { 16167 killUnneededProcessLocked(app, "cached #" + numCached); 16168 } 16169 break; 16170 case ActivityManager.PROCESS_STATE_CACHED_EMPTY: 16171 if (numEmpty > ProcessList.TRIM_EMPTY_APPS 16172 && app.lastActivityTime < oldTime) { 16173 killUnneededProcessLocked(app, "empty for " 16174 + ((oldTime + ProcessList.MAX_EMPTY_TIME - app.lastActivityTime) 16175 / 1000) + "s"); 16176 } else { 16177 numEmpty++; 16178 if (numEmpty > emptyProcessLimit) { 16179 killUnneededProcessLocked(app, "empty #" + numEmpty); 16180 } 16181 } 16182 break; 16183 default: 16184 mNumNonCachedProcs++; 16185 break; 16186 } 16187 16188 if (app.isolated && app.services.size() <= 0) { 16189 // If this is an isolated process, and there are no 16190 // services running in it, then the process is no longer 16191 // needed. We agressively kill these because we can by 16192 // definition not re-use the same process again, and it is 16193 // good to avoid having whatever code was running in them 16194 // left sitting around after no longer needed. 16195 killUnneededProcessLocked(app, "isolated not needed"); 16196 } 16197 16198 if (app.curProcState >= ActivityManager.PROCESS_STATE_HOME 16199 && !app.killedByAm) { 16200 numTrimming++; 16201 } 16202 } 16203 } 16204 16205 mNumServiceProcs = mNewNumServiceProcs; 16206 16207 // Now determine the memory trimming level of background processes. 16208 // Unfortunately we need to start at the back of the list to do this 16209 // properly. We only do this if the number of background apps we 16210 // are managing to keep around is less than half the maximum we desire; 16211 // if we are keeping a good number around, we'll let them use whatever 16212 // memory they want. 16213 final int numCachedAndEmpty = numCached + numEmpty; 16214 int memFactor; 16215 if (numCached <= ProcessList.TRIM_CACHED_APPS 16216 && numEmpty <= ProcessList.TRIM_EMPTY_APPS) { 16217 if (numCachedAndEmpty <= ProcessList.TRIM_CRITICAL_THRESHOLD) { 16218 memFactor = ProcessStats.ADJ_MEM_FACTOR_CRITICAL; 16219 } else if (numCachedAndEmpty <= ProcessList.TRIM_LOW_THRESHOLD) { 16220 memFactor = ProcessStats.ADJ_MEM_FACTOR_LOW; 16221 } else { 16222 memFactor = ProcessStats.ADJ_MEM_FACTOR_MODERATE; 16223 } 16224 } else { 16225 memFactor = ProcessStats.ADJ_MEM_FACTOR_NORMAL; 16226 } 16227 // We always allow the memory level to go up (better). We only allow it to go 16228 // down if we are in a state where that is allowed, *and* the total number of processes 16229 // has gone down since last time. 16230 if (DEBUG_OOM_ADJ) Slog.d(TAG, "oom: memFactor=" + memFactor + " last=" + mLastMemoryLevel 16231 + " allowLow=" + mAllowLowerMemLevel + " numProcs=" + mLruProcesses.size() 16232 + " last=" + mLastNumProcesses); 16233 if (memFactor > mLastMemoryLevel) { 16234 if (!mAllowLowerMemLevel || mLruProcesses.size() >= mLastNumProcesses) { 16235 memFactor = mLastMemoryLevel; 16236 if (DEBUG_OOM_ADJ) Slog.d(TAG, "Keeping last mem factor!"); 16237 } 16238 } 16239 mLastMemoryLevel = memFactor; 16240 mLastNumProcesses = mLruProcesses.size(); 16241 boolean allChanged = mProcessStats.setMemFactorLocked(memFactor, !isSleeping(), now); 16242 final int trackerMemFactor = mProcessStats.getMemFactorLocked(); 16243 if (memFactor != ProcessStats.ADJ_MEM_FACTOR_NORMAL) { 16244 if (mLowRamStartTime == 0) { 16245 mLowRamStartTime = now; 16246 } 16247 int step = 0; 16248 int fgTrimLevel; 16249 switch (memFactor) { 16250 case ProcessStats.ADJ_MEM_FACTOR_CRITICAL: 16251 fgTrimLevel = ComponentCallbacks2.TRIM_MEMORY_RUNNING_CRITICAL; 16252 break; 16253 case ProcessStats.ADJ_MEM_FACTOR_LOW: 16254 fgTrimLevel = ComponentCallbacks2.TRIM_MEMORY_RUNNING_LOW; 16255 break; 16256 default: 16257 fgTrimLevel = ComponentCallbacks2.TRIM_MEMORY_RUNNING_MODERATE; 16258 break; 16259 } 16260 int factor = numTrimming/3; 16261 int minFactor = 2; 16262 if (mHomeProcess != null) minFactor++; 16263 if (mPreviousProcess != null) minFactor++; 16264 if (factor < minFactor) factor = minFactor; 16265 int curLevel = ComponentCallbacks2.TRIM_MEMORY_COMPLETE; 16266 for (int i=N-1; i>=0; i--) { 16267 ProcessRecord app = mLruProcesses.get(i); 16268 if (allChanged || app.procStateChanged) { 16269 setProcessTrackerState(app, trackerMemFactor, now); 16270 app.procStateChanged = false; 16271 } 16272 if (app.curProcState >= ActivityManager.PROCESS_STATE_HOME 16273 && !app.killedByAm) { 16274 if (app.trimMemoryLevel < curLevel && app.thread != null) { 16275 try { 16276 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 16277 "Trimming memory of " + app.processName 16278 + " to " + curLevel); 16279 app.thread.scheduleTrimMemory(curLevel); 16280 } catch (RemoteException e) { 16281 } 16282 if (false) { 16283 // For now we won't do this; our memory trimming seems 16284 // to be good enough at this point that destroying 16285 // activities causes more harm than good. 16286 if (curLevel >= ComponentCallbacks2.TRIM_MEMORY_COMPLETE 16287 && app != mHomeProcess && app != mPreviousProcess) { 16288 // Need to do this on its own message because the stack may not 16289 // be in a consistent state at this point. 16290 // For these apps we will also finish their activities 16291 // to help them free memory. 16292 mStackSupervisor.scheduleDestroyAllActivities(app, "trim"); 16293 } 16294 } 16295 } 16296 app.trimMemoryLevel = curLevel; 16297 step++; 16298 if (step >= factor) { 16299 step = 0; 16300 switch (curLevel) { 16301 case ComponentCallbacks2.TRIM_MEMORY_COMPLETE: 16302 curLevel = ComponentCallbacks2.TRIM_MEMORY_MODERATE; 16303 break; 16304 case ComponentCallbacks2.TRIM_MEMORY_MODERATE: 16305 curLevel = ComponentCallbacks2.TRIM_MEMORY_BACKGROUND; 16306 break; 16307 } 16308 } 16309 } else if (app.curProcState == ActivityManager.PROCESS_STATE_HEAVY_WEIGHT) { 16310 if (app.trimMemoryLevel < ComponentCallbacks2.TRIM_MEMORY_BACKGROUND 16311 && app.thread != null) { 16312 try { 16313 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 16314 "Trimming memory of heavy-weight " + app.processName 16315 + " to " + ComponentCallbacks2.TRIM_MEMORY_BACKGROUND); 16316 app.thread.scheduleTrimMemory( 16317 ComponentCallbacks2.TRIM_MEMORY_BACKGROUND); 16318 } catch (RemoteException e) { 16319 } 16320 } 16321 app.trimMemoryLevel = ComponentCallbacks2.TRIM_MEMORY_BACKGROUND; 16322 } else { 16323 if ((app.curProcState >= ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND 16324 || app.systemNoUi) && app.pendingUiClean) { 16325 // If this application is now in the background and it 16326 // had done UI, then give it the special trim level to 16327 // have it free UI resources. 16328 final int level = ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN; 16329 if (app.trimMemoryLevel < level && app.thread != null) { 16330 try { 16331 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 16332 "Trimming memory of bg-ui " + app.processName 16333 + " to " + level); 16334 app.thread.scheduleTrimMemory(level); 16335 } catch (RemoteException e) { 16336 } 16337 } 16338 app.pendingUiClean = false; 16339 } 16340 if (app.trimMemoryLevel < fgTrimLevel && app.thread != null) { 16341 try { 16342 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 16343 "Trimming memory of fg " + app.processName 16344 + " to " + fgTrimLevel); 16345 app.thread.scheduleTrimMemory(fgTrimLevel); 16346 } catch (RemoteException e) { 16347 } 16348 } 16349 app.trimMemoryLevel = fgTrimLevel; 16350 } 16351 } 16352 } else { 16353 if (mLowRamStartTime != 0) { 16354 mLowRamTimeSinceLastIdle += now - mLowRamStartTime; 16355 mLowRamStartTime = 0; 16356 } 16357 for (int i=N-1; i>=0; i--) { 16358 ProcessRecord app = mLruProcesses.get(i); 16359 if (allChanged || app.procStateChanged) { 16360 setProcessTrackerState(app, trackerMemFactor, now); 16361 app.procStateChanged = false; 16362 } 16363 if ((app.curProcState >= ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND 16364 || app.systemNoUi) && app.pendingUiClean) { 16365 if (app.trimMemoryLevel < ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN 16366 && app.thread != null) { 16367 try { 16368 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 16369 "Trimming memory of ui hidden " + app.processName 16370 + " to " + ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN); 16371 app.thread.scheduleTrimMemory( 16372 ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN); 16373 } catch (RemoteException e) { 16374 } 16375 } 16376 app.pendingUiClean = false; 16377 } 16378 app.trimMemoryLevel = 0; 16379 } 16380 } 16381 16382 if (mAlwaysFinishActivities) { 16383 // Need to do this on its own message because the stack may not 16384 // be in a consistent state at this point. 16385 mStackSupervisor.scheduleDestroyAllActivities(null, "always-finish"); 16386 } 16387 16388 if (allChanged) { 16389 requestPssAllProcsLocked(now, false, mProcessStats.isMemFactorLowered()); 16390 } 16391 16392 if (mProcessStats.shouldWriteNowLocked(now)) { 16393 mHandler.post(new Runnable() { 16394 @Override public void run() { 16395 synchronized (ActivityManagerService.this) { 16396 mProcessStats.writeStateAsyncLocked(); 16397 } 16398 } 16399 }); 16400 } 16401 16402 if (DEBUG_OOM_ADJ) { 16403 Slog.d(TAG, "Did OOM ADJ in " + (SystemClock.uptimeMillis()-now) + "ms"); 16404 } 16405 } 16406 16407 final void trimApplications() { 16408 synchronized (this) { 16409 int i; 16410 16411 // First remove any unused application processes whose package 16412 // has been removed. 16413 for (i=mRemovedProcesses.size()-1; i>=0; i--) { 16414 final ProcessRecord app = mRemovedProcesses.get(i); 16415 if (app.activities.size() == 0 16416 && app.curReceiver == null && app.services.size() == 0) { 16417 Slog.i( 16418 TAG, "Exiting empty application process " 16419 + app.processName + " (" 16420 + (app.thread != null ? app.thread.asBinder() : null) 16421 + ")\n"); 16422 if (app.pid > 0 && app.pid != MY_PID) { 16423 EventLog.writeEvent(EventLogTags.AM_KILL, app.userId, app.pid, 16424 app.processName, app.setAdj, "empty"); 16425 app.killedByAm = true; 16426 Process.killProcessQuiet(app.pid); 16427 } else { 16428 try { 16429 app.thread.scheduleExit(); 16430 } catch (Exception e) { 16431 // Ignore exceptions. 16432 } 16433 } 16434 cleanUpApplicationRecordLocked(app, false, true, -1); 16435 mRemovedProcesses.remove(i); 16436 16437 if (app.persistent) { 16438 if (app.persistent) { 16439 addAppLocked(app.info, false, null /* ABI override */); 16440 } 16441 } 16442 } 16443 } 16444 16445 // Now update the oom adj for all processes. 16446 updateOomAdjLocked(); 16447 } 16448 } 16449 16450 /** This method sends the specified signal to each of the persistent apps */ 16451 public void signalPersistentProcesses(int sig) throws RemoteException { 16452 if (sig != Process.SIGNAL_USR1) { 16453 throw new SecurityException("Only SIGNAL_USR1 is allowed"); 16454 } 16455 16456 synchronized (this) { 16457 if (checkCallingPermission(android.Manifest.permission.SIGNAL_PERSISTENT_PROCESSES) 16458 != PackageManager.PERMISSION_GRANTED) { 16459 throw new SecurityException("Requires permission " 16460 + android.Manifest.permission.SIGNAL_PERSISTENT_PROCESSES); 16461 } 16462 16463 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 16464 ProcessRecord r = mLruProcesses.get(i); 16465 if (r.thread != null && r.persistent) { 16466 Process.sendSignal(r.pid, sig); 16467 } 16468 } 16469 } 16470 } 16471 16472 private void stopProfilerLocked(ProcessRecord proc, String path, int profileType) { 16473 if (proc == null || proc == mProfileProc) { 16474 proc = mProfileProc; 16475 path = mProfileFile; 16476 profileType = mProfileType; 16477 clearProfilerLocked(); 16478 } 16479 if (proc == null) { 16480 return; 16481 } 16482 try { 16483 proc.thread.profilerControl(false, path, null, profileType); 16484 } catch (RemoteException e) { 16485 throw new IllegalStateException("Process disappeared"); 16486 } 16487 } 16488 16489 private void clearProfilerLocked() { 16490 if (mProfileFd != null) { 16491 try { 16492 mProfileFd.close(); 16493 } catch (IOException e) { 16494 } 16495 } 16496 mProfileApp = null; 16497 mProfileProc = null; 16498 mProfileFile = null; 16499 mProfileType = 0; 16500 mAutoStopProfiler = false; 16501 } 16502 16503 public boolean profileControl(String process, int userId, boolean start, 16504 String path, ParcelFileDescriptor fd, int profileType) throws RemoteException { 16505 16506 try { 16507 synchronized (this) { 16508 // note: hijacking SET_ACTIVITY_WATCHER, but should be changed to 16509 // its own permission. 16510 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 16511 != PackageManager.PERMISSION_GRANTED) { 16512 throw new SecurityException("Requires permission " 16513 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 16514 } 16515 16516 if (start && fd == null) { 16517 throw new IllegalArgumentException("null fd"); 16518 } 16519 16520 ProcessRecord proc = null; 16521 if (process != null) { 16522 proc = findProcessLocked(process, userId, "profileControl"); 16523 } 16524 16525 if (start && (proc == null || proc.thread == null)) { 16526 throw new IllegalArgumentException("Unknown process: " + process); 16527 } 16528 16529 if (start) { 16530 stopProfilerLocked(null, null, 0); 16531 setProfileApp(proc.info, proc.processName, path, fd, false); 16532 mProfileProc = proc; 16533 mProfileType = profileType; 16534 try { 16535 fd = fd.dup(); 16536 } catch (IOException e) { 16537 fd = null; 16538 } 16539 proc.thread.profilerControl(start, path, fd, profileType); 16540 fd = null; 16541 mProfileFd = null; 16542 } else { 16543 stopProfilerLocked(proc, path, profileType); 16544 if (fd != null) { 16545 try { 16546 fd.close(); 16547 } catch (IOException e) { 16548 } 16549 } 16550 } 16551 16552 return true; 16553 } 16554 } catch (RemoteException e) { 16555 throw new IllegalStateException("Process disappeared"); 16556 } finally { 16557 if (fd != null) { 16558 try { 16559 fd.close(); 16560 } catch (IOException e) { 16561 } 16562 } 16563 } 16564 } 16565 16566 private ProcessRecord findProcessLocked(String process, int userId, String callName) { 16567 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 16568 userId, true, true, callName, null); 16569 ProcessRecord proc = null; 16570 try { 16571 int pid = Integer.parseInt(process); 16572 synchronized (mPidsSelfLocked) { 16573 proc = mPidsSelfLocked.get(pid); 16574 } 16575 } catch (NumberFormatException e) { 16576 } 16577 16578 if (proc == null) { 16579 ArrayMap<String, SparseArray<ProcessRecord>> all 16580 = mProcessNames.getMap(); 16581 SparseArray<ProcessRecord> procs = all.get(process); 16582 if (procs != null && procs.size() > 0) { 16583 proc = procs.valueAt(0); 16584 if (userId != UserHandle.USER_ALL && proc.userId != userId) { 16585 for (int i=1; i<procs.size(); i++) { 16586 ProcessRecord thisProc = procs.valueAt(i); 16587 if (thisProc.userId == userId) { 16588 proc = thisProc; 16589 break; 16590 } 16591 } 16592 } 16593 } 16594 } 16595 16596 return proc; 16597 } 16598 16599 public boolean dumpHeap(String process, int userId, boolean managed, 16600 String path, ParcelFileDescriptor fd) throws RemoteException { 16601 16602 try { 16603 synchronized (this) { 16604 // note: hijacking SET_ACTIVITY_WATCHER, but should be changed to 16605 // its own permission (same as profileControl). 16606 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 16607 != PackageManager.PERMISSION_GRANTED) { 16608 throw new SecurityException("Requires permission " 16609 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 16610 } 16611 16612 if (fd == null) { 16613 throw new IllegalArgumentException("null fd"); 16614 } 16615 16616 ProcessRecord proc = findProcessLocked(process, userId, "dumpHeap"); 16617 if (proc == null || proc.thread == null) { 16618 throw new IllegalArgumentException("Unknown process: " + process); 16619 } 16620 16621 boolean isDebuggable = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 16622 if (!isDebuggable) { 16623 if ((proc.info.flags&ApplicationInfo.FLAG_DEBUGGABLE) == 0) { 16624 throw new SecurityException("Process not debuggable: " + proc); 16625 } 16626 } 16627 16628 proc.thread.dumpHeap(managed, path, fd); 16629 fd = null; 16630 return true; 16631 } 16632 } catch (RemoteException e) { 16633 throw new IllegalStateException("Process disappeared"); 16634 } finally { 16635 if (fd != null) { 16636 try { 16637 fd.close(); 16638 } catch (IOException e) { 16639 } 16640 } 16641 } 16642 } 16643 16644 /** In this method we try to acquire our lock to make sure that we have not deadlocked */ 16645 public void monitor() { 16646 synchronized (this) { } 16647 } 16648 16649 void onCoreSettingsChange(Bundle settings) { 16650 for (int i = mLruProcesses.size() - 1; i >= 0; i--) { 16651 ProcessRecord processRecord = mLruProcesses.get(i); 16652 try { 16653 if (processRecord.thread != null) { 16654 processRecord.thread.setCoreSettings(settings); 16655 } 16656 } catch (RemoteException re) { 16657 /* ignore */ 16658 } 16659 } 16660 } 16661 16662 // Multi-user methods 16663 16664 /** 16665 * Start user, if its not already running, but don't bring it to foreground. 16666 */ 16667 @Override 16668 public boolean startUserInBackground(final int userId) { 16669 return startUser(userId, /* foreground */ false); 16670 } 16671 16672 /** 16673 * Refreshes the list of users related to the current user when either a 16674 * user switch happens or when a new related user is started in the 16675 * background. 16676 */ 16677 private void updateCurrentProfileIdsLocked() { 16678 final List<UserInfo> profiles = getUserManagerLocked().getProfiles( 16679 mCurrentUserId, false /* enabledOnly */); 16680 int[] currentProfileIds = new int[profiles.size()]; // profiles will not be null 16681 for (int i = 0; i < currentProfileIds.length; i++) { 16682 currentProfileIds[i] = profiles.get(i).id; 16683 } 16684 mCurrentProfileIds = currentProfileIds; 16685 } 16686 16687 private Set getProfileIdsLocked(int userId) { 16688 Set userIds = new HashSet<Integer>(); 16689 final List<UserInfo> profiles = getUserManagerLocked().getProfiles( 16690 userId, false /* enabledOnly */); 16691 for (UserInfo user : profiles) { 16692 userIds.add(Integer.valueOf(user.id)); 16693 } 16694 return userIds; 16695 } 16696 16697 @Override 16698 public boolean switchUser(final int userId) { 16699 return startUser(userId, /* foregound */ true); 16700 } 16701 16702 private boolean startUser(final int userId, boolean foreground) { 16703 if (checkCallingPermission(INTERACT_ACROSS_USERS_FULL) 16704 != PackageManager.PERMISSION_GRANTED) { 16705 String msg = "Permission Denial: switchUser() from pid=" 16706 + Binder.getCallingPid() 16707 + ", uid=" + Binder.getCallingUid() 16708 + " requires " + INTERACT_ACROSS_USERS_FULL; 16709 Slog.w(TAG, msg); 16710 throw new SecurityException(msg); 16711 } 16712 16713 if (DEBUG_MU) Slog.i(TAG_MU, "starting userid:" + userId + " fore:" + foreground); 16714 16715 final long ident = Binder.clearCallingIdentity(); 16716 try { 16717 synchronized (this) { 16718 final int oldUserId = mCurrentUserId; 16719 if (oldUserId == userId) { 16720 return true; 16721 } 16722 16723 mStackSupervisor.setLockTaskModeLocked(null, false); 16724 16725 final UserInfo userInfo = getUserManagerLocked().getUserInfo(userId); 16726 if (userInfo == null) { 16727 Slog.w(TAG, "No user info for user #" + userId); 16728 return false; 16729 } 16730 16731 if (foreground) { 16732 mWindowManager.startFreezingScreen(R.anim.screen_user_exit, 16733 R.anim.screen_user_enter); 16734 } 16735 16736 boolean needStart = false; 16737 16738 // If the user we are switching to is not currently started, then 16739 // we need to start it now. 16740 if (mStartedUsers.get(userId) == null) { 16741 mStartedUsers.put(userId, new UserStartedState(new UserHandle(userId), false)); 16742 updateStartedUserArrayLocked(); 16743 needStart = true; 16744 } 16745 16746 final Integer userIdInt = Integer.valueOf(userId); 16747 mUserLru.remove(userIdInt); 16748 mUserLru.add(userIdInt); 16749 16750 if (foreground) { 16751 mCurrentUserId = userId; 16752 updateCurrentProfileIdsLocked(); 16753 mWindowManager.setCurrentUser(userId, mCurrentProfileIds); 16754 // Once the internal notion of the active user has switched, we lock the device 16755 // with the option to show the user switcher on the keyguard. 16756 mWindowManager.lockNow(null); 16757 } else { 16758 final Integer currentUserIdInt = Integer.valueOf(mCurrentUserId); 16759 updateCurrentProfileIdsLocked(); 16760 mWindowManager.setCurrentProfileIds(mCurrentProfileIds); 16761 mUserLru.remove(currentUserIdInt); 16762 mUserLru.add(currentUserIdInt); 16763 } 16764 16765 final UserStartedState uss = mStartedUsers.get(userId); 16766 16767 // Make sure user is in the started state. If it is currently 16768 // stopping, we need to knock that off. 16769 if (uss.mState == UserStartedState.STATE_STOPPING) { 16770 // If we are stopping, we haven't sent ACTION_SHUTDOWN, 16771 // so we can just fairly silently bring the user back from 16772 // the almost-dead. 16773 uss.mState = UserStartedState.STATE_RUNNING; 16774 updateStartedUserArrayLocked(); 16775 needStart = true; 16776 } else if (uss.mState == UserStartedState.STATE_SHUTDOWN) { 16777 // This means ACTION_SHUTDOWN has been sent, so we will 16778 // need to treat this as a new boot of the user. 16779 uss.mState = UserStartedState.STATE_BOOTING; 16780 updateStartedUserArrayLocked(); 16781 needStart = true; 16782 } 16783 16784 if (uss.mState == UserStartedState.STATE_BOOTING) { 16785 // Booting up a new user, need to tell system services about it. 16786 // Note that this is on the same handler as scheduling of broadcasts, 16787 // which is important because it needs to go first. 16788 mHandler.sendMessage(mHandler.obtainMessage(SYSTEM_USER_START_MSG, userId)); 16789 } 16790 16791 if (foreground) { 16792 mHandler.sendMessage(mHandler.obtainMessage(SYSTEM_USER_CURRENT_MSG, userId)); 16793 mHandler.removeMessages(REPORT_USER_SWITCH_MSG); 16794 mHandler.removeMessages(USER_SWITCH_TIMEOUT_MSG); 16795 mHandler.sendMessage(mHandler.obtainMessage(REPORT_USER_SWITCH_MSG, 16796 oldUserId, userId, uss)); 16797 mHandler.sendMessageDelayed(mHandler.obtainMessage(USER_SWITCH_TIMEOUT_MSG, 16798 oldUserId, userId, uss), USER_SWITCH_TIMEOUT); 16799 } 16800 16801 if (needStart) { 16802 Intent intent = new Intent(Intent.ACTION_USER_STARTED); 16803 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 16804 | Intent.FLAG_RECEIVER_FOREGROUND); 16805 intent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 16806 broadcastIntentLocked(null, null, intent, 16807 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 16808 false, false, MY_PID, Process.SYSTEM_UID, userId); 16809 } 16810 16811 if ((userInfo.flags&UserInfo.FLAG_INITIALIZED) == 0) { 16812 if (userId != UserHandle.USER_OWNER) { 16813 Intent intent = new Intent(Intent.ACTION_USER_INITIALIZE); 16814 intent.addFlags(Intent.FLAG_RECEIVER_FOREGROUND); 16815 broadcastIntentLocked(null, null, intent, null, 16816 new IIntentReceiver.Stub() { 16817 public void performReceive(Intent intent, int resultCode, 16818 String data, Bundle extras, boolean ordered, 16819 boolean sticky, int sendingUser) { 16820 userInitialized(uss, userId); 16821 } 16822 }, 0, null, null, null, AppOpsManager.OP_NONE, 16823 true, false, MY_PID, Process.SYSTEM_UID, 16824 userId); 16825 uss.initializing = true; 16826 } else { 16827 getUserManagerLocked().makeInitialized(userInfo.id); 16828 } 16829 } 16830 16831 if (foreground) { 16832 boolean homeInFront = mStackSupervisor.switchUserLocked(userId, uss); 16833 if (homeInFront) { 16834 startHomeActivityLocked(userId); 16835 } else { 16836 mStackSupervisor.resumeTopActivitiesLocked(); 16837 } 16838 EventLogTags.writeAmSwitchUser(userId); 16839 getUserManagerLocked().userForeground(userId); 16840 sendUserSwitchBroadcastsLocked(oldUserId, userId); 16841 } else { 16842 mStackSupervisor.startBackgroundUserLocked(userId, uss); 16843 } 16844 16845 if (needStart) { 16846 Intent intent = new Intent(Intent.ACTION_USER_STARTING); 16847 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 16848 intent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 16849 broadcastIntentLocked(null, null, intent, 16850 null, new IIntentReceiver.Stub() { 16851 @Override 16852 public void performReceive(Intent intent, int resultCode, String data, 16853 Bundle extras, boolean ordered, boolean sticky, int sendingUser) 16854 throws RemoteException { 16855 } 16856 }, 0, null, null, 16857 android.Manifest.permission.INTERACT_ACROSS_USERS, AppOpsManager.OP_NONE, 16858 true, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 16859 } 16860 } 16861 } finally { 16862 Binder.restoreCallingIdentity(ident); 16863 } 16864 16865 return true; 16866 } 16867 16868 void sendUserSwitchBroadcastsLocked(int oldUserId, int newUserId) { 16869 long ident = Binder.clearCallingIdentity(); 16870 try { 16871 Intent intent; 16872 if (oldUserId >= 0) { 16873 intent = new Intent(Intent.ACTION_USER_BACKGROUND); 16874 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 16875 | Intent.FLAG_RECEIVER_FOREGROUND); 16876 intent.putExtra(Intent.EXTRA_USER_HANDLE, oldUserId); 16877 broadcastIntentLocked(null, null, intent, 16878 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 16879 false, false, MY_PID, Process.SYSTEM_UID, oldUserId); 16880 } 16881 if (newUserId >= 0) { 16882 intent = new Intent(Intent.ACTION_USER_FOREGROUND); 16883 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 16884 | Intent.FLAG_RECEIVER_FOREGROUND); 16885 intent.putExtra(Intent.EXTRA_USER_HANDLE, newUserId); 16886 broadcastIntentLocked(null, null, intent, 16887 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 16888 false, false, MY_PID, Process.SYSTEM_UID, newUserId); 16889 intent = new Intent(Intent.ACTION_USER_SWITCHED); 16890 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 16891 | Intent.FLAG_RECEIVER_FOREGROUND); 16892 intent.putExtra(Intent.EXTRA_USER_HANDLE, newUserId); 16893 broadcastIntentLocked(null, null, intent, 16894 null, null, 0, null, null, 16895 android.Manifest.permission.MANAGE_USERS, AppOpsManager.OP_NONE, 16896 false, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 16897 } 16898 } finally { 16899 Binder.restoreCallingIdentity(ident); 16900 } 16901 } 16902 16903 void dispatchUserSwitch(final UserStartedState uss, final int oldUserId, 16904 final int newUserId) { 16905 final int N = mUserSwitchObservers.beginBroadcast(); 16906 if (N > 0) { 16907 final IRemoteCallback callback = new IRemoteCallback.Stub() { 16908 int mCount = 0; 16909 @Override 16910 public void sendResult(Bundle data) throws RemoteException { 16911 synchronized (ActivityManagerService.this) { 16912 if (mCurUserSwitchCallback == this) { 16913 mCount++; 16914 if (mCount == N) { 16915 sendContinueUserSwitchLocked(uss, oldUserId, newUserId); 16916 } 16917 } 16918 } 16919 } 16920 }; 16921 synchronized (this) { 16922 uss.switching = true; 16923 mCurUserSwitchCallback = callback; 16924 } 16925 for (int i=0; i<N; i++) { 16926 try { 16927 mUserSwitchObservers.getBroadcastItem(i).onUserSwitching( 16928 newUserId, callback); 16929 } catch (RemoteException e) { 16930 } 16931 } 16932 } else { 16933 synchronized (this) { 16934 sendContinueUserSwitchLocked(uss, oldUserId, newUserId); 16935 } 16936 } 16937 mUserSwitchObservers.finishBroadcast(); 16938 } 16939 16940 void timeoutUserSwitch(UserStartedState uss, int oldUserId, int newUserId) { 16941 synchronized (this) { 16942 Slog.w(TAG, "User switch timeout: from " + oldUserId + " to " + newUserId); 16943 sendContinueUserSwitchLocked(uss, oldUserId, newUserId); 16944 } 16945 } 16946 16947 void sendContinueUserSwitchLocked(UserStartedState uss, int oldUserId, int newUserId) { 16948 mCurUserSwitchCallback = null; 16949 mHandler.removeMessages(USER_SWITCH_TIMEOUT_MSG); 16950 mHandler.sendMessage(mHandler.obtainMessage(CONTINUE_USER_SWITCH_MSG, 16951 oldUserId, newUserId, uss)); 16952 } 16953 16954 void userInitialized(UserStartedState uss, int newUserId) { 16955 completeSwitchAndInitalize(uss, newUserId, true, false); 16956 } 16957 16958 void continueUserSwitch(UserStartedState uss, int oldUserId, int newUserId) { 16959 completeSwitchAndInitalize(uss, newUserId, false, true); 16960 } 16961 16962 void completeSwitchAndInitalize(UserStartedState uss, int newUserId, 16963 boolean clearInitializing, boolean clearSwitching) { 16964 boolean unfrozen = false; 16965 synchronized (this) { 16966 if (clearInitializing) { 16967 uss.initializing = false; 16968 getUserManagerLocked().makeInitialized(uss.mHandle.getIdentifier()); 16969 } 16970 if (clearSwitching) { 16971 uss.switching = false; 16972 } 16973 if (!uss.switching && !uss.initializing) { 16974 mWindowManager.stopFreezingScreen(); 16975 unfrozen = true; 16976 } 16977 } 16978 if (unfrozen) { 16979 final int N = mUserSwitchObservers.beginBroadcast(); 16980 for (int i=0; i<N; i++) { 16981 try { 16982 mUserSwitchObservers.getBroadcastItem(i).onUserSwitchComplete(newUserId); 16983 } catch (RemoteException e) { 16984 } 16985 } 16986 mUserSwitchObservers.finishBroadcast(); 16987 } 16988 } 16989 16990 void scheduleStartProfilesLocked() { 16991 if (!mHandler.hasMessages(START_PROFILES_MSG)) { 16992 mHandler.sendMessageDelayed(mHandler.obtainMessage(START_PROFILES_MSG), 16993 DateUtils.SECOND_IN_MILLIS); 16994 } 16995 } 16996 16997 void startProfilesLocked() { 16998 if (DEBUG_MU) Slog.i(TAG_MU, "startProfilesLocked"); 16999 List<UserInfo> profiles = getUserManagerLocked().getProfiles( 17000 mCurrentUserId, false /* enabledOnly */); 17001 List<UserInfo> toStart = new ArrayList<UserInfo>(profiles.size()); 17002 for (UserInfo user : profiles) { 17003 if ((user.flags & UserInfo.FLAG_INITIALIZED) == UserInfo.FLAG_INITIALIZED 17004 && user.id != mCurrentUserId) { 17005 toStart.add(user); 17006 } 17007 } 17008 final int n = toStart.size(); 17009 int i = 0; 17010 for (; i < n && i < (MAX_RUNNING_USERS - 1); ++i) { 17011 startUserInBackground(toStart.get(i).id); 17012 } 17013 if (i < n) { 17014 Slog.w(TAG_MU, "More profiles than MAX_RUNNING_USERS"); 17015 } 17016 } 17017 17018 void finishUserBoot(UserStartedState uss) { 17019 synchronized (this) { 17020 if (uss.mState == UserStartedState.STATE_BOOTING 17021 && mStartedUsers.get(uss.mHandle.getIdentifier()) == uss) { 17022 uss.mState = UserStartedState.STATE_RUNNING; 17023 final int userId = uss.mHandle.getIdentifier(); 17024 Intent intent = new Intent(Intent.ACTION_BOOT_COMPLETED, null); 17025 intent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 17026 intent.addFlags(Intent.FLAG_RECEIVER_NO_ABORT); 17027 broadcastIntentLocked(null, null, intent, 17028 null, null, 0, null, null, 17029 android.Manifest.permission.RECEIVE_BOOT_COMPLETED, AppOpsManager.OP_NONE, 17030 true, false, MY_PID, Process.SYSTEM_UID, userId); 17031 } 17032 } 17033 } 17034 17035 void finishUserSwitch(UserStartedState uss) { 17036 synchronized (this) { 17037 finishUserBoot(uss); 17038 17039 startProfilesLocked(); 17040 17041 int num = mUserLru.size(); 17042 int i = 0; 17043 while (num > MAX_RUNNING_USERS && i < mUserLru.size()) { 17044 Integer oldUserId = mUserLru.get(i); 17045 UserStartedState oldUss = mStartedUsers.get(oldUserId); 17046 if (oldUss == null) { 17047 // Shouldn't happen, but be sane if it does. 17048 mUserLru.remove(i); 17049 num--; 17050 continue; 17051 } 17052 if (oldUss.mState == UserStartedState.STATE_STOPPING 17053 || oldUss.mState == UserStartedState.STATE_SHUTDOWN) { 17054 // This user is already stopping, doesn't count. 17055 num--; 17056 i++; 17057 continue; 17058 } 17059 if (oldUserId == UserHandle.USER_OWNER || oldUserId == mCurrentUserId) { 17060 // Owner and current can't be stopped, but count as running. 17061 i++; 17062 continue; 17063 } 17064 // This is a user to be stopped. 17065 stopUserLocked(oldUserId, null); 17066 num--; 17067 i++; 17068 } 17069 } 17070 } 17071 17072 @Override 17073 public int stopUser(final int userId, final IStopUserCallback callback) { 17074 if (checkCallingPermission(INTERACT_ACROSS_USERS_FULL) 17075 != PackageManager.PERMISSION_GRANTED) { 17076 String msg = "Permission Denial: switchUser() from pid=" 17077 + Binder.getCallingPid() 17078 + ", uid=" + Binder.getCallingUid() 17079 + " requires " + INTERACT_ACROSS_USERS_FULL; 17080 Slog.w(TAG, msg); 17081 throw new SecurityException(msg); 17082 } 17083 if (userId <= 0) { 17084 throw new IllegalArgumentException("Can't stop primary user " + userId); 17085 } 17086 synchronized (this) { 17087 return stopUserLocked(userId, callback); 17088 } 17089 } 17090 17091 private int stopUserLocked(final int userId, final IStopUserCallback callback) { 17092 if (DEBUG_MU) Slog.i(TAG_MU, "stopUserLocked userId=" + userId); 17093 if (mCurrentUserId == userId) { 17094 return ActivityManager.USER_OP_IS_CURRENT; 17095 } 17096 17097 final UserStartedState uss = mStartedUsers.get(userId); 17098 if (uss == null) { 17099 // User is not started, nothing to do... but we do need to 17100 // callback if requested. 17101 if (callback != null) { 17102 mHandler.post(new Runnable() { 17103 @Override 17104 public void run() { 17105 try { 17106 callback.userStopped(userId); 17107 } catch (RemoteException e) { 17108 } 17109 } 17110 }); 17111 } 17112 return ActivityManager.USER_OP_SUCCESS; 17113 } 17114 17115 if (callback != null) { 17116 uss.mStopCallbacks.add(callback); 17117 } 17118 17119 if (uss.mState != UserStartedState.STATE_STOPPING 17120 && uss.mState != UserStartedState.STATE_SHUTDOWN) { 17121 uss.mState = UserStartedState.STATE_STOPPING; 17122 updateStartedUserArrayLocked(); 17123 17124 long ident = Binder.clearCallingIdentity(); 17125 try { 17126 // We are going to broadcast ACTION_USER_STOPPING and then 17127 // once that is done send a final ACTION_SHUTDOWN and then 17128 // stop the user. 17129 final Intent stoppingIntent = new Intent(Intent.ACTION_USER_STOPPING); 17130 stoppingIntent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 17131 stoppingIntent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 17132 stoppingIntent.putExtra(Intent.EXTRA_SHUTDOWN_USERSPACE_ONLY, true); 17133 final Intent shutdownIntent = new Intent(Intent.ACTION_SHUTDOWN); 17134 // This is the result receiver for the final shutdown broadcast. 17135 final IIntentReceiver shutdownReceiver = new IIntentReceiver.Stub() { 17136 @Override 17137 public void performReceive(Intent intent, int resultCode, String data, 17138 Bundle extras, boolean ordered, boolean sticky, int sendingUser) { 17139 finishUserStop(uss); 17140 } 17141 }; 17142 // This is the result receiver for the initial stopping broadcast. 17143 final IIntentReceiver stoppingReceiver = new IIntentReceiver.Stub() { 17144 @Override 17145 public void performReceive(Intent intent, int resultCode, String data, 17146 Bundle extras, boolean ordered, boolean sticky, int sendingUser) { 17147 // On to the next. 17148 synchronized (ActivityManagerService.this) { 17149 if (uss.mState != UserStartedState.STATE_STOPPING) { 17150 // Whoops, we are being started back up. Abort, abort! 17151 return; 17152 } 17153 uss.mState = UserStartedState.STATE_SHUTDOWN; 17154 } 17155 mSystemServiceManager.stopUser(userId); 17156 broadcastIntentLocked(null, null, shutdownIntent, 17157 null, shutdownReceiver, 0, null, null, null, AppOpsManager.OP_NONE, 17158 true, false, MY_PID, Process.SYSTEM_UID, userId); 17159 } 17160 }; 17161 // Kick things off. 17162 broadcastIntentLocked(null, null, stoppingIntent, 17163 null, stoppingReceiver, 0, null, null, 17164 android.Manifest.permission.INTERACT_ACROSS_USERS, AppOpsManager.OP_NONE, 17165 true, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 17166 } finally { 17167 Binder.restoreCallingIdentity(ident); 17168 } 17169 } 17170 17171 return ActivityManager.USER_OP_SUCCESS; 17172 } 17173 17174 void finishUserStop(UserStartedState uss) { 17175 final int userId = uss.mHandle.getIdentifier(); 17176 boolean stopped; 17177 ArrayList<IStopUserCallback> callbacks; 17178 synchronized (this) { 17179 callbacks = new ArrayList<IStopUserCallback>(uss.mStopCallbacks); 17180 if (mStartedUsers.get(userId) != uss) { 17181 stopped = false; 17182 } else if (uss.mState != UserStartedState.STATE_SHUTDOWN) { 17183 stopped = false; 17184 } else { 17185 stopped = true; 17186 // User can no longer run. 17187 mStartedUsers.remove(userId); 17188 mUserLru.remove(Integer.valueOf(userId)); 17189 updateStartedUserArrayLocked(); 17190 17191 // Clean up all state and processes associated with the user. 17192 // Kill all the processes for the user. 17193 forceStopUserLocked(userId, "finish user"); 17194 } 17195 } 17196 17197 for (int i=0; i<callbacks.size(); i++) { 17198 try { 17199 if (stopped) callbacks.get(i).userStopped(userId); 17200 else callbacks.get(i).userStopAborted(userId); 17201 } catch (RemoteException e) { 17202 } 17203 } 17204 17205 if (stopped) { 17206 mSystemServiceManager.cleanupUser(userId); 17207 synchronized (this) { 17208 mStackSupervisor.removeUserLocked(userId); 17209 } 17210 } 17211 } 17212 17213 @Override 17214 public UserInfo getCurrentUser() { 17215 if ((checkCallingPermission(android.Manifest.permission.INTERACT_ACROSS_USERS) 17216 != PackageManager.PERMISSION_GRANTED) && ( 17217 checkCallingPermission(INTERACT_ACROSS_USERS_FULL) 17218 != PackageManager.PERMISSION_GRANTED)) { 17219 String msg = "Permission Denial: getCurrentUser() from pid=" 17220 + Binder.getCallingPid() 17221 + ", uid=" + Binder.getCallingUid() 17222 + " requires " + android.Manifest.permission.INTERACT_ACROSS_USERS; 17223 Slog.w(TAG, msg); 17224 throw new SecurityException(msg); 17225 } 17226 synchronized (this) { 17227 return getUserManagerLocked().getUserInfo(mCurrentUserId); 17228 } 17229 } 17230 17231 int getCurrentUserIdLocked() { 17232 return mCurrentUserId; 17233 } 17234 17235 @Override 17236 public boolean isUserRunning(int userId, boolean orStopped) { 17237 if (checkCallingPermission(android.Manifest.permission.INTERACT_ACROSS_USERS) 17238 != PackageManager.PERMISSION_GRANTED) { 17239 String msg = "Permission Denial: isUserRunning() from pid=" 17240 + Binder.getCallingPid() 17241 + ", uid=" + Binder.getCallingUid() 17242 + " requires " + android.Manifest.permission.INTERACT_ACROSS_USERS; 17243 Slog.w(TAG, msg); 17244 throw new SecurityException(msg); 17245 } 17246 synchronized (this) { 17247 return isUserRunningLocked(userId, orStopped); 17248 } 17249 } 17250 17251 boolean isUserRunningLocked(int userId, boolean orStopped) { 17252 UserStartedState state = mStartedUsers.get(userId); 17253 if (state == null) { 17254 return false; 17255 } 17256 if (orStopped) { 17257 return true; 17258 } 17259 return state.mState != UserStartedState.STATE_STOPPING 17260 && state.mState != UserStartedState.STATE_SHUTDOWN; 17261 } 17262 17263 @Override 17264 public int[] getRunningUserIds() { 17265 if (checkCallingPermission(android.Manifest.permission.INTERACT_ACROSS_USERS) 17266 != PackageManager.PERMISSION_GRANTED) { 17267 String msg = "Permission Denial: isUserRunning() from pid=" 17268 + Binder.getCallingPid() 17269 + ", uid=" + Binder.getCallingUid() 17270 + " requires " + android.Manifest.permission.INTERACT_ACROSS_USERS; 17271 Slog.w(TAG, msg); 17272 throw new SecurityException(msg); 17273 } 17274 synchronized (this) { 17275 return mStartedUserArray; 17276 } 17277 } 17278 17279 private void updateStartedUserArrayLocked() { 17280 int num = 0; 17281 for (int i=0; i<mStartedUsers.size(); i++) { 17282 UserStartedState uss = mStartedUsers.valueAt(i); 17283 // This list does not include stopping users. 17284 if (uss.mState != UserStartedState.STATE_STOPPING 17285 && uss.mState != UserStartedState.STATE_SHUTDOWN) { 17286 num++; 17287 } 17288 } 17289 mStartedUserArray = new int[num]; 17290 num = 0; 17291 for (int i=0; i<mStartedUsers.size(); i++) { 17292 UserStartedState uss = mStartedUsers.valueAt(i); 17293 if (uss.mState != UserStartedState.STATE_STOPPING 17294 && uss.mState != UserStartedState.STATE_SHUTDOWN) { 17295 mStartedUserArray[num] = mStartedUsers.keyAt(i); 17296 num++; 17297 } 17298 } 17299 } 17300 17301 @Override 17302 public void registerUserSwitchObserver(IUserSwitchObserver observer) { 17303 if (checkCallingPermission(INTERACT_ACROSS_USERS_FULL) 17304 != PackageManager.PERMISSION_GRANTED) { 17305 String msg = "Permission Denial: registerUserSwitchObserver() from pid=" 17306 + Binder.getCallingPid() 17307 + ", uid=" + Binder.getCallingUid() 17308 + " requires " + INTERACT_ACROSS_USERS_FULL; 17309 Slog.w(TAG, msg); 17310 throw new SecurityException(msg); 17311 } 17312 17313 mUserSwitchObservers.register(observer); 17314 } 17315 17316 @Override 17317 public void unregisterUserSwitchObserver(IUserSwitchObserver observer) { 17318 mUserSwitchObservers.unregister(observer); 17319 } 17320 17321 private boolean userExists(int userId) { 17322 if (userId == 0) { 17323 return true; 17324 } 17325 UserManagerService ums = getUserManagerLocked(); 17326 return ums != null ? (ums.getUserInfo(userId) != null) : false; 17327 } 17328 17329 int[] getUsersLocked() { 17330 UserManagerService ums = getUserManagerLocked(); 17331 return ums != null ? ums.getUserIds() : new int[] { 0 }; 17332 } 17333 17334 UserManagerService getUserManagerLocked() { 17335 if (mUserManager == null) { 17336 IBinder b = ServiceManager.getService(Context.USER_SERVICE); 17337 mUserManager = (UserManagerService)IUserManager.Stub.asInterface(b); 17338 } 17339 return mUserManager; 17340 } 17341 17342 private int applyUserId(int uid, int userId) { 17343 return UserHandle.getUid(userId, uid); 17344 } 17345 17346 ApplicationInfo getAppInfoForUser(ApplicationInfo info, int userId) { 17347 if (info == null) return null; 17348 ApplicationInfo newInfo = new ApplicationInfo(info); 17349 newInfo.uid = applyUserId(info.uid, userId); 17350 newInfo.dataDir = USER_DATA_DIR + userId + "/" 17351 + info.packageName; 17352 return newInfo; 17353 } 17354 17355 ActivityInfo getActivityInfoForUser(ActivityInfo aInfo, int userId) { 17356 if (aInfo == null 17357 || (userId < 1 && aInfo.applicationInfo.uid < UserHandle.PER_USER_RANGE)) { 17358 return aInfo; 17359 } 17360 17361 ActivityInfo info = new ActivityInfo(aInfo); 17362 info.applicationInfo = getAppInfoForUser(info.applicationInfo, userId); 17363 return info; 17364 } 17365 17366 private final class LocalService extends ActivityManagerInternal { 17367 @Override 17368 public void goingToSleep() { 17369 ActivityManagerService.this.goingToSleep(); 17370 } 17371 17372 @Override 17373 public void wakingUp() { 17374 ActivityManagerService.this.wakingUp(); 17375 } 17376 } 17377 17378 /** 17379 * An implementation of IAppTask, that allows an app to manage its own tasks via 17380 * {@link android.app.ActivityManager.AppTask}. We keep track of the callingUid to ensure that 17381 * only the process that calls getAppTasks() can call the AppTask methods. 17382 */ 17383 class AppTaskImpl extends IAppTask.Stub { 17384 private int mTaskId; 17385 private int mCallingUid; 17386 17387 public AppTaskImpl(int taskId, int callingUid) { 17388 mTaskId = taskId; 17389 mCallingUid = callingUid; 17390 } 17391 17392 @Override 17393 public void finishAndRemoveTask() { 17394 // Ensure that we are called from the same process that created this AppTask 17395 if (mCallingUid != Binder.getCallingUid()) { 17396 Slog.w(TAG, "finishAndRemoveTask: caller " + mCallingUid 17397 + " does not match caller of getAppTasks(): " + Binder.getCallingUid()); 17398 return; 17399 } 17400 17401 synchronized (ActivityManagerService.this) { 17402 long origId = Binder.clearCallingIdentity(); 17403 try { 17404 TaskRecord tr = recentTaskForIdLocked(mTaskId); 17405 if (tr != null) { 17406 // Only kill the process if we are not a new document 17407 int flags = tr.getBaseIntent().getFlags(); 17408 boolean isDocument = (flags & Intent.FLAG_ACTIVITY_NEW_DOCUMENT) == 17409 Intent.FLAG_ACTIVITY_NEW_DOCUMENT; 17410 removeTaskByIdLocked(mTaskId, 17411 !isDocument ? ActivityManager.REMOVE_TASK_KILL_PROCESS : 0); 17412 } 17413 } finally { 17414 Binder.restoreCallingIdentity(origId); 17415 } 17416 } 17417 } 17418 17419 @Override 17420 public ActivityManager.RecentTaskInfo getTaskInfo() { 17421 // Ensure that we are called from the same process that created this AppTask 17422 if (mCallingUid != Binder.getCallingUid()) { 17423 Slog.w(TAG, "finishAndRemoveTask: caller " + mCallingUid 17424 + " does not match caller of getAppTasks(): " + Binder.getCallingUid()); 17425 return null; 17426 } 17427 17428 synchronized (ActivityManagerService.this) { 17429 long origId = Binder.clearCallingIdentity(); 17430 try { 17431 TaskRecord tr = recentTaskForIdLocked(mTaskId); 17432 if (tr != null) { 17433 return createRecentTaskInfoFromTaskRecord(tr); 17434 } 17435 } finally { 17436 Binder.restoreCallingIdentity(origId); 17437 } 17438 return null; 17439 } 17440 } 17441 } 17442} 17443