ActivityManagerService.java revision 585d8b28f5d174d0f50d0c7c3e5e7202f6cd36a1
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 com.android.internal.telephony.TelephonyIntents; 20import com.google.android.collect.Lists; 21import com.google.android.collect.Maps; 22import com.android.internal.R; 23import com.android.internal.annotations.GuardedBy; 24import com.android.internal.app.AssistUtils; 25import com.android.internal.app.DumpHeapActivity; 26import com.android.internal.app.IAppOpsCallback; 27import com.android.internal.app.IAppOpsService; 28import com.android.internal.app.IVoiceInteractor; 29import com.android.internal.app.ProcessMap; 30import com.android.internal.app.SystemUserHomeActivity; 31import com.android.internal.app.procstats.ProcessStats; 32import com.android.internal.os.BackgroundThread; 33import com.android.internal.os.BatteryStatsImpl; 34import com.android.internal.os.IResultReceiver; 35import com.android.internal.os.ProcessCpuTracker; 36import com.android.internal.os.TransferPipe; 37import com.android.internal.os.Zygote; 38import com.android.internal.os.InstallerConnection.InstallerException; 39import com.android.internal.util.ArrayUtils; 40import com.android.internal.util.FastPrintWriter; 41import com.android.internal.util.FastXmlSerializer; 42import com.android.internal.util.MemInfoReader; 43import com.android.internal.util.Preconditions; 44import com.android.internal.util.ProgressReporter; 45import com.android.server.AppOpsService; 46import com.android.server.AttributeCache; 47import com.android.server.DeviceIdleController; 48import com.android.server.IntentResolver; 49import com.android.server.LocalServices; 50import com.android.server.LockGuard; 51import com.android.server.ServiceThread; 52import com.android.server.SystemService; 53import com.android.server.SystemServiceManager; 54import com.android.server.Watchdog; 55import com.android.server.am.ActivityStack.ActivityState; 56import com.android.server.firewall.IntentFirewall; 57import com.android.server.pm.Installer; 58import com.android.server.statusbar.StatusBarManagerInternal; 59import com.android.server.vr.VrManagerInternal; 60import com.android.server.wm.WindowManagerService; 61 62import org.xmlpull.v1.XmlPullParser; 63import org.xmlpull.v1.XmlPullParserException; 64import org.xmlpull.v1.XmlSerializer; 65 66import android.Manifest; 67import android.annotation.UserIdInt; 68import android.app.Activity; 69import android.app.ActivityManager; 70import android.app.ActivityManager.RunningTaskInfo; 71import android.app.ActivityManager.StackId; 72import android.app.ActivityManager.StackInfo; 73import android.app.ActivityManager.TaskThumbnailInfo; 74import android.app.ActivityManagerInternal; 75import android.app.ActivityManagerInternal.SleepToken; 76import android.app.ActivityManagerNative; 77import android.app.ActivityOptions; 78import android.app.ActivityThread; 79import android.app.AlertDialog; 80import android.app.AppGlobals; 81import android.app.AppOpsManager; 82import android.app.ApplicationErrorReport; 83import android.app.ApplicationThreadNative; 84import android.app.BroadcastOptions; 85import android.app.Dialog; 86import android.app.IActivityContainer; 87import android.app.IActivityContainerCallback; 88import android.app.IActivityController; 89import android.app.IAppTask; 90import android.app.IApplicationThread; 91import android.app.IInstrumentationWatcher; 92import android.app.INotificationManager; 93import android.app.IProcessObserver; 94import android.app.IServiceConnection; 95import android.app.IStopUserCallback; 96import android.app.ITaskStackListener; 97import android.app.IUiAutomationConnection; 98import android.app.IUidObserver; 99import android.app.IUserSwitchObserver; 100import android.app.Instrumentation; 101import android.app.KeyguardManager; 102import android.app.Notification; 103import android.app.NotificationManager; 104import android.app.PendingIntent; 105import android.app.ProfilerInfo; 106import android.app.admin.DevicePolicyManager; 107import android.app.admin.DevicePolicyManagerInternal; 108import android.app.assist.AssistContent; 109import android.app.assist.AssistStructure; 110import android.app.backup.IBackupManager; 111import android.app.usage.UsageEvents; 112import android.app.usage.UsageStatsManagerInternal; 113import android.appwidget.AppWidgetManager; 114import android.content.ActivityNotFoundException; 115import android.content.BroadcastReceiver; 116import android.content.ClipData; 117import android.content.ComponentCallbacks2; 118import android.content.ComponentName; 119import android.content.ContentProvider; 120import android.content.ContentResolver; 121import android.content.Context; 122import android.content.DialogInterface; 123import android.content.IContentProvider; 124import android.content.IIntentReceiver; 125import android.content.IIntentSender; 126import android.content.Intent; 127import android.content.IntentFilter; 128import android.content.IntentSender; 129import android.content.pm.ActivityInfo; 130import android.content.pm.ApplicationInfo; 131import android.content.pm.ConfigurationInfo; 132import android.content.pm.IPackageDataObserver; 133import android.content.pm.IPackageManager; 134import android.content.pm.InstrumentationInfo; 135import android.content.pm.PackageInfo; 136import android.content.pm.PackageManager; 137import android.content.pm.PackageManager.NameNotFoundException; 138import android.content.pm.PackageManagerInternal; 139import android.content.pm.ParceledListSlice; 140import android.content.pm.PathPermission; 141import android.content.pm.PermissionInfo; 142import android.content.pm.ProviderInfo; 143import android.content.pm.ResolveInfo; 144import android.content.pm.ServiceInfo; 145import android.content.pm.ShortcutServiceInternal; 146import android.content.pm.UserInfo; 147import android.content.res.CompatibilityInfo; 148import android.content.res.Configuration; 149import android.content.res.Resources; 150import android.database.ContentObserver; 151import android.graphics.Bitmap; 152import android.graphics.Point; 153import android.graphics.Rect; 154import android.location.LocationManager; 155import android.net.Proxy; 156import android.net.ProxyInfo; 157import android.net.Uri; 158import android.os.BatteryStats; 159import android.os.Binder; 160import android.os.Build; 161import android.os.Bundle; 162import android.os.Debug; 163import android.os.DropBoxManager; 164import android.os.Environment; 165import android.os.FactoryTest; 166import android.os.FileObserver; 167import android.os.FileUtils; 168import android.os.Handler; 169import android.os.IBinder; 170import android.os.IPermissionController; 171import android.os.IProcessInfoService; 172import android.os.IProgressListener; 173import android.os.LocaleList; 174import android.os.Looper; 175import android.os.Message; 176import android.os.Parcel; 177import android.os.ParcelFileDescriptor; 178import android.os.PersistableBundle; 179import android.os.PowerManager; 180import android.os.PowerManagerInternal; 181import android.os.Process; 182import android.os.RemoteCallbackList; 183import android.os.RemoteException; 184import android.os.ResultReceiver; 185import android.os.ServiceManager; 186import android.os.StrictMode; 187import android.os.SystemClock; 188import android.os.SystemProperties; 189import android.os.Trace; 190import android.os.TransactionTooLargeException; 191import android.os.UpdateLock; 192import android.os.UserHandle; 193import android.os.UserManager; 194import android.os.WorkSource; 195import android.os.storage.IMountService; 196import android.os.storage.MountServiceInternal; 197import android.os.storage.StorageManager; 198import android.provider.Settings; 199import android.service.voice.IVoiceInteractionSession; 200import android.service.voice.VoiceInteractionManagerInternal; 201import android.service.voice.VoiceInteractionSession; 202import android.text.format.DateUtils; 203import android.text.format.Time; 204import android.text.style.SuggestionSpan; 205import android.util.ArrayMap; 206import android.util.ArraySet; 207import android.util.AtomicFile; 208import android.util.DebugUtils; 209import android.util.EventLog; 210import android.util.Log; 211import android.util.Pair; 212import android.util.PrintWriterPrinter; 213import android.util.Slog; 214import android.util.SparseArray; 215import android.util.TimeUtils; 216import android.util.Xml; 217import android.view.Display; 218import android.view.Gravity; 219import android.view.LayoutInflater; 220import android.view.View; 221import android.view.WindowManager; 222 223import java.io.File; 224import java.io.FileDescriptor; 225import java.io.FileInputStream; 226import java.io.FileNotFoundException; 227import java.io.FileOutputStream; 228import java.io.IOException; 229import java.io.InputStreamReader; 230import java.io.PrintWriter; 231import java.io.StringWriter; 232import java.lang.ref.WeakReference; 233import java.nio.charset.StandardCharsets; 234import java.util.ArrayList; 235import java.util.Arrays; 236import java.util.Collections; 237import java.util.Comparator; 238import java.util.HashMap; 239import java.util.HashSet; 240import java.util.Iterator; 241import java.util.List; 242import java.util.Locale; 243import java.util.Map; 244import java.util.Objects; 245import java.util.Set; 246import java.util.concurrent.atomic.AtomicBoolean; 247import java.util.concurrent.atomic.AtomicLong; 248 249import dalvik.system.VMRuntime; 250 251import libcore.io.IoUtils; 252import libcore.util.EmptyArray; 253 254import static android.Manifest.permission.INTERACT_ACROSS_USERS; 255import static android.Manifest.permission.INTERACT_ACROSS_USERS_FULL; 256import static android.Manifest.permission.MANAGE_ACTIVITY_STACKS; 257import static android.Manifest.permission.START_TASKS_FROM_RECENTS; 258import static android.app.ActivityManager.DOCKED_STACK_CREATE_MODE_TOP_OR_LEFT; 259import static android.app.ActivityManager.RESIZE_MODE_PRESERVE_WINDOW; 260import static android.app.ActivityManager.StackId.DOCKED_STACK_ID; 261import static android.app.ActivityManager.StackId.FIRST_STATIC_STACK_ID; 262import static android.app.ActivityManager.StackId.FREEFORM_WORKSPACE_STACK_ID; 263import static android.app.ActivityManager.StackId.FULLSCREEN_WORKSPACE_STACK_ID; 264import static android.app.ActivityManager.StackId.HOME_STACK_ID; 265import static android.app.ActivityManager.StackId.INVALID_STACK_ID; 266import static android.app.ActivityManager.StackId.LAST_STATIC_STACK_ID; 267import static android.app.ActivityManager.StackId.PINNED_STACK_ID; 268import static android.content.pm.PackageManager.FEATURE_FREEFORM_WINDOW_MANAGEMENT; 269import static android.content.pm.PackageManager.FEATURE_PICTURE_IN_PICTURE; 270import static android.content.pm.PackageManager.GET_PROVIDERS; 271import static android.content.pm.PackageManager.MATCH_DEBUG_TRIAGED_MISSING; 272import static android.content.pm.PackageManager.MATCH_DIRECT_BOOT_UNAWARE; 273import static android.content.pm.PackageManager.MATCH_SYSTEM_ONLY; 274import static android.content.pm.PackageManager.MATCH_UNINSTALLED_PACKAGES; 275import static android.content.pm.PackageManager.PERMISSION_GRANTED; 276import static android.content.res.Configuration.UI_MODE_TYPE_TELEVISION; 277import static android.provider.Settings.Global.ALWAYS_FINISH_ACTIVITIES; 278import static android.provider.Settings.Global.DEBUG_APP; 279import static android.provider.Settings.Global.DEVELOPMENT_ENABLE_FREEFORM_WINDOWS_SUPPORT; 280import static android.provider.Settings.Global.DEVELOPMENT_FORCE_RESIZABLE_ACTIVITIES; 281import static android.provider.Settings.Global.DEVELOPMENT_FORCE_RTL; 282import static android.provider.Settings.Global.LENIENT_BACKGROUND_CHECK; 283import static android.provider.Settings.Global.WAIT_FOR_DEBUGGER; 284import static android.provider.Settings.System.FONT_SCALE; 285import static com.android.internal.util.XmlUtils.readBooleanAttribute; 286import static com.android.internal.util.XmlUtils.readIntAttribute; 287import static com.android.internal.util.XmlUtils.readLongAttribute; 288import static com.android.internal.util.XmlUtils.writeBooleanAttribute; 289import static com.android.internal.util.XmlUtils.writeIntAttribute; 290import static com.android.internal.util.XmlUtils.writeLongAttribute; 291import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_ALL; 292import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_ANR; 293import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_BACKUP; 294import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_BROADCAST; 295import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_BROADCAST_BACKGROUND; 296import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_BROADCAST_LIGHT; 297import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_CLEANUP; 298import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_CONFIGURATION; 299import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_FOCUS; 300import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_IMMERSIVE; 301import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_LOCKSCREEN; 302import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_LOCKTASK; 303import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_LRU; 304import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_MU; 305import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_OOM_ADJ; 306import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_PERMISSIONS_REVIEW; 307import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_POWER; 308import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_POWER_QUICK; 309import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_PROCESSES; 310import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_PROCESS_OBSERVERS; 311import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_PROVIDER; 312import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_PSS; 313import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_RECENTS; 314import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_SERVICE; 315import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_STACK; 316import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_SWITCH; 317import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_TASKS; 318import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_UID_OBSERVERS; 319import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_URI_PERMISSION; 320import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_USAGE_STATS; 321import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_VISIBILITY; 322import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_VISIBLE_BEHIND; 323import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_BACKUP; 324import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_BROADCAST; 325import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_CLEANUP; 326import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_CONFIGURATION; 327import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_FOCUS; 328import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_IMMERSIVE; 329import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_LOCKSCREEN; 330import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_LOCKTASK; 331import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_LRU; 332import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_MU; 333import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_OOM_ADJ; 334import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_POWER; 335import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_PROCESSES; 336import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_PROCESS_OBSERVERS; 337import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_PROVIDER; 338import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_PSS; 339import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_RECENTS; 340import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_SERVICE; 341import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_STACK; 342import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_SWITCH; 343import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_UID_OBSERVERS; 344import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_URI_PERMISSION; 345import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_VISIBILITY; 346import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_VISIBLE_BEHIND; 347import static com.android.server.am.ActivityManagerDebugConfig.TAG_AM; 348import static com.android.server.am.ActivityManagerDebugConfig.TAG_WITH_CLASS_NAME; 349import static com.android.server.am.ActivityRecord.RECENTS_ACTIVITY_TYPE; 350import static com.android.server.am.ActivityStackSupervisor.ActivityContainer.FORCE_NEW_TASK_FLAGS; 351import static com.android.server.am.ActivityStackSupervisor.DEFER_RESUME; 352import static com.android.server.am.ActivityStackSupervisor.FORCE_FOCUS; 353import static com.android.server.am.ActivityStackSupervisor.ON_TOP; 354import static com.android.server.am.ActivityStackSupervisor.PRESERVE_WINDOWS; 355import static com.android.server.am.ActivityStackSupervisor.RESTORE_FROM_RECENTS; 356import static com.android.server.am.TaskRecord.INVALID_TASK_ID; 357import static com.android.server.am.TaskRecord.LOCK_TASK_AUTH_DONT_LOCK; 358import static com.android.server.am.TaskRecord.LOCK_TASK_AUTH_LAUNCHABLE_PRIV; 359import static com.android.server.am.TaskRecord.LOCK_TASK_AUTH_PINNABLE; 360import static com.android.server.wm.AppTransition.TRANSIT_ACTIVITY_OPEN; 361import static com.android.server.wm.AppTransition.TRANSIT_ACTIVITY_RELAUNCH; 362import static com.android.server.wm.AppTransition.TRANSIT_TASK_IN_PLACE; 363import static com.android.server.wm.AppTransition.TRANSIT_TASK_OPEN; 364import static com.android.server.wm.AppTransition.TRANSIT_TASK_TO_FRONT; 365import static org.xmlpull.v1.XmlPullParser.END_DOCUMENT; 366import static org.xmlpull.v1.XmlPullParser.START_TAG; 367 368public final class ActivityManagerService extends ActivityManagerNative 369 implements Watchdog.Monitor, BatteryStatsImpl.BatteryCallback { 370 371 private static final String TAG = TAG_WITH_CLASS_NAME ? "ActivityManagerService" : TAG_AM; 372 private static final String TAG_BACKUP = TAG + POSTFIX_BACKUP; 373 private static final String TAG_BROADCAST = TAG + POSTFIX_BROADCAST; 374 private static final String TAG_CLEANUP = TAG + POSTFIX_CLEANUP; 375 private static final String TAG_CONFIGURATION = TAG + POSTFIX_CONFIGURATION; 376 private static final String TAG_FOCUS = TAG + POSTFIX_FOCUS; 377 private static final String TAG_IMMERSIVE = TAG + POSTFIX_IMMERSIVE; 378 private static final String TAG_LOCKSCREEN = TAG + POSTFIX_LOCKSCREEN; 379 private static final String TAG_LOCKTASK = TAG + POSTFIX_LOCKTASK; 380 private static final String TAG_LRU = TAG + POSTFIX_LRU; 381 private static final String TAG_MU = TAG + POSTFIX_MU; 382 private static final String TAG_OOM_ADJ = TAG + POSTFIX_OOM_ADJ; 383 private static final String TAG_POWER = TAG + POSTFIX_POWER; 384 private static final String TAG_PROCESS_OBSERVERS = TAG + POSTFIX_PROCESS_OBSERVERS; 385 private static final String TAG_PROCESSES = TAG + POSTFIX_PROCESSES; 386 private static final String TAG_PROVIDER = TAG + POSTFIX_PROVIDER; 387 private static final String TAG_PSS = TAG + POSTFIX_PSS; 388 private static final String TAG_RECENTS = TAG + POSTFIX_RECENTS; 389 private static final String TAG_SERVICE = TAG + POSTFIX_SERVICE; 390 private static final String TAG_STACK = TAG + POSTFIX_STACK; 391 private static final String TAG_SWITCH = TAG + POSTFIX_SWITCH; 392 private static final String TAG_UID_OBSERVERS = TAG + POSTFIX_UID_OBSERVERS; 393 private static final String TAG_URI_PERMISSION = TAG + POSTFIX_URI_PERMISSION; 394 private static final String TAG_VISIBILITY = TAG + POSTFIX_VISIBILITY; 395 private static final String TAG_VISIBLE_BEHIND = TAG + POSTFIX_VISIBLE_BEHIND; 396 397 // Mock "pretend we're idle now" broadcast action to the job scheduler; declared 398 // here so that while the job scheduler can depend on AMS, the other way around 399 // need not be the case. 400 public static final String ACTION_TRIGGER_IDLE = "com.android.server.ACTION_TRIGGER_IDLE"; 401 402 /** Control over CPU and battery monitoring */ 403 // write battery stats every 30 minutes. 404 static final long BATTERY_STATS_TIME = 30 * 60 * 1000; 405 static final boolean MONITOR_CPU_USAGE = true; 406 // don't sample cpu less than every 5 seconds. 407 static final long MONITOR_CPU_MIN_TIME = 5 * 1000; 408 // wait possibly forever for next cpu sample. 409 static final long MONITOR_CPU_MAX_TIME = 0x0fffffff; 410 static final boolean MONITOR_THREAD_CPU_USAGE = false; 411 412 // The flags that are set for all calls we make to the package manager. 413 static final int STOCK_PM_FLAGS = PackageManager.GET_SHARED_LIBRARY_FILES; 414 415 static final String SYSTEM_DEBUGGABLE = "ro.debuggable"; 416 417 static final boolean IS_USER_BUILD = "user".equals(Build.TYPE); 418 419 // Amount of time after a call to stopAppSwitches() during which we will 420 // prevent further untrusted switches from happening. 421 static final long APP_SWITCH_DELAY_TIME = 5*1000; 422 423 // How long we wait for a launched process to attach to the activity manager 424 // before we decide it's never going to come up for real. 425 static final int PROC_START_TIMEOUT = 10*1000; 426 // How long we wait for an attached process to publish its content providers 427 // before we decide it must be hung. 428 static final int CONTENT_PROVIDER_PUBLISH_TIMEOUT = 10*1000; 429 430 // How long we will retain processes hosting content providers in the "last activity" 431 // state before allowing them to drop down to the regular cached LRU list. This is 432 // to avoid thrashing of provider processes under low memory situations. 433 static final int CONTENT_PROVIDER_RETAIN_TIME = 20*1000; 434 435 // How long we wait for a launched process to attach to the activity manager 436 // before we decide it's never going to come up for real, when the process was 437 // started with a wrapper for instrumentation (such as Valgrind) because it 438 // could take much longer than usual. 439 static final int PROC_START_TIMEOUT_WITH_WRAPPER = 1200*1000; 440 441 // How long to wait after going idle before forcing apps to GC. 442 static final int GC_TIMEOUT = 5*1000; 443 444 // The minimum amount of time between successive GC requests for a process. 445 static final int GC_MIN_INTERVAL = 60*1000; 446 447 // The minimum amount of time between successive PSS requests for a process. 448 static final int FULL_PSS_MIN_INTERVAL = 10*60*1000; 449 450 // The minimum amount of time between successive PSS requests for a process 451 // when the request is due to the memory state being lowered. 452 static final int FULL_PSS_LOWERED_INTERVAL = 2*60*1000; 453 454 // The rate at which we check for apps using excessive power -- 15 mins. 455 static final int POWER_CHECK_DELAY = (DEBUG_POWER_QUICK ? 2 : 15) * 60*1000; 456 457 // The minimum sample duration we will allow before deciding we have 458 // enough data on wake locks to start killing things. 459 static final int WAKE_LOCK_MIN_CHECK_DURATION = (DEBUG_POWER_QUICK ? 1 : 5) * 60*1000; 460 461 // The minimum sample duration we will allow before deciding we have 462 // enough data on CPU usage to start killing things. 463 static final int CPU_MIN_CHECK_DURATION = (DEBUG_POWER_QUICK ? 1 : 5) * 60*1000; 464 465 // How long we allow a receiver to run before giving up on it. 466 static final int BROADCAST_FG_TIMEOUT = 10*1000; 467 static final int BROADCAST_BG_TIMEOUT = 60*1000; 468 469 // How long we wait until we timeout on key dispatching. 470 static final int KEY_DISPATCHING_TIMEOUT = 5*1000; 471 472 // How long we wait until we timeout on key dispatching during instrumentation. 473 static final int INSTRUMENTATION_KEY_DISPATCHING_TIMEOUT = 60*1000; 474 475 // This is the amount of time an app needs to be running a foreground service before 476 // we will consider it to be doing interaction for usage stats. 477 static final int SERVICE_USAGE_INTERACTION_TIME = 30*60*1000; 478 479 // Maximum amount of time we will allow to elapse before re-reporting usage stats 480 // interaction with foreground processes. 481 static final long USAGE_STATS_INTERACTION_INTERVAL = 24*60*60*1000L; 482 483 // This is the amount of time we allow an app to settle after it goes into the background, 484 // before we start restricting what it can do. 485 static final int BACKGROUND_SETTLE_TIME = 1*60*1000; 486 487 // How long to wait in getAssistContextExtras for the activity and foreground services 488 // to respond with the result. 489 static final int PENDING_ASSIST_EXTRAS_TIMEOUT = 500; 490 491 // How long top wait when going through the modern assist (which doesn't need to block 492 // on getting this result before starting to launch its UI). 493 static final int PENDING_ASSIST_EXTRAS_LONG_TIMEOUT = 2000; 494 495 // Maximum number of persisted Uri grants a package is allowed 496 static final int MAX_PERSISTED_URI_GRANTS = 128; 497 498 static final int MY_PID = Process.myPid(); 499 500 static final String[] EMPTY_STRING_ARRAY = new String[0]; 501 502 // How many bytes to write into the dropbox log before truncating 503 static final int DROPBOX_MAX_SIZE = 256 * 1024; 504 505 // Access modes for handleIncomingUser. 506 static final int ALLOW_NON_FULL = 0; 507 static final int ALLOW_NON_FULL_IN_PROFILE = 1; 508 static final int ALLOW_FULL_ONLY = 2; 509 510 // Delay in notifying task stack change listeners (in millis) 511 static final int NOTIFY_TASK_STACK_CHANGE_LISTENERS_DELAY = 100; 512 513 // Necessary ApplicationInfo flags to mark an app as persistent 514 private static final int PERSISTENT_MASK = 515 ApplicationInfo.FLAG_SYSTEM|ApplicationInfo.FLAG_PERSISTENT; 516 517 // Intent sent when remote bugreport collection has been completed 518 private static final String INTENT_REMOTE_BUGREPORT_FINISHED = 519 "android.intent.action.REMOTE_BUGREPORT_FINISHED"; 520 521 // Delay to disable app launch boost 522 static final int APP_BOOST_MESSAGE_DELAY = 3000; 523 // Lower delay than APP_BOOST_MESSAGE_DELAY to disable the boost 524 static final int APP_BOOST_TIMEOUT = 2500; 525 526 // Used to indicate that a task is removed it should also be removed from recents. 527 private static final boolean REMOVE_FROM_RECENTS = true; 528 // Used to indicate that an app transition should be animated. 529 static final boolean ANIMATE = true; 530 531 // Determines whether to take full screen screenshots 532 static final boolean TAKE_FULLSCREEN_SCREENSHOTS = true; 533 public static final float FULLSCREEN_SCREENSHOT_SCALE = 0.6f; 534 535 private static native int nativeMigrateToBoost(); 536 private static native int nativeMigrateFromBoost(); 537 private boolean mIsBoosted = false; 538 private long mBoostStartTime = 0; 539 540 /** All system services */ 541 SystemServiceManager mSystemServiceManager; 542 543 private Installer mInstaller; 544 545 /** Run all ActivityStacks through this */ 546 final ActivityStackSupervisor mStackSupervisor; 547 548 final ActivityStarter mActivityStarter; 549 550 /** Task stack change listeners. */ 551 private final RemoteCallbackList<ITaskStackListener> mTaskStackListeners = 552 new RemoteCallbackList<ITaskStackListener>(); 553 554 final InstrumentationReporter mInstrumentationReporter = new InstrumentationReporter(); 555 556 public IntentFirewall mIntentFirewall; 557 558 // Whether we should show our dialogs (ANR, crash, etc) or just perform their 559 // default actuion automatically. Important for devices without direct input 560 // devices. 561 private boolean mShowDialogs = true; 562 private boolean mInVrMode = false; 563 564 BroadcastQueue mFgBroadcastQueue; 565 BroadcastQueue mBgBroadcastQueue; 566 // Convenient for easy iteration over the queues. Foreground is first 567 // so that dispatch of foreground broadcasts gets precedence. 568 final BroadcastQueue[] mBroadcastQueues = new BroadcastQueue[2]; 569 570 BroadcastQueue broadcastQueueForIntent(Intent intent) { 571 final boolean isFg = (intent.getFlags() & Intent.FLAG_RECEIVER_FOREGROUND) != 0; 572 if (DEBUG_BROADCAST_BACKGROUND) Slog.i(TAG_BROADCAST, 573 "Broadcast intent " + intent + " on " 574 + (isFg ? "foreground" : "background") + " queue"); 575 return (isFg) ? mFgBroadcastQueue : mBgBroadcastQueue; 576 } 577 578 /** 579 * Activity we have told the window manager to have key focus. 580 */ 581 ActivityRecord mFocusedActivity = null; 582 583 /** 584 * User id of the last activity mFocusedActivity was set to. 585 */ 586 private int mLastFocusedUserId; 587 588 /** 589 * If non-null, we are tracking the time the user spends in the currently focused app. 590 */ 591 private AppTimeTracker mCurAppTimeTracker; 592 593 /** 594 * List of intents that were used to start the most recent tasks. 595 */ 596 final RecentTasks mRecentTasks; 597 598 /** 599 * For addAppTask: cached of the last activity component that was added. 600 */ 601 ComponentName mLastAddedTaskComponent; 602 603 /** 604 * For addAppTask: cached of the last activity uid that was added. 605 */ 606 int mLastAddedTaskUid; 607 608 /** 609 * For addAppTask: cached of the last ActivityInfo that was added. 610 */ 611 ActivityInfo mLastAddedTaskActivity; 612 613 /** 614 * List of packages whitelisted by DevicePolicyManager for locktask. Indexed by userId. 615 */ 616 SparseArray<String[]> mLockTaskPackages = new SparseArray<>(); 617 618 /** 619 * The package name of the DeviceOwner. This package is not permitted to have its data cleared. 620 */ 621 String mDeviceOwnerName; 622 623 final UserController mUserController; 624 625 final AppErrors mAppErrors; 626 627 boolean mDoingSetFocusedActivity; 628 629 public boolean canShowErrorDialogs() { 630 return mShowDialogs && !mSleeping && !mShuttingDown; 631 } 632 633 // it's a semaphore; boost when 0->1, reset when 1->0 634 static ThreadLocal<Integer> sIsBoosted = new ThreadLocal<Integer>() { 635 @Override protected Integer initialValue() { 636 return 0; 637 } 638 }; 639 640 static void boostPriorityForLockedSection() { 641 if (sIsBoosted.get() == 0) { 642 // boost to prio 118 while holding a global lock 643 Process.setThreadPriority(Process.myTid(), -2); 644 //Log.e(TAG, "PRIORITY BOOST: set priority on TID " + Process.myTid()); 645 } 646 int cur = sIsBoosted.get(); 647 sIsBoosted.set(cur + 1); 648 } 649 650 static void resetPriorityAfterLockedSection() { 651 sIsBoosted.set(sIsBoosted.get() - 1); 652 if (sIsBoosted.get() == 0) { 653 //Log.e(TAG, "PRIORITY BOOST: reset priority on TID " + Process.myTid()); 654 Process.setThreadPriority(Process.myTid(), 0); 655 } 656 } 657 public class PendingAssistExtras extends Binder implements Runnable { 658 public final ActivityRecord activity; 659 public final Bundle extras; 660 public final Intent intent; 661 public final String hint; 662 public final IResultReceiver receiver; 663 public final int userHandle; 664 public boolean haveResult = false; 665 public Bundle result = null; 666 public AssistStructure structure = null; 667 public AssistContent content = null; 668 public Bundle receiverExtras; 669 670 public PendingAssistExtras(ActivityRecord _activity, Bundle _extras, Intent _intent, 671 String _hint, IResultReceiver _receiver, Bundle _receiverExtras, int _userHandle) { 672 activity = _activity; 673 extras = _extras; 674 intent = _intent; 675 hint = _hint; 676 receiver = _receiver; 677 receiverExtras = _receiverExtras; 678 userHandle = _userHandle; 679 } 680 @Override 681 public void run() { 682 Slog.w(TAG, "getAssistContextExtras failed: timeout retrieving from " + activity); 683 synchronized (this) { 684 haveResult = true; 685 notifyAll(); 686 } 687 pendingAssistExtrasTimedOut(this); 688 } 689 } 690 691 final ArrayList<PendingAssistExtras> mPendingAssistExtras 692 = new ArrayList<PendingAssistExtras>(); 693 694 /** 695 * Process management. 696 */ 697 final ProcessList mProcessList = new ProcessList(); 698 699 /** 700 * All of the applications we currently have running organized by name. 701 * The keys are strings of the application package name (as 702 * returned by the package manager), and the keys are ApplicationRecord 703 * objects. 704 */ 705 final ProcessMap<ProcessRecord> mProcessNames = new ProcessMap<ProcessRecord>(); 706 707 /** 708 * Tracking long-term execution of processes to look for abuse and other 709 * bad app behavior. 710 */ 711 final ProcessStatsService mProcessStats; 712 713 /** 714 * The currently running isolated processes. 715 */ 716 final SparseArray<ProcessRecord> mIsolatedProcesses = new SparseArray<ProcessRecord>(); 717 718 /** 719 * Counter for assigning isolated process uids, to avoid frequently reusing the 720 * same ones. 721 */ 722 int mNextIsolatedProcessUid = 0; 723 724 /** 725 * The currently running heavy-weight process, if any. 726 */ 727 ProcessRecord mHeavyWeightProcess = null; 728 729 /** 730 * All of the processes we currently have running organized by pid. 731 * The keys are the pid running the application. 732 * 733 * <p>NOTE: This object is protected by its own lock, NOT the global 734 * activity manager lock! 735 */ 736 final SparseArray<ProcessRecord> mPidsSelfLocked = new SparseArray<ProcessRecord>(); 737 738 /** 739 * All of the processes that have been forced to be foreground. The key 740 * is the pid of the caller who requested it (we hold a death 741 * link on it). 742 */ 743 abstract class ForegroundToken implements IBinder.DeathRecipient { 744 int pid; 745 IBinder token; 746 } 747 final SparseArray<ForegroundToken> mForegroundProcesses = new SparseArray<ForegroundToken>(); 748 749 /** 750 * List of records for processes that someone had tried to start before the 751 * system was ready. We don't start them at that point, but ensure they 752 * are started by the time booting is complete. 753 */ 754 final ArrayList<ProcessRecord> mProcessesOnHold = new ArrayList<ProcessRecord>(); 755 756 /** 757 * List of persistent applications that are in the process 758 * of being started. 759 */ 760 final ArrayList<ProcessRecord> mPersistentStartingProcesses = new ArrayList<ProcessRecord>(); 761 762 /** 763 * Processes that are being forcibly torn down. 764 */ 765 final ArrayList<ProcessRecord> mRemovedProcesses = new ArrayList<ProcessRecord>(); 766 767 /** 768 * List of running applications, sorted by recent usage. 769 * The first entry in the list is the least recently used. 770 */ 771 final ArrayList<ProcessRecord> mLruProcesses = new ArrayList<ProcessRecord>(); 772 773 /** 774 * Where in mLruProcesses that the processes hosting activities start. 775 */ 776 int mLruProcessActivityStart = 0; 777 778 /** 779 * Where in mLruProcesses that the processes hosting services start. 780 * This is after (lower index) than mLruProcessesActivityStart. 781 */ 782 int mLruProcessServiceStart = 0; 783 784 /** 785 * List of processes that should gc as soon as things are idle. 786 */ 787 final ArrayList<ProcessRecord> mProcessesToGc = new ArrayList<ProcessRecord>(); 788 789 /** 790 * Processes we want to collect PSS data from. 791 */ 792 final ArrayList<ProcessRecord> mPendingPssProcesses = new ArrayList<ProcessRecord>(); 793 794 private boolean mBinderTransactionTrackingEnabled = false; 795 796 /** 797 * Last time we requested PSS data of all processes. 798 */ 799 long mLastFullPssTime = SystemClock.uptimeMillis(); 800 801 /** 802 * If set, the next time we collect PSS data we should do a full collection 803 * with data from native processes and the kernel. 804 */ 805 boolean mFullPssPending = false; 806 807 /** 808 * This is the process holding what we currently consider to be 809 * the "home" activity. 810 */ 811 ProcessRecord mHomeProcess; 812 813 /** 814 * This is the process holding the activity the user last visited that 815 * is in a different process from the one they are currently in. 816 */ 817 ProcessRecord mPreviousProcess; 818 819 /** 820 * The time at which the previous process was last visible. 821 */ 822 long mPreviousProcessVisibleTime; 823 824 /** 825 * Track all uids that have actively running processes. 826 */ 827 final SparseArray<UidRecord> mActiveUids = new SparseArray<>(); 828 829 /** 830 * This is for verifying the UID report flow. 831 */ 832 static final boolean VALIDATE_UID_STATES = true; 833 final SparseArray<UidRecord> mValidateUids = new SparseArray<>(); 834 835 /** 836 * Packages that the user has asked to have run in screen size 837 * compatibility mode instead of filling the screen. 838 */ 839 final CompatModePackages mCompatModePackages; 840 841 /** 842 * Set of IntentSenderRecord objects that are currently active. 843 */ 844 final HashMap<PendingIntentRecord.Key, WeakReference<PendingIntentRecord>> mIntentSenderRecords 845 = new HashMap<PendingIntentRecord.Key, WeakReference<PendingIntentRecord>>(); 846 847 /** 848 * Fingerprints (hashCode()) of stack traces that we've 849 * already logged DropBox entries for. Guarded by itself. If 850 * something (rogue user app) forces this over 851 * MAX_DUP_SUPPRESSED_STACKS entries, the contents are cleared. 852 */ 853 private final HashSet<Integer> mAlreadyLoggedViolatedStacks = new HashSet<Integer>(); 854 private static final int MAX_DUP_SUPPRESSED_STACKS = 5000; 855 856 /** 857 * Strict Mode background batched logging state. 858 * 859 * The string buffer is guarded by itself, and its lock is also 860 * used to determine if another batched write is already 861 * in-flight. 862 */ 863 private final StringBuilder mStrictModeBuffer = new StringBuilder(); 864 865 /** 866 * Keeps track of all IIntentReceivers that have been registered for broadcasts. 867 * Hash keys are the receiver IBinder, hash value is a ReceiverList. 868 */ 869 final HashMap<IBinder, ReceiverList> mRegisteredReceivers = new HashMap<>(); 870 871 /** 872 * Resolver for broadcast intents to registered receivers. 873 * Holds BroadcastFilter (subclass of IntentFilter). 874 */ 875 final IntentResolver<BroadcastFilter, BroadcastFilter> mReceiverResolver 876 = new IntentResolver<BroadcastFilter, BroadcastFilter>() { 877 @Override 878 protected boolean allowFilterResult( 879 BroadcastFilter filter, List<BroadcastFilter> dest) { 880 IBinder target = filter.receiverList.receiver.asBinder(); 881 for (int i = dest.size() - 1; i >= 0; i--) { 882 if (dest.get(i).receiverList.receiver.asBinder() == target) { 883 return false; 884 } 885 } 886 return true; 887 } 888 889 @Override 890 protected BroadcastFilter newResult(BroadcastFilter filter, int match, int userId) { 891 if (userId == UserHandle.USER_ALL || filter.owningUserId == UserHandle.USER_ALL 892 || userId == filter.owningUserId) { 893 return super.newResult(filter, match, userId); 894 } 895 return null; 896 } 897 898 @Override 899 protected BroadcastFilter[] newArray(int size) { 900 return new BroadcastFilter[size]; 901 } 902 903 @Override 904 protected boolean isPackageForFilter(String packageName, BroadcastFilter filter) { 905 return packageName.equals(filter.packageName); 906 } 907 }; 908 909 /** 910 * State of all active sticky broadcasts per user. Keys are the action of the 911 * sticky Intent, values are an ArrayList of all broadcasted intents with 912 * that action (which should usually be one). The SparseArray is keyed 913 * by the user ID the sticky is for, and can include UserHandle.USER_ALL 914 * for stickies that are sent to all users. 915 */ 916 final SparseArray<ArrayMap<String, ArrayList<Intent>>> mStickyBroadcasts = 917 new SparseArray<ArrayMap<String, ArrayList<Intent>>>(); 918 919 final ActiveServices mServices; 920 921 final static class Association { 922 final int mSourceUid; 923 final String mSourceProcess; 924 final int mTargetUid; 925 final ComponentName mTargetComponent; 926 final String mTargetProcess; 927 928 int mCount; 929 long mTime; 930 931 int mNesting; 932 long mStartTime; 933 934 // states of the source process when the bind occurred. 935 int mLastState = ActivityManager.MAX_PROCESS_STATE + 1; 936 long mLastStateUptime; 937 long[] mStateTimes = new long[ActivityManager.MAX_PROCESS_STATE 938 - ActivityManager.MIN_PROCESS_STATE+1]; 939 940 Association(int sourceUid, String sourceProcess, int targetUid, 941 ComponentName targetComponent, String targetProcess) { 942 mSourceUid = sourceUid; 943 mSourceProcess = sourceProcess; 944 mTargetUid = targetUid; 945 mTargetComponent = targetComponent; 946 mTargetProcess = targetProcess; 947 } 948 } 949 950 /** 951 * When service association tracking is enabled, this is all of the associations we 952 * have seen. Mapping is target uid -> target component -> source uid -> source process name 953 * -> association data. 954 */ 955 final SparseArray<ArrayMap<ComponentName, SparseArray<ArrayMap<String, Association>>>> 956 mAssociations = new SparseArray<>(); 957 boolean mTrackingAssociations; 958 959 /** 960 * Backup/restore process management 961 */ 962 String mBackupAppName = null; 963 BackupRecord mBackupTarget = null; 964 965 final ProviderMap mProviderMap; 966 967 /** 968 * List of content providers who have clients waiting for them. The 969 * application is currently being launched and the provider will be 970 * removed from this list once it is published. 971 */ 972 final ArrayList<ContentProviderRecord> mLaunchingProviders 973 = new ArrayList<ContentProviderRecord>(); 974 975 /** 976 * File storing persisted {@link #mGrantedUriPermissions}. 977 */ 978 private final AtomicFile mGrantFile; 979 980 /** XML constants used in {@link #mGrantFile} */ 981 private static final String TAG_URI_GRANTS = "uri-grants"; 982 private static final String TAG_URI_GRANT = "uri-grant"; 983 private static final String ATTR_USER_HANDLE = "userHandle"; 984 private static final String ATTR_SOURCE_USER_ID = "sourceUserId"; 985 private static final String ATTR_TARGET_USER_ID = "targetUserId"; 986 private static final String ATTR_SOURCE_PKG = "sourcePkg"; 987 private static final String ATTR_TARGET_PKG = "targetPkg"; 988 private static final String ATTR_URI = "uri"; 989 private static final String ATTR_MODE_FLAGS = "modeFlags"; 990 private static final String ATTR_CREATED_TIME = "createdTime"; 991 private static final String ATTR_PREFIX = "prefix"; 992 993 /** 994 * Global set of specific {@link Uri} permissions that have been granted. 995 * This optimized lookup structure maps from {@link UriPermission#targetUid} 996 * to {@link UriPermission#uri} to {@link UriPermission}. 997 */ 998 @GuardedBy("this") 999 private final SparseArray<ArrayMap<GrantUri, UriPermission>> 1000 mGrantedUriPermissions = new SparseArray<ArrayMap<GrantUri, UriPermission>>(); 1001 1002 public static class GrantUri { 1003 public final int sourceUserId; 1004 public final Uri uri; 1005 public boolean prefix; 1006 1007 public GrantUri(int sourceUserId, Uri uri, boolean prefix) { 1008 this.sourceUserId = sourceUserId; 1009 this.uri = uri; 1010 this.prefix = prefix; 1011 } 1012 1013 @Override 1014 public int hashCode() { 1015 int hashCode = 1; 1016 hashCode = 31 * hashCode + sourceUserId; 1017 hashCode = 31 * hashCode + uri.hashCode(); 1018 hashCode = 31 * hashCode + (prefix ? 1231 : 1237); 1019 return hashCode; 1020 } 1021 1022 @Override 1023 public boolean equals(Object o) { 1024 if (o instanceof GrantUri) { 1025 GrantUri other = (GrantUri) o; 1026 return uri.equals(other.uri) && (sourceUserId == other.sourceUserId) 1027 && prefix == other.prefix; 1028 } 1029 return false; 1030 } 1031 1032 @Override 1033 public String toString() { 1034 String result = Integer.toString(sourceUserId) + " @ " + uri.toString(); 1035 if (prefix) result += " [prefix]"; 1036 return result; 1037 } 1038 1039 public String toSafeString() { 1040 String result = Integer.toString(sourceUserId) + " @ " + uri.toSafeString(); 1041 if (prefix) result += " [prefix]"; 1042 return result; 1043 } 1044 1045 public static GrantUri resolve(int defaultSourceUserHandle, Uri uri) { 1046 return new GrantUri(ContentProvider.getUserIdFromUri(uri, defaultSourceUserHandle), 1047 ContentProvider.getUriWithoutUserId(uri), false); 1048 } 1049 } 1050 1051 CoreSettingsObserver mCoreSettingsObserver; 1052 1053 FontScaleSettingObserver mFontScaleSettingObserver; 1054 1055 private final class FontScaleSettingObserver extends ContentObserver { 1056 private final Uri mFontScaleUri = Settings.System.getUriFor(FONT_SCALE); 1057 1058 public FontScaleSettingObserver() { 1059 super(mHandler); 1060 ContentResolver resolver = mContext.getContentResolver(); 1061 resolver.registerContentObserver(mFontScaleUri, false, this, UserHandle.USER_ALL); 1062 } 1063 1064 @Override 1065 public void onChange(boolean selfChange, Uri uri) { 1066 if (mFontScaleUri.equals(uri)) { 1067 updateFontScaleIfNeeded(); 1068 } 1069 } 1070 } 1071 1072 /** 1073 * Thread-local storage used to carry caller permissions over through 1074 * indirect content-provider access. 1075 */ 1076 private class Identity { 1077 public final IBinder token; 1078 public final int pid; 1079 public final int uid; 1080 1081 Identity(IBinder _token, int _pid, int _uid) { 1082 token = _token; 1083 pid = _pid; 1084 uid = _uid; 1085 } 1086 } 1087 1088 private static final ThreadLocal<Identity> sCallerIdentity = new ThreadLocal<Identity>(); 1089 1090 /** 1091 * All information we have collected about the runtime performance of 1092 * any user id that can impact battery performance. 1093 */ 1094 final BatteryStatsService mBatteryStatsService; 1095 1096 /** 1097 * Information about component usage 1098 */ 1099 UsageStatsManagerInternal mUsageStatsService; 1100 1101 /** 1102 * Access to DeviceIdleController service. 1103 */ 1104 DeviceIdleController.LocalService mLocalDeviceIdleController; 1105 1106 /** 1107 * Information about and control over application operations 1108 */ 1109 final AppOpsService mAppOpsService; 1110 1111 /** 1112 * Current configuration information. HistoryRecord objects are given 1113 * a reference to this object to indicate which configuration they are 1114 * currently running in, so this object must be kept immutable. 1115 */ 1116 Configuration mConfiguration = new Configuration(); 1117 1118 /** 1119 * Current sequencing integer of the configuration, for skipping old 1120 * configurations. 1121 */ 1122 int mConfigurationSeq = 0; 1123 1124 boolean mSuppressResizeConfigChanges = false; 1125 1126 /** 1127 * Hardware-reported OpenGLES version. 1128 */ 1129 final int GL_ES_VERSION; 1130 1131 /** 1132 * List of initialization arguments to pass to all processes when binding applications to them. 1133 * For example, references to the commonly used services. 1134 */ 1135 HashMap<String, IBinder> mAppBindArgs; 1136 1137 /** 1138 * Temporary to avoid allocations. Protected by main lock. 1139 */ 1140 final StringBuilder mStringBuilder = new StringBuilder(256); 1141 1142 /** 1143 * Used to control how we initialize the service. 1144 */ 1145 ComponentName mTopComponent; 1146 String mTopAction = Intent.ACTION_MAIN; 1147 String mTopData; 1148 1149 volatile boolean mProcessesReady = false; 1150 volatile boolean mSystemReady = false; 1151 volatile boolean mOnBattery = false; 1152 volatile int mFactoryTest; 1153 1154 @GuardedBy("this") boolean mBooting = false; 1155 @GuardedBy("this") boolean mCallFinishBooting = false; 1156 @GuardedBy("this") boolean mBootAnimationComplete = false; 1157 @GuardedBy("this") boolean mLaunchWarningShown = false; 1158 @GuardedBy("this") boolean mCheckedForSetup = false; 1159 1160 Context mContext; 1161 1162 /** 1163 * The time at which we will allow normal application switches again, 1164 * after a call to {@link #stopAppSwitches()}. 1165 */ 1166 long mAppSwitchesAllowedTime; 1167 1168 /** 1169 * This is set to true after the first switch after mAppSwitchesAllowedTime 1170 * is set; any switches after that will clear the time. 1171 */ 1172 boolean mDidAppSwitch; 1173 1174 /** 1175 * Last time (in realtime) at which we checked for power usage. 1176 */ 1177 long mLastPowerCheckRealtime; 1178 1179 /** 1180 * Last time (in uptime) at which we checked for power usage. 1181 */ 1182 long mLastPowerCheckUptime; 1183 1184 /** 1185 * Set while we are wanting to sleep, to prevent any 1186 * activities from being started/resumed. 1187 */ 1188 private boolean mSleeping = false; 1189 1190 /** 1191 * The process state used for processes that are running the top activities. 1192 * This changes between TOP and TOP_SLEEPING to following mSleeping. 1193 */ 1194 int mTopProcessState = ActivityManager.PROCESS_STATE_TOP; 1195 1196 /** 1197 * Set while we are running a voice interaction. This overrides 1198 * sleeping while it is active. 1199 */ 1200 private IVoiceInteractionSession mRunningVoice; 1201 1202 /** 1203 * For some direct access we need to power manager. 1204 */ 1205 PowerManagerInternal mLocalPowerManager; 1206 1207 /** 1208 * We want to hold a wake lock while running a voice interaction session, since 1209 * this may happen with the screen off and we need to keep the CPU running to 1210 * be able to continue to interact with the user. 1211 */ 1212 PowerManager.WakeLock mVoiceWakeLock; 1213 1214 /** 1215 * State of external calls telling us if the device is awake or asleep. 1216 */ 1217 private int mWakefulness = PowerManagerInternal.WAKEFULNESS_AWAKE; 1218 1219 /** 1220 * A list of tokens that cause the top activity to be put to sleep. 1221 * They are used by components that may hide and block interaction with underlying 1222 * activities. 1223 */ 1224 final ArrayList<SleepToken> mSleepTokens = new ArrayList<SleepToken>(); 1225 1226 static final int LOCK_SCREEN_HIDDEN = 0; 1227 static final int LOCK_SCREEN_LEAVING = 1; 1228 static final int LOCK_SCREEN_SHOWN = 2; 1229 /** 1230 * State of external call telling us if the lock screen is shown. 1231 */ 1232 int mLockScreenShown = LOCK_SCREEN_HIDDEN; 1233 1234 /** 1235 * Set if we are shutting down the system, similar to sleeping. 1236 */ 1237 boolean mShuttingDown = false; 1238 1239 /** 1240 * Current sequence id for oom_adj computation traversal. 1241 */ 1242 int mAdjSeq = 0; 1243 1244 /** 1245 * Current sequence id for process LRU updating. 1246 */ 1247 int mLruSeq = 0; 1248 1249 /** 1250 * Keep track of the non-cached/empty process we last found, to help 1251 * determine how to distribute cached/empty processes next time. 1252 */ 1253 int mNumNonCachedProcs = 0; 1254 1255 /** 1256 * Keep track of the number of cached hidden procs, to balance oom adj 1257 * distribution between those and empty procs. 1258 */ 1259 int mNumCachedHiddenProcs = 0; 1260 1261 /** 1262 * Keep track of the number of service processes we last found, to 1263 * determine on the next iteration which should be B services. 1264 */ 1265 int mNumServiceProcs = 0; 1266 int mNewNumAServiceProcs = 0; 1267 int mNewNumServiceProcs = 0; 1268 1269 /** 1270 * Allow the current computed overall memory level of the system to go down? 1271 * This is set to false when we are killing processes for reasons other than 1272 * memory management, so that the now smaller process list will not be taken as 1273 * an indication that memory is tighter. 1274 */ 1275 boolean mAllowLowerMemLevel = false; 1276 1277 /** 1278 * The last computed memory level, for holding when we are in a state that 1279 * processes are going away for other reasons. 1280 */ 1281 int mLastMemoryLevel = ProcessStats.ADJ_MEM_FACTOR_NORMAL; 1282 1283 /** 1284 * The last total number of process we have, to determine if changes actually look 1285 * like a shrinking number of process due to lower RAM. 1286 */ 1287 int mLastNumProcesses; 1288 1289 /** 1290 * The uptime of the last time we performed idle maintenance. 1291 */ 1292 long mLastIdleTime = SystemClock.uptimeMillis(); 1293 1294 /** 1295 * Total time spent with RAM that has been added in the past since the last idle time. 1296 */ 1297 long mLowRamTimeSinceLastIdle = 0; 1298 1299 /** 1300 * If RAM is currently low, when that horrible situation started. 1301 */ 1302 long mLowRamStartTime = 0; 1303 1304 /** 1305 * For reporting to battery stats the current top application. 1306 */ 1307 private String mCurResumedPackage = null; 1308 private int mCurResumedUid = -1; 1309 1310 /** 1311 * For reporting to battery stats the apps currently running foreground 1312 * service. The ProcessMap is package/uid tuples; each of these contain 1313 * an array of the currently foreground processes. 1314 */ 1315 final ProcessMap<ArrayList<ProcessRecord>> mForegroundPackages 1316 = new ProcessMap<ArrayList<ProcessRecord>>(); 1317 1318 /** 1319 * This is set if we had to do a delayed dexopt of an app before launching 1320 * it, to increase the ANR timeouts in that case. 1321 */ 1322 boolean mDidDexOpt; 1323 1324 /** 1325 * Set if the systemServer made a call to enterSafeMode. 1326 */ 1327 boolean mSafeMode; 1328 1329 /** 1330 * If true, we are running under a test environment so will sample PSS from processes 1331 * much more rapidly to try to collect better data when the tests are rapidly 1332 * running through apps. 1333 */ 1334 boolean mTestPssMode = false; 1335 1336 String mDebugApp = null; 1337 boolean mWaitForDebugger = false; 1338 boolean mDebugTransient = false; 1339 String mOrigDebugApp = null; 1340 boolean mOrigWaitForDebugger = false; 1341 boolean mAlwaysFinishActivities = false; 1342 boolean mLenientBackgroundCheck = false; 1343 boolean mForceResizableActivities; 1344 boolean mSupportsMultiWindow; 1345 boolean mSupportsFreeformWindowManagement; 1346 boolean mSupportsPictureInPicture; 1347 Rect mDefaultPinnedStackBounds; 1348 IActivityController mController = null; 1349 boolean mControllerIsAMonkey = false; 1350 String mProfileApp = null; 1351 ProcessRecord mProfileProc = null; 1352 String mProfileFile; 1353 ParcelFileDescriptor mProfileFd; 1354 int mSamplingInterval = 0; 1355 boolean mAutoStopProfiler = false; 1356 int mProfileType = 0; 1357 final ProcessMap<Pair<Long, String>> mMemWatchProcesses = new ProcessMap<>(); 1358 String mMemWatchDumpProcName; 1359 String mMemWatchDumpFile; 1360 int mMemWatchDumpPid; 1361 int mMemWatchDumpUid; 1362 String mTrackAllocationApp = null; 1363 String mNativeDebuggingApp = null; 1364 1365 final long[] mTmpLong = new long[2]; 1366 1367 static final class ProcessChangeItem { 1368 static final int CHANGE_ACTIVITIES = 1<<0; 1369 static final int CHANGE_PROCESS_STATE = 1<<1; 1370 int changes; 1371 int uid; 1372 int pid; 1373 int processState; 1374 boolean foregroundActivities; 1375 } 1376 1377 final RemoteCallbackList<IProcessObserver> mProcessObservers = new RemoteCallbackList<>(); 1378 ProcessChangeItem[] mActiveProcessChanges = new ProcessChangeItem[5]; 1379 1380 final ArrayList<ProcessChangeItem> mPendingProcessChanges = new ArrayList<>(); 1381 final ArrayList<ProcessChangeItem> mAvailProcessChanges = new ArrayList<>(); 1382 1383 final RemoteCallbackList<IUidObserver> mUidObservers = new RemoteCallbackList<>(); 1384 UidRecord.ChangeItem[] mActiveUidChanges = new UidRecord.ChangeItem[5]; 1385 1386 final ArrayList<UidRecord.ChangeItem> mPendingUidChanges = new ArrayList<>(); 1387 final ArrayList<UidRecord.ChangeItem> mAvailUidChanges = new ArrayList<>(); 1388 1389 /** 1390 * Runtime CPU use collection thread. This object's lock is used to 1391 * perform synchronization with the thread (notifying it to run). 1392 */ 1393 final Thread mProcessCpuThread; 1394 1395 /** 1396 * Used to collect per-process CPU use for ANRs, battery stats, etc. 1397 * Must acquire this object's lock when accessing it. 1398 * NOTE: this lock will be held while doing long operations (trawling 1399 * through all processes in /proc), so it should never be acquired by 1400 * any critical paths such as when holding the main activity manager lock. 1401 */ 1402 final ProcessCpuTracker mProcessCpuTracker = new ProcessCpuTracker( 1403 MONITOR_THREAD_CPU_USAGE); 1404 final AtomicLong mLastCpuTime = new AtomicLong(0); 1405 final AtomicBoolean mProcessCpuMutexFree = new AtomicBoolean(true); 1406 1407 long mLastWriteTime = 0; 1408 1409 /** 1410 * Used to retain an update lock when the foreground activity is in 1411 * immersive mode. 1412 */ 1413 final UpdateLock mUpdateLock = new UpdateLock("immersive"); 1414 1415 /** 1416 * Set to true after the system has finished booting. 1417 */ 1418 boolean mBooted = false; 1419 1420 int mProcessLimit = ProcessList.MAX_CACHED_APPS; 1421 int mProcessLimitOverride = -1; 1422 1423 WindowManagerService mWindowManager; 1424 final ActivityThread mSystemThread; 1425 1426 private final class AppDeathRecipient implements IBinder.DeathRecipient { 1427 final ProcessRecord mApp; 1428 final int mPid; 1429 final IApplicationThread mAppThread; 1430 1431 AppDeathRecipient(ProcessRecord app, int pid, 1432 IApplicationThread thread) { 1433 if (DEBUG_ALL) Slog.v( 1434 TAG, "New death recipient " + this 1435 + " for thread " + thread.asBinder()); 1436 mApp = app; 1437 mPid = pid; 1438 mAppThread = thread; 1439 } 1440 1441 @Override 1442 public void binderDied() { 1443 if (DEBUG_ALL) Slog.v( 1444 TAG, "Death received in " + this 1445 + " for thread " + mAppThread.asBinder()); 1446 synchronized(ActivityManagerService.this) { 1447 appDiedLocked(mApp, mPid, mAppThread, true); 1448 } 1449 } 1450 } 1451 1452 static final int SHOW_ERROR_UI_MSG = 1; 1453 static final int SHOW_NOT_RESPONDING_UI_MSG = 2; 1454 static final int SHOW_FACTORY_ERROR_UI_MSG = 3; 1455 static final int UPDATE_CONFIGURATION_MSG = 4; 1456 static final int GC_BACKGROUND_PROCESSES_MSG = 5; 1457 static final int WAIT_FOR_DEBUGGER_UI_MSG = 6; 1458 static final int SERVICE_TIMEOUT_MSG = 12; 1459 static final int UPDATE_TIME_ZONE = 13; 1460 static final int SHOW_UID_ERROR_UI_MSG = 14; 1461 static final int SHOW_FINGERPRINT_ERROR_UI_MSG = 15; 1462 static final int PROC_START_TIMEOUT_MSG = 20; 1463 static final int DO_PENDING_ACTIVITY_LAUNCHES_MSG = 21; 1464 static final int KILL_APPLICATION_MSG = 22; 1465 static final int FINALIZE_PENDING_INTENT_MSG = 23; 1466 static final int POST_HEAVY_NOTIFICATION_MSG = 24; 1467 static final int CANCEL_HEAVY_NOTIFICATION_MSG = 25; 1468 static final int SHOW_STRICT_MODE_VIOLATION_UI_MSG = 26; 1469 static final int CHECK_EXCESSIVE_WAKE_LOCKS_MSG = 27; 1470 static final int CLEAR_DNS_CACHE_MSG = 28; 1471 static final int UPDATE_HTTP_PROXY_MSG = 29; 1472 static final int SHOW_COMPAT_MODE_DIALOG_UI_MSG = 30; 1473 static final int DISPATCH_PROCESSES_CHANGED_UI_MSG = 31; 1474 static final int DISPATCH_PROCESS_DIED_UI_MSG = 32; 1475 static final int REPORT_MEM_USAGE_MSG = 33; 1476 static final int REPORT_USER_SWITCH_MSG = 34; 1477 static final int CONTINUE_USER_SWITCH_MSG = 35; 1478 static final int USER_SWITCH_TIMEOUT_MSG = 36; 1479 static final int IMMERSIVE_MODE_LOCK_MSG = 37; 1480 static final int PERSIST_URI_GRANTS_MSG = 38; 1481 static final int REQUEST_ALL_PSS_MSG = 39; 1482 static final int START_PROFILES_MSG = 40; 1483 static final int UPDATE_TIME = 41; 1484 static final int SYSTEM_USER_START_MSG = 42; 1485 static final int SYSTEM_USER_CURRENT_MSG = 43; 1486 static final int ENTER_ANIMATION_COMPLETE_MSG = 44; 1487 static final int FINISH_BOOTING_MSG = 45; 1488 static final int START_USER_SWITCH_UI_MSG = 46; 1489 static final int SEND_LOCALE_TO_MOUNT_DAEMON_MSG = 47; 1490 static final int DISMISS_DIALOG_UI_MSG = 48; 1491 static final int NOTIFY_TASK_STACK_CHANGE_LISTENERS_MSG = 49; 1492 static final int NOTIFY_CLEARTEXT_NETWORK_MSG = 50; 1493 static final int POST_DUMP_HEAP_NOTIFICATION_MSG = 51; 1494 static final int DELETE_DUMPHEAP_MSG = 52; 1495 static final int FOREGROUND_PROFILE_CHANGED_MSG = 53; 1496 static final int DISPATCH_UIDS_CHANGED_UI_MSG = 54; 1497 static final int REPORT_TIME_TRACKER_MSG = 55; 1498 static final int REPORT_USER_SWITCH_COMPLETE_MSG = 56; 1499 static final int SHUTDOWN_UI_AUTOMATION_CONNECTION_MSG = 57; 1500 static final int APP_BOOST_DEACTIVATE_MSG = 58; 1501 static final int CONTENT_PROVIDER_PUBLISH_TIMEOUT_MSG = 59; 1502 static final int IDLE_UIDS_MSG = 60; 1503 static final int SYSTEM_USER_UNLOCK_MSG = 61; 1504 static final int LOG_STACK_STATE = 62; 1505 static final int VR_MODE_CHANGE_MSG = 63; 1506 static final int NOTIFY_ACTIVITY_PINNED_LISTENERS_MSG = 64; 1507 static final int NOTIFY_PINNED_ACTIVITY_RESTART_ATTEMPT_LISTENERS_MSG = 65; 1508 static final int NOTIFY_PINNED_STACK_ANIMATION_ENDED_LISTENERS_MSG = 66; 1509 static final int NOTIFY_FORCED_RESIZABLE_MSG = 67; 1510 static final int NOTIFY_ACTIVITY_DISMISSING_DOCKED_STACK_MSG = 68; 1511 static final int VR_MODE_APPLY_IF_NEEDED_MSG = 69; 1512 1513 static final int FIRST_ACTIVITY_STACK_MSG = 100; 1514 static final int FIRST_BROADCAST_QUEUE_MSG = 200; 1515 static final int FIRST_COMPAT_MODE_MSG = 300; 1516 static final int FIRST_SUPERVISOR_STACK_MSG = 100; 1517 1518 static ServiceThread sKillThread = null; 1519 static KillHandler sKillHandler = null; 1520 1521 CompatModeDialog mCompatModeDialog; 1522 long mLastMemUsageReportTime = 0; 1523 1524 /** 1525 * Flag whether the current user is a "monkey", i.e. whether 1526 * the UI is driven by a UI automation tool. 1527 */ 1528 private boolean mUserIsMonkey; 1529 1530 /** Flag whether the device has a Recents UI */ 1531 boolean mHasRecents; 1532 1533 /** The dimensions of the thumbnails in the Recents UI. */ 1534 int mThumbnailWidth; 1535 int mThumbnailHeight; 1536 float mFullscreenThumbnailScale; 1537 1538 final ServiceThread mHandlerThread; 1539 final MainHandler mHandler; 1540 final UiHandler mUiHandler; 1541 1542 PackageManagerInternal mPackageManagerInt; 1543 1544 // VoiceInteraction session ID that changes for each new request except when 1545 // being called for multiwindow assist in a single session. 1546 private int mViSessionId = 1000; 1547 1548 final class KillHandler extends Handler { 1549 static final int KILL_PROCESS_GROUP_MSG = 4000; 1550 1551 public KillHandler(Looper looper) { 1552 super(looper, null, true); 1553 } 1554 1555 @Override 1556 public void handleMessage(Message msg) { 1557 switch (msg.what) { 1558 case KILL_PROCESS_GROUP_MSG: 1559 { 1560 Trace.traceBegin(Trace.TRACE_TAG_ACTIVITY_MANAGER, "killProcessGroup"); 1561 Process.killProcessGroup(msg.arg1 /* uid */, msg.arg2 /* pid */); 1562 Trace.traceEnd(Trace.TRACE_TAG_ACTIVITY_MANAGER); 1563 } 1564 break; 1565 1566 default: 1567 super.handleMessage(msg); 1568 } 1569 } 1570 } 1571 1572 final class UiHandler extends Handler { 1573 public UiHandler() { 1574 super(com.android.server.UiThread.get().getLooper(), null, true); 1575 } 1576 1577 @Override 1578 public void handleMessage(Message msg) { 1579 switch (msg.what) { 1580 case SHOW_ERROR_UI_MSG: { 1581 mAppErrors.handleShowAppErrorUi(msg); 1582 ensureBootCompleted(); 1583 } break; 1584 case SHOW_NOT_RESPONDING_UI_MSG: { 1585 mAppErrors.handleShowAnrUi(msg); 1586 ensureBootCompleted(); 1587 } break; 1588 case SHOW_STRICT_MODE_VIOLATION_UI_MSG: { 1589 HashMap<String, Object> data = (HashMap<String, Object>) msg.obj; 1590 synchronized (ActivityManagerService.this) { 1591 ProcessRecord proc = (ProcessRecord) data.get("app"); 1592 if (proc == null) { 1593 Slog.e(TAG, "App not found when showing strict mode dialog."); 1594 break; 1595 } 1596 if (proc.crashDialog != null) { 1597 Slog.e(TAG, "App already has strict mode dialog: " + proc); 1598 return; 1599 } 1600 AppErrorResult res = (AppErrorResult) data.get("result"); 1601 if (mShowDialogs && !mSleeping && !mShuttingDown) { 1602 Dialog d = new StrictModeViolationDialog(mContext, 1603 ActivityManagerService.this, res, proc); 1604 d.show(); 1605 proc.crashDialog = d; 1606 } else { 1607 // The device is asleep, so just pretend that the user 1608 // saw a crash dialog and hit "force quit". 1609 res.set(0); 1610 } 1611 } 1612 ensureBootCompleted(); 1613 } break; 1614 case SHOW_FACTORY_ERROR_UI_MSG: { 1615 Dialog d = new FactoryErrorDialog( 1616 mContext, msg.getData().getCharSequence("msg")); 1617 d.show(); 1618 ensureBootCompleted(); 1619 } break; 1620 case WAIT_FOR_DEBUGGER_UI_MSG: { 1621 synchronized (ActivityManagerService.this) { 1622 ProcessRecord app = (ProcessRecord)msg.obj; 1623 if (msg.arg1 != 0) { 1624 if (!app.waitedForDebugger) { 1625 Dialog d = new AppWaitingForDebuggerDialog( 1626 ActivityManagerService.this, 1627 mContext, app); 1628 app.waitDialog = d; 1629 app.waitedForDebugger = true; 1630 d.show(); 1631 } 1632 } else { 1633 if (app.waitDialog != null) { 1634 app.waitDialog.dismiss(); 1635 app.waitDialog = null; 1636 } 1637 } 1638 } 1639 } break; 1640 case SHOW_UID_ERROR_UI_MSG: { 1641 if (mShowDialogs) { 1642 AlertDialog d = new BaseErrorDialog(mContext); 1643 d.getWindow().setType(WindowManager.LayoutParams.TYPE_SYSTEM_ERROR); 1644 d.setCancelable(false); 1645 d.setTitle(mContext.getText(R.string.android_system_label)); 1646 d.setMessage(mContext.getText(R.string.system_error_wipe_data)); 1647 d.setButton(DialogInterface.BUTTON_POSITIVE, mContext.getText(R.string.ok), 1648 obtainMessage(DISMISS_DIALOG_UI_MSG, d)); 1649 d.show(); 1650 } 1651 } break; 1652 case SHOW_FINGERPRINT_ERROR_UI_MSG: { 1653 if (mShowDialogs) { 1654 AlertDialog d = new BaseErrorDialog(mContext); 1655 d.getWindow().setType(WindowManager.LayoutParams.TYPE_SYSTEM_ERROR); 1656 d.setCancelable(false); 1657 d.setTitle(mContext.getText(R.string.android_system_label)); 1658 d.setMessage(mContext.getText(R.string.system_error_manufacturer)); 1659 d.setButton(DialogInterface.BUTTON_POSITIVE, mContext.getText(R.string.ok), 1660 obtainMessage(DISMISS_DIALOG_UI_MSG, d)); 1661 d.show(); 1662 } 1663 } break; 1664 case SHOW_COMPAT_MODE_DIALOG_UI_MSG: { 1665 synchronized (ActivityManagerService.this) { 1666 ActivityRecord ar = (ActivityRecord) msg.obj; 1667 if (mCompatModeDialog != null) { 1668 if (mCompatModeDialog.mAppInfo.packageName.equals( 1669 ar.info.applicationInfo.packageName)) { 1670 return; 1671 } 1672 mCompatModeDialog.dismiss(); 1673 mCompatModeDialog = null; 1674 } 1675 if (ar != null && false) { 1676 if (mCompatModePackages.getPackageAskCompatModeLocked( 1677 ar.packageName)) { 1678 int mode = mCompatModePackages.computeCompatModeLocked( 1679 ar.info.applicationInfo); 1680 if (mode == ActivityManager.COMPAT_MODE_DISABLED 1681 || mode == ActivityManager.COMPAT_MODE_ENABLED) { 1682 mCompatModeDialog = new CompatModeDialog( 1683 ActivityManagerService.this, mContext, 1684 ar.info.applicationInfo); 1685 mCompatModeDialog.show(); 1686 } 1687 } 1688 } 1689 } 1690 break; 1691 } 1692 case START_USER_SWITCH_UI_MSG: { 1693 mUserController.showUserSwitchDialog((Pair<UserInfo, UserInfo>) msg.obj); 1694 break; 1695 } 1696 case DISMISS_DIALOG_UI_MSG: { 1697 final Dialog d = (Dialog) msg.obj; 1698 d.dismiss(); 1699 break; 1700 } 1701 case DISPATCH_PROCESSES_CHANGED_UI_MSG: { 1702 dispatchProcessesChanged(); 1703 break; 1704 } 1705 case DISPATCH_PROCESS_DIED_UI_MSG: { 1706 final int pid = msg.arg1; 1707 final int uid = msg.arg2; 1708 dispatchProcessDied(pid, uid); 1709 break; 1710 } 1711 case DISPATCH_UIDS_CHANGED_UI_MSG: { 1712 dispatchUidsChanged(); 1713 } break; 1714 } 1715 } 1716 } 1717 1718 final class MainHandler extends Handler { 1719 public MainHandler(Looper looper) { 1720 super(looper, null, true); 1721 } 1722 1723 @Override 1724 public void handleMessage(Message msg) { 1725 switch (msg.what) { 1726 case UPDATE_CONFIGURATION_MSG: { 1727 final ContentResolver resolver = mContext.getContentResolver(); 1728 Settings.System.putConfigurationForUser(resolver, (Configuration) msg.obj, 1729 msg.arg1); 1730 } break; 1731 case GC_BACKGROUND_PROCESSES_MSG: { 1732 synchronized (ActivityManagerService.this) { 1733 performAppGcsIfAppropriateLocked(); 1734 } 1735 } break; 1736 case SERVICE_TIMEOUT_MSG: { 1737 if (mDidDexOpt) { 1738 mDidDexOpt = false; 1739 Message nmsg = mHandler.obtainMessage(SERVICE_TIMEOUT_MSG); 1740 nmsg.obj = msg.obj; 1741 mHandler.sendMessageDelayed(nmsg, ActiveServices.SERVICE_TIMEOUT); 1742 return; 1743 } 1744 mServices.serviceTimeout((ProcessRecord)msg.obj); 1745 } break; 1746 case UPDATE_TIME_ZONE: { 1747 synchronized (ActivityManagerService.this) { 1748 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 1749 ProcessRecord r = mLruProcesses.get(i); 1750 if (r.thread != null) { 1751 try { 1752 r.thread.updateTimeZone(); 1753 } catch (RemoteException ex) { 1754 Slog.w(TAG, "Failed to update time zone for: " + r.info.processName); 1755 } 1756 } 1757 } 1758 } 1759 } break; 1760 case CLEAR_DNS_CACHE_MSG: { 1761 synchronized (ActivityManagerService.this) { 1762 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 1763 ProcessRecord r = mLruProcesses.get(i); 1764 if (r.thread != null) { 1765 try { 1766 r.thread.clearDnsCache(); 1767 } catch (RemoteException ex) { 1768 Slog.w(TAG, "Failed to clear dns cache for: " + r.info.processName); 1769 } 1770 } 1771 } 1772 } 1773 } break; 1774 case UPDATE_HTTP_PROXY_MSG: { 1775 ProxyInfo proxy = (ProxyInfo)msg.obj; 1776 String host = ""; 1777 String port = ""; 1778 String exclList = ""; 1779 Uri pacFileUrl = Uri.EMPTY; 1780 if (proxy != null) { 1781 host = proxy.getHost(); 1782 port = Integer.toString(proxy.getPort()); 1783 exclList = proxy.getExclusionListAsString(); 1784 pacFileUrl = proxy.getPacFileUrl(); 1785 } 1786 synchronized (ActivityManagerService.this) { 1787 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 1788 ProcessRecord r = mLruProcesses.get(i); 1789 if (r.thread != null) { 1790 try { 1791 r.thread.setHttpProxy(host, port, exclList, pacFileUrl); 1792 } catch (RemoteException ex) { 1793 Slog.w(TAG, "Failed to update http proxy for: " + 1794 r.info.processName); 1795 } 1796 } 1797 } 1798 } 1799 } break; 1800 case PROC_START_TIMEOUT_MSG: { 1801 if (mDidDexOpt) { 1802 mDidDexOpt = false; 1803 Message nmsg = mHandler.obtainMessage(PROC_START_TIMEOUT_MSG); 1804 nmsg.obj = msg.obj; 1805 mHandler.sendMessageDelayed(nmsg, PROC_START_TIMEOUT); 1806 return; 1807 } 1808 ProcessRecord app = (ProcessRecord)msg.obj; 1809 synchronized (ActivityManagerService.this) { 1810 processStartTimedOutLocked(app); 1811 } 1812 } break; 1813 case CONTENT_PROVIDER_PUBLISH_TIMEOUT_MSG: { 1814 ProcessRecord app = (ProcessRecord)msg.obj; 1815 synchronized (ActivityManagerService.this) { 1816 processContentProviderPublishTimedOutLocked(app); 1817 } 1818 } break; 1819 case DO_PENDING_ACTIVITY_LAUNCHES_MSG: { 1820 synchronized (ActivityManagerService.this) { 1821 mActivityStarter.doPendingActivityLaunchesLocked(true); 1822 } 1823 } break; 1824 case KILL_APPLICATION_MSG: { 1825 synchronized (ActivityManagerService.this) { 1826 int appid = msg.arg1; 1827 boolean restart = (msg.arg2 == 1); 1828 Bundle bundle = (Bundle)msg.obj; 1829 String pkg = bundle.getString("pkg"); 1830 String reason = bundle.getString("reason"); 1831 forceStopPackageLocked(pkg, appid, restart, false, true, false, 1832 false, UserHandle.USER_ALL, reason); 1833 } 1834 } break; 1835 case FINALIZE_PENDING_INTENT_MSG: { 1836 ((PendingIntentRecord)msg.obj).completeFinalize(); 1837 } break; 1838 case POST_HEAVY_NOTIFICATION_MSG: { 1839 INotificationManager inm = NotificationManager.getService(); 1840 if (inm == null) { 1841 return; 1842 } 1843 1844 ActivityRecord root = (ActivityRecord)msg.obj; 1845 ProcessRecord process = root.app; 1846 if (process == null) { 1847 return; 1848 } 1849 1850 try { 1851 Context context = mContext.createPackageContext(process.info.packageName, 0); 1852 String text = mContext.getString(R.string.heavy_weight_notification, 1853 context.getApplicationInfo().loadLabel(context.getPackageManager())); 1854 Notification notification = new Notification.Builder(context) 1855 .setSmallIcon(com.android.internal.R.drawable.stat_sys_adb) 1856 .setWhen(0) 1857 .setOngoing(true) 1858 .setTicker(text) 1859 .setColor(mContext.getColor( 1860 com.android.internal.R.color.system_notification_accent_color)) 1861 .setContentTitle(text) 1862 .setContentText( 1863 mContext.getText(R.string.heavy_weight_notification_detail)) 1864 .setContentIntent(PendingIntent.getActivityAsUser(mContext, 0, 1865 root.intent, PendingIntent.FLAG_CANCEL_CURRENT, null, 1866 new UserHandle(root.userId))) 1867 .build(); 1868 try { 1869 int[] outId = new int[1]; 1870 inm.enqueueNotificationWithTag("android", "android", null, 1871 R.string.heavy_weight_notification, 1872 notification, outId, root.userId); 1873 } catch (RuntimeException e) { 1874 Slog.w(ActivityManagerService.TAG, 1875 "Error showing notification for heavy-weight app", e); 1876 } catch (RemoteException e) { 1877 } 1878 } catch (NameNotFoundException e) { 1879 Slog.w(TAG, "Unable to create context for heavy notification", e); 1880 } 1881 } break; 1882 case CANCEL_HEAVY_NOTIFICATION_MSG: { 1883 INotificationManager inm = NotificationManager.getService(); 1884 if (inm == null) { 1885 return; 1886 } 1887 try { 1888 inm.cancelNotificationWithTag("android", null, 1889 R.string.heavy_weight_notification, msg.arg1); 1890 } catch (RuntimeException e) { 1891 Slog.w(ActivityManagerService.TAG, 1892 "Error canceling notification for service", e); 1893 } catch (RemoteException e) { 1894 } 1895 } break; 1896 case CHECK_EXCESSIVE_WAKE_LOCKS_MSG: { 1897 synchronized (ActivityManagerService.this) { 1898 checkExcessivePowerUsageLocked(true); 1899 removeMessages(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 1900 Message nmsg = obtainMessage(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 1901 sendMessageDelayed(nmsg, POWER_CHECK_DELAY); 1902 } 1903 } break; 1904 case REPORT_MEM_USAGE_MSG: { 1905 final ArrayList<ProcessMemInfo> memInfos = (ArrayList<ProcessMemInfo>)msg.obj; 1906 Thread thread = new Thread() { 1907 @Override public void run() { 1908 reportMemUsage(memInfos); 1909 } 1910 }; 1911 thread.start(); 1912 break; 1913 } 1914 case REPORT_USER_SWITCH_MSG: { 1915 mUserController.dispatchUserSwitch((UserState) msg.obj, msg.arg1, msg.arg2); 1916 break; 1917 } 1918 case CONTINUE_USER_SWITCH_MSG: { 1919 mUserController.continueUserSwitch((UserState) msg.obj, msg.arg1, msg.arg2); 1920 break; 1921 } 1922 case USER_SWITCH_TIMEOUT_MSG: { 1923 mUserController.timeoutUserSwitch((UserState) msg.obj, msg.arg1, msg.arg2); 1924 break; 1925 } 1926 case IMMERSIVE_MODE_LOCK_MSG: { 1927 final boolean nextState = (msg.arg1 != 0); 1928 if (mUpdateLock.isHeld() != nextState) { 1929 if (DEBUG_IMMERSIVE) Slog.d(TAG_IMMERSIVE, 1930 "Applying new update lock state '" + nextState 1931 + "' for " + (ActivityRecord)msg.obj); 1932 if (nextState) { 1933 mUpdateLock.acquire(); 1934 } else { 1935 mUpdateLock.release(); 1936 } 1937 } 1938 break; 1939 } 1940 case PERSIST_URI_GRANTS_MSG: { 1941 writeGrantedUriPermissions(); 1942 break; 1943 } 1944 case REQUEST_ALL_PSS_MSG: { 1945 synchronized (ActivityManagerService.this) { 1946 requestPssAllProcsLocked(SystemClock.uptimeMillis(), true, false); 1947 } 1948 break; 1949 } 1950 case START_PROFILES_MSG: { 1951 synchronized (ActivityManagerService.this) { 1952 mUserController.startProfilesLocked(); 1953 } 1954 break; 1955 } 1956 case UPDATE_TIME: { 1957 synchronized (ActivityManagerService.this) { 1958 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 1959 ProcessRecord r = mLruProcesses.get(i); 1960 if (r.thread != null) { 1961 try { 1962 r.thread.updateTimePrefs(msg.arg1 == 0 ? false : true); 1963 } catch (RemoteException ex) { 1964 Slog.w(TAG, "Failed to update preferences for: " + r.info.processName); 1965 } 1966 } 1967 } 1968 } 1969 break; 1970 } 1971 case SYSTEM_USER_START_MSG: { 1972 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_USER_RUNNING_START, 1973 Integer.toString(msg.arg1), msg.arg1); 1974 mSystemServiceManager.startUser(msg.arg1); 1975 break; 1976 } 1977 case SYSTEM_USER_UNLOCK_MSG: { 1978 final int userId = msg.arg1; 1979 mSystemServiceManager.unlockUser(userId); 1980 synchronized (ActivityManagerService.this) { 1981 mRecentTasks.loadUserRecentsLocked(userId); 1982 } 1983 if (userId == UserHandle.USER_SYSTEM) { 1984 startPersistentApps(PackageManager.MATCH_DIRECT_BOOT_UNAWARE); 1985 } 1986 installEncryptionUnawareProviders(userId); 1987 mUserController.finishUserUnlocked((UserState) msg.obj); 1988 break; 1989 } 1990 case SYSTEM_USER_CURRENT_MSG: { 1991 mBatteryStatsService.noteEvent( 1992 BatteryStats.HistoryItem.EVENT_USER_FOREGROUND_FINISH, 1993 Integer.toString(msg.arg2), msg.arg2); 1994 mBatteryStatsService.noteEvent( 1995 BatteryStats.HistoryItem.EVENT_USER_FOREGROUND_START, 1996 Integer.toString(msg.arg1), msg.arg1); 1997 mSystemServiceManager.switchUser(msg.arg1); 1998 break; 1999 } 2000 case ENTER_ANIMATION_COMPLETE_MSG: { 2001 synchronized (ActivityManagerService.this) { 2002 ActivityRecord r = ActivityRecord.forTokenLocked((IBinder) msg.obj); 2003 if (r != null && r.app != null && r.app.thread != null) { 2004 try { 2005 r.app.thread.scheduleEnterAnimationComplete(r.appToken); 2006 } catch (RemoteException e) { 2007 } 2008 } 2009 } 2010 break; 2011 } 2012 case FINISH_BOOTING_MSG: { 2013 if (msg.arg1 != 0) { 2014 Trace.traceBegin(Trace.TRACE_TAG_ACTIVITY_MANAGER, "FinishBooting"); 2015 finishBooting(); 2016 Trace.traceEnd(Trace.TRACE_TAG_ACTIVITY_MANAGER); 2017 } 2018 if (msg.arg2 != 0) { 2019 enableScreenAfterBoot(); 2020 } 2021 break; 2022 } 2023 case SEND_LOCALE_TO_MOUNT_DAEMON_MSG: { 2024 try { 2025 Locale l = (Locale) msg.obj; 2026 IBinder service = ServiceManager.getService("mount"); 2027 IMountService mountService = IMountService.Stub.asInterface(service); 2028 Log.d(TAG, "Storing locale " + l.toLanguageTag() + " for decryption UI"); 2029 mountService.setField(StorageManager.SYSTEM_LOCALE_KEY, l.toLanguageTag()); 2030 } catch (RemoteException e) { 2031 Log.e(TAG, "Error storing locale for decryption UI", e); 2032 } 2033 break; 2034 } 2035 case NOTIFY_TASK_STACK_CHANGE_LISTENERS_MSG: { 2036 synchronized (ActivityManagerService.this) { 2037 for (int i = mTaskStackListeners.beginBroadcast() - 1; i >= 0; i--) { 2038 try { 2039 // Make a one-way callback to the listener 2040 mTaskStackListeners.getBroadcastItem(i).onTaskStackChanged(); 2041 } catch (RemoteException e){ 2042 // Handled by the RemoteCallbackList 2043 } 2044 } 2045 mTaskStackListeners.finishBroadcast(); 2046 } 2047 break; 2048 } 2049 case NOTIFY_ACTIVITY_PINNED_LISTENERS_MSG: { 2050 synchronized (ActivityManagerService.this) { 2051 for (int i = mTaskStackListeners.beginBroadcast() - 1; i >= 0; i--) { 2052 try { 2053 // Make a one-way callback to the listener 2054 mTaskStackListeners.getBroadcastItem(i).onActivityPinned(); 2055 } catch (RemoteException e){ 2056 // Handled by the RemoteCallbackList 2057 } 2058 } 2059 mTaskStackListeners.finishBroadcast(); 2060 } 2061 break; 2062 } 2063 case NOTIFY_PINNED_ACTIVITY_RESTART_ATTEMPT_LISTENERS_MSG: { 2064 synchronized (ActivityManagerService.this) { 2065 for (int i = mTaskStackListeners.beginBroadcast() - 1; i >= 0; i--) { 2066 try { 2067 // Make a one-way callback to the listener 2068 mTaskStackListeners.getBroadcastItem(i).onPinnedActivityRestartAttempt(); 2069 } catch (RemoteException e){ 2070 // Handled by the RemoteCallbackList 2071 } 2072 } 2073 mTaskStackListeners.finishBroadcast(); 2074 } 2075 break; 2076 } 2077 case NOTIFY_PINNED_STACK_ANIMATION_ENDED_LISTENERS_MSG: { 2078 synchronized (ActivityManagerService.this) { 2079 for (int i = mTaskStackListeners.beginBroadcast() - 1; i >= 0; i--) { 2080 try { 2081 // Make a one-way callback to the listener 2082 mTaskStackListeners.getBroadcastItem(i).onPinnedStackAnimationEnded(); 2083 } catch (RemoteException e){ 2084 // Handled by the RemoteCallbackList 2085 } 2086 } 2087 mTaskStackListeners.finishBroadcast(); 2088 } 2089 break; 2090 } 2091 case NOTIFY_FORCED_RESIZABLE_MSG: { 2092 synchronized (ActivityManagerService.this) { 2093 for (int i = mTaskStackListeners.beginBroadcast() - 1; i >= 0; i--) { 2094 try { 2095 // Make a one-way callback to the listener 2096 mTaskStackListeners.getBroadcastItem(i).onActivityForcedResizable( 2097 (String) msg.obj, msg.arg1); 2098 } catch (RemoteException e){ 2099 // Handled by the RemoteCallbackList 2100 } 2101 } 2102 mTaskStackListeners.finishBroadcast(); 2103 } 2104 break; 2105 } 2106 case NOTIFY_ACTIVITY_DISMISSING_DOCKED_STACK_MSG: { 2107 synchronized (ActivityManagerService.this) { 2108 for (int i = mTaskStackListeners.beginBroadcast() - 1; i >= 0; i--) { 2109 try { 2110 // Make a one-way callback to the listener 2111 mTaskStackListeners.getBroadcastItem(i) 2112 .onActivityDismissingDockedStack(); 2113 } catch (RemoteException e){ 2114 // Handled by the RemoteCallbackList 2115 } 2116 } 2117 mTaskStackListeners.finishBroadcast(); 2118 } 2119 break; 2120 } 2121 case NOTIFY_CLEARTEXT_NETWORK_MSG: { 2122 final int uid = msg.arg1; 2123 final byte[] firstPacket = (byte[]) msg.obj; 2124 2125 synchronized (mPidsSelfLocked) { 2126 for (int i = 0; i < mPidsSelfLocked.size(); i++) { 2127 final ProcessRecord p = mPidsSelfLocked.valueAt(i); 2128 if (p.uid == uid) { 2129 try { 2130 p.thread.notifyCleartextNetwork(firstPacket); 2131 } catch (RemoteException ignored) { 2132 } 2133 } 2134 } 2135 } 2136 break; 2137 } 2138 case POST_DUMP_HEAP_NOTIFICATION_MSG: { 2139 final String procName; 2140 final int uid; 2141 final long memLimit; 2142 final String reportPackage; 2143 synchronized (ActivityManagerService.this) { 2144 procName = mMemWatchDumpProcName; 2145 uid = mMemWatchDumpUid; 2146 Pair<Long, String> val = mMemWatchProcesses.get(procName, uid); 2147 if (val == null) { 2148 val = mMemWatchProcesses.get(procName, 0); 2149 } 2150 if (val != null) { 2151 memLimit = val.first; 2152 reportPackage = val.second; 2153 } else { 2154 memLimit = 0; 2155 reportPackage = null; 2156 } 2157 } 2158 if (procName == null) { 2159 return; 2160 } 2161 2162 if (DEBUG_PSS) Slog.d(TAG_PSS, 2163 "Showing dump heap notification from " + procName + "/" + uid); 2164 2165 INotificationManager inm = NotificationManager.getService(); 2166 if (inm == null) { 2167 return; 2168 } 2169 2170 String text = mContext.getString(R.string.dump_heap_notification, procName); 2171 2172 2173 Intent deleteIntent = new Intent(); 2174 deleteIntent.setAction(DumpHeapActivity.ACTION_DELETE_DUMPHEAP); 2175 Intent intent = new Intent(); 2176 intent.setClassName("android", DumpHeapActivity.class.getName()); 2177 intent.putExtra(DumpHeapActivity.KEY_PROCESS, procName); 2178 intent.putExtra(DumpHeapActivity.KEY_SIZE, memLimit); 2179 if (reportPackage != null) { 2180 intent.putExtra(DumpHeapActivity.KEY_DIRECT_LAUNCH, reportPackage); 2181 } 2182 int userId = UserHandle.getUserId(uid); 2183 Notification notification = new Notification.Builder(mContext) 2184 .setSmallIcon(com.android.internal.R.drawable.stat_sys_adb) 2185 .setWhen(0) 2186 .setOngoing(true) 2187 .setAutoCancel(true) 2188 .setTicker(text) 2189 .setColor(mContext.getColor( 2190 com.android.internal.R.color.system_notification_accent_color)) 2191 .setContentTitle(text) 2192 .setContentText( 2193 mContext.getText(R.string.dump_heap_notification_detail)) 2194 .setContentIntent(PendingIntent.getActivityAsUser(mContext, 0, 2195 intent, PendingIntent.FLAG_CANCEL_CURRENT, null, 2196 new UserHandle(userId))) 2197 .setDeleteIntent(PendingIntent.getBroadcastAsUser(mContext, 0, 2198 deleteIntent, 0, UserHandle.SYSTEM)) 2199 .build(); 2200 2201 try { 2202 int[] outId = new int[1]; 2203 inm.enqueueNotificationWithTag("android", "android", null, 2204 R.string.dump_heap_notification, 2205 notification, outId, userId); 2206 } catch (RuntimeException e) { 2207 Slog.w(ActivityManagerService.TAG, 2208 "Error showing notification for dump heap", e); 2209 } catch (RemoteException e) { 2210 } 2211 } break; 2212 case DELETE_DUMPHEAP_MSG: { 2213 revokeUriPermission(ActivityThread.currentActivityThread().getApplicationThread(), 2214 DumpHeapActivity.JAVA_URI, 2215 Intent.FLAG_GRANT_READ_URI_PERMISSION 2216 | Intent.FLAG_GRANT_WRITE_URI_PERMISSION, 2217 UserHandle.myUserId()); 2218 synchronized (ActivityManagerService.this) { 2219 mMemWatchDumpFile = null; 2220 mMemWatchDumpProcName = null; 2221 mMemWatchDumpPid = -1; 2222 mMemWatchDumpUid = -1; 2223 } 2224 } break; 2225 case FOREGROUND_PROFILE_CHANGED_MSG: { 2226 mUserController.dispatchForegroundProfileChanged(msg.arg1); 2227 } break; 2228 case REPORT_TIME_TRACKER_MSG: { 2229 AppTimeTracker tracker = (AppTimeTracker)msg.obj; 2230 tracker.deliverResult(mContext); 2231 } break; 2232 case REPORT_USER_SWITCH_COMPLETE_MSG: { 2233 mUserController.dispatchUserSwitchComplete(msg.arg1); 2234 } break; 2235 case SHUTDOWN_UI_AUTOMATION_CONNECTION_MSG: { 2236 IUiAutomationConnection connection = (IUiAutomationConnection) msg.obj; 2237 try { 2238 connection.shutdown(); 2239 } catch (RemoteException e) { 2240 Slog.w(TAG, "Error shutting down UiAutomationConnection"); 2241 } 2242 // Only a UiAutomation can set this flag and now that 2243 // it is finished we make sure it is reset to its default. 2244 mUserIsMonkey = false; 2245 } break; 2246 case APP_BOOST_DEACTIVATE_MSG: { 2247 synchronized(ActivityManagerService.this) { 2248 if (mIsBoosted) { 2249 if (mBoostStartTime < (SystemClock.uptimeMillis() - APP_BOOST_TIMEOUT)) { 2250 nativeMigrateFromBoost(); 2251 mIsBoosted = false; 2252 mBoostStartTime = 0; 2253 } else { 2254 Message newmsg = mHandler.obtainMessage(APP_BOOST_DEACTIVATE_MSG); 2255 mHandler.sendMessageDelayed(newmsg, APP_BOOST_TIMEOUT); 2256 } 2257 } 2258 } 2259 } break; 2260 case IDLE_UIDS_MSG: { 2261 idleUids(); 2262 } break; 2263 case LOG_STACK_STATE: { 2264 synchronized (ActivityManagerService.this) { 2265 mStackSupervisor.logStackState(); 2266 } 2267 } break; 2268 case VR_MODE_CHANGE_MSG: { 2269 VrManagerInternal vrService = LocalServices.getService(VrManagerInternal.class); 2270 final ActivityRecord r = (ActivityRecord) msg.obj; 2271 boolean vrMode; 2272 ComponentName requestedPackage; 2273 ComponentName callingPackage; 2274 int userId; 2275 synchronized (ActivityManagerService.this) { 2276 vrMode = r.requestedVrComponent != null; 2277 requestedPackage = r.requestedVrComponent; 2278 userId = r.userId; 2279 callingPackage = r.info.getComponentName(); 2280 if (mInVrMode != vrMode) { 2281 mInVrMode = vrMode; 2282 mShowDialogs = shouldShowDialogs(mConfiguration, mInVrMode); 2283 } 2284 } 2285 vrService.setVrMode(vrMode, requestedPackage, userId, callingPackage); 2286 } break; 2287 case VR_MODE_APPLY_IF_NEEDED_MSG: { 2288 final ActivityRecord r = (ActivityRecord) msg.obj; 2289 final boolean needsVrMode = r != null && r.requestedVrComponent != null; 2290 if (needsVrMode) { 2291 VrManagerInternal vrService = 2292 LocalServices.getService(VrManagerInternal.class); 2293 boolean enable = msg.arg1 == 1; 2294 vrService.setVrMode(enable, r.requestedVrComponent, r.userId, 2295 r.info.getComponentName()); 2296 } 2297 } break; 2298 } 2299 } 2300 }; 2301 2302 static final int COLLECT_PSS_BG_MSG = 1; 2303 2304 final Handler mBgHandler = new Handler(BackgroundThread.getHandler().getLooper()) { 2305 @Override 2306 public void handleMessage(Message msg) { 2307 switch (msg.what) { 2308 case COLLECT_PSS_BG_MSG: { 2309 long start = SystemClock.uptimeMillis(); 2310 MemInfoReader memInfo = null; 2311 synchronized (ActivityManagerService.this) { 2312 if (mFullPssPending) { 2313 mFullPssPending = false; 2314 memInfo = new MemInfoReader(); 2315 } 2316 } 2317 if (memInfo != null) { 2318 updateCpuStatsNow(); 2319 long nativeTotalPss = 0; 2320 synchronized (mProcessCpuTracker) { 2321 final int N = mProcessCpuTracker.countStats(); 2322 for (int j=0; j<N; j++) { 2323 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(j); 2324 if (st.vsize <= 0 || st.uid >= Process.FIRST_APPLICATION_UID) { 2325 // This is definitely an application process; skip it. 2326 continue; 2327 } 2328 synchronized (mPidsSelfLocked) { 2329 if (mPidsSelfLocked.indexOfKey(st.pid) >= 0) { 2330 // This is one of our own processes; skip it. 2331 continue; 2332 } 2333 } 2334 nativeTotalPss += Debug.getPss(st.pid, null, null); 2335 } 2336 } 2337 memInfo.readMemInfo(); 2338 synchronized (ActivityManagerService.this) { 2339 if (DEBUG_PSS) Slog.d(TAG_PSS, "Collected native and kernel memory in " 2340 + (SystemClock.uptimeMillis()-start) + "ms"); 2341 final long cachedKb = memInfo.getCachedSizeKb(); 2342 final long freeKb = memInfo.getFreeSizeKb(); 2343 final long zramKb = memInfo.getZramTotalSizeKb(); 2344 final long kernelKb = memInfo.getKernelUsedSizeKb(); 2345 EventLogTags.writeAmMeminfo(cachedKb*1024, freeKb*1024, zramKb*1024, 2346 kernelKb*1024, nativeTotalPss*1024); 2347 mProcessStats.addSysMemUsageLocked(cachedKb, freeKb, zramKb, kernelKb, 2348 nativeTotalPss); 2349 } 2350 } 2351 2352 int num = 0; 2353 long[] tmp = new long[2]; 2354 do { 2355 ProcessRecord proc; 2356 int procState; 2357 int pid; 2358 long lastPssTime; 2359 synchronized (ActivityManagerService.this) { 2360 if (mPendingPssProcesses.size() <= 0) { 2361 if (mTestPssMode || DEBUG_PSS) Slog.d(TAG_PSS, 2362 "Collected PSS of " + num + " processes in " 2363 + (SystemClock.uptimeMillis() - start) + "ms"); 2364 mPendingPssProcesses.clear(); 2365 return; 2366 } 2367 proc = mPendingPssProcesses.remove(0); 2368 procState = proc.pssProcState; 2369 lastPssTime = proc.lastPssTime; 2370 if (proc.thread != null && procState == proc.setProcState 2371 && (lastPssTime+ProcessList.PSS_SAFE_TIME_FROM_STATE_CHANGE) 2372 < SystemClock.uptimeMillis()) { 2373 pid = proc.pid; 2374 } else { 2375 proc = null; 2376 pid = 0; 2377 } 2378 } 2379 if (proc != null) { 2380 long pss = Debug.getPss(pid, tmp, null); 2381 synchronized (ActivityManagerService.this) { 2382 if (pss != 0 && proc.thread != null && proc.setProcState == procState 2383 && proc.pid == pid && proc.lastPssTime == lastPssTime) { 2384 num++; 2385 recordPssSampleLocked(proc, procState, pss, tmp[0], tmp[1], 2386 SystemClock.uptimeMillis()); 2387 } 2388 } 2389 } 2390 } while (true); 2391 } 2392 } 2393 } 2394 }; 2395 2396 public void setSystemProcess() { 2397 try { 2398 ServiceManager.addService(Context.ACTIVITY_SERVICE, this, true); 2399 ServiceManager.addService(ProcessStats.SERVICE_NAME, mProcessStats); 2400 ServiceManager.addService("meminfo", new MemBinder(this)); 2401 ServiceManager.addService("gfxinfo", new GraphicsBinder(this)); 2402 ServiceManager.addService("dbinfo", new DbBinder(this)); 2403 if (MONITOR_CPU_USAGE) { 2404 ServiceManager.addService("cpuinfo", new CpuBinder(this)); 2405 } 2406 ServiceManager.addService("permission", new PermissionController(this)); 2407 ServiceManager.addService("processinfo", new ProcessInfoService(this)); 2408 2409 ApplicationInfo info = mContext.getPackageManager().getApplicationInfo( 2410 "android", STOCK_PM_FLAGS | MATCH_SYSTEM_ONLY); 2411 mSystemThread.installSystemApplicationInfo(info, getClass().getClassLoader()); 2412 2413 synchronized (this) { 2414 ProcessRecord app = newProcessRecordLocked(info, info.processName, false, 0); 2415 app.persistent = true; 2416 app.pid = MY_PID; 2417 app.maxAdj = ProcessList.SYSTEM_ADJ; 2418 app.makeActive(mSystemThread.getApplicationThread(), mProcessStats); 2419 synchronized (mPidsSelfLocked) { 2420 mPidsSelfLocked.put(app.pid, app); 2421 } 2422 updateLruProcessLocked(app, false, null); 2423 updateOomAdjLocked(); 2424 } 2425 } catch (PackageManager.NameNotFoundException e) { 2426 throw new RuntimeException( 2427 "Unable to find android system package", e); 2428 } 2429 } 2430 2431 public void setWindowManager(WindowManagerService wm) { 2432 mWindowManager = wm; 2433 mStackSupervisor.setWindowManager(wm); 2434 mActivityStarter.setWindowManager(wm); 2435 } 2436 2437 public void setUsageStatsManager(UsageStatsManagerInternal usageStatsManager) { 2438 mUsageStatsService = usageStatsManager; 2439 } 2440 2441 public void startObservingNativeCrashes() { 2442 final NativeCrashListener ncl = new NativeCrashListener(this); 2443 ncl.start(); 2444 } 2445 2446 public IAppOpsService getAppOpsService() { 2447 return mAppOpsService; 2448 } 2449 2450 static class MemBinder extends Binder { 2451 ActivityManagerService mActivityManagerService; 2452 MemBinder(ActivityManagerService activityManagerService) { 2453 mActivityManagerService = activityManagerService; 2454 } 2455 2456 @Override 2457 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 2458 if (mActivityManagerService.checkCallingPermission(android.Manifest.permission.DUMP) 2459 != PackageManager.PERMISSION_GRANTED) { 2460 pw.println("Permission Denial: can't dump meminfo from from pid=" 2461 + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid() 2462 + " without permission " + android.Manifest.permission.DUMP); 2463 return; 2464 } 2465 2466 mActivityManagerService.dumpApplicationMemoryUsage(fd, pw, " ", args, false, null); 2467 } 2468 } 2469 2470 static class GraphicsBinder extends Binder { 2471 ActivityManagerService mActivityManagerService; 2472 GraphicsBinder(ActivityManagerService activityManagerService) { 2473 mActivityManagerService = activityManagerService; 2474 } 2475 2476 @Override 2477 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 2478 if (mActivityManagerService.checkCallingPermission(android.Manifest.permission.DUMP) 2479 != PackageManager.PERMISSION_GRANTED) { 2480 pw.println("Permission Denial: can't dump gfxinfo from from pid=" 2481 + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid() 2482 + " without permission " + android.Manifest.permission.DUMP); 2483 return; 2484 } 2485 2486 mActivityManagerService.dumpGraphicsHardwareUsage(fd, pw, args); 2487 } 2488 } 2489 2490 static class DbBinder extends Binder { 2491 ActivityManagerService mActivityManagerService; 2492 DbBinder(ActivityManagerService activityManagerService) { 2493 mActivityManagerService = activityManagerService; 2494 } 2495 2496 @Override 2497 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 2498 if (mActivityManagerService.checkCallingPermission(android.Manifest.permission.DUMP) 2499 != PackageManager.PERMISSION_GRANTED) { 2500 pw.println("Permission Denial: can't dump dbinfo from from pid=" 2501 + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid() 2502 + " without permission " + android.Manifest.permission.DUMP); 2503 return; 2504 } 2505 2506 mActivityManagerService.dumpDbInfo(fd, pw, args); 2507 } 2508 } 2509 2510 static class CpuBinder extends Binder { 2511 ActivityManagerService mActivityManagerService; 2512 CpuBinder(ActivityManagerService activityManagerService) { 2513 mActivityManagerService = activityManagerService; 2514 } 2515 2516 @Override 2517 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 2518 if (mActivityManagerService.checkCallingPermission(android.Manifest.permission.DUMP) 2519 != PackageManager.PERMISSION_GRANTED) { 2520 pw.println("Permission Denial: can't dump cpuinfo from from pid=" 2521 + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid() 2522 + " without permission " + android.Manifest.permission.DUMP); 2523 return; 2524 } 2525 2526 synchronized (mActivityManagerService.mProcessCpuTracker) { 2527 pw.print(mActivityManagerService.mProcessCpuTracker.printCurrentLoad()); 2528 pw.print(mActivityManagerService.mProcessCpuTracker.printCurrentState( 2529 SystemClock.uptimeMillis())); 2530 } 2531 } 2532 } 2533 2534 public static final class Lifecycle extends SystemService { 2535 private final ActivityManagerService mService; 2536 2537 public Lifecycle(Context context) { 2538 super(context); 2539 mService = new ActivityManagerService(context); 2540 } 2541 2542 @Override 2543 public void onStart() { 2544 mService.start(); 2545 } 2546 2547 public ActivityManagerService getService() { 2548 return mService; 2549 } 2550 } 2551 2552 // Note: This method is invoked on the main thread but may need to attach various 2553 // handlers to other threads. So take care to be explicit about the looper. 2554 public ActivityManagerService(Context systemContext) { 2555 mContext = systemContext; 2556 mFactoryTest = FactoryTest.getMode(); 2557 mSystemThread = ActivityThread.currentActivityThread(); 2558 2559 Slog.i(TAG, "Memory class: " + ActivityManager.staticGetMemoryClass()); 2560 2561 mHandlerThread = new ServiceThread(TAG, 2562 android.os.Process.THREAD_PRIORITY_FOREGROUND, false /*allowIo*/); 2563 mHandlerThread.start(); 2564 mHandler = new MainHandler(mHandlerThread.getLooper()); 2565 mUiHandler = new UiHandler(); 2566 2567 /* static; one-time init here */ 2568 if (sKillHandler == null) { 2569 sKillThread = new ServiceThread(TAG + ":kill", 2570 android.os.Process.THREAD_PRIORITY_BACKGROUND, true /* allowIo */); 2571 sKillThread.start(); 2572 sKillHandler = new KillHandler(sKillThread.getLooper()); 2573 } 2574 2575 mFgBroadcastQueue = new BroadcastQueue(this, mHandler, 2576 "foreground", BROADCAST_FG_TIMEOUT, false); 2577 mBgBroadcastQueue = new BroadcastQueue(this, mHandler, 2578 "background", BROADCAST_BG_TIMEOUT, true); 2579 mBroadcastQueues[0] = mFgBroadcastQueue; 2580 mBroadcastQueues[1] = mBgBroadcastQueue; 2581 2582 mServices = new ActiveServices(this); 2583 mProviderMap = new ProviderMap(this); 2584 mAppErrors = new AppErrors(mContext, this); 2585 2586 // TODO: Move creation of battery stats service outside of activity manager service. 2587 File dataDir = Environment.getDataDirectory(); 2588 File systemDir = new File(dataDir, "system"); 2589 systemDir.mkdirs(); 2590 mBatteryStatsService = new BatteryStatsService(systemDir, mHandler); 2591 mBatteryStatsService.getActiveStatistics().readLocked(); 2592 mBatteryStatsService.scheduleWriteToDisk(); 2593 mOnBattery = DEBUG_POWER ? true 2594 : mBatteryStatsService.getActiveStatistics().getIsOnBattery(); 2595 mBatteryStatsService.getActiveStatistics().setCallback(this); 2596 2597 mProcessStats = new ProcessStatsService(this, new File(systemDir, "procstats")); 2598 2599 mAppOpsService = new AppOpsService(new File(systemDir, "appops.xml"), mHandler); 2600 mAppOpsService.startWatchingMode(AppOpsManager.OP_RUN_IN_BACKGROUND, null, 2601 new IAppOpsCallback.Stub() { 2602 @Override public void opChanged(int op, int uid, String packageName) { 2603 if (op == AppOpsManager.OP_RUN_IN_BACKGROUND && packageName != null) { 2604 if (mAppOpsService.checkOperation(op, uid, packageName) 2605 != AppOpsManager.MODE_ALLOWED) { 2606 runInBackgroundDisabled(uid); 2607 } 2608 } 2609 } 2610 }); 2611 2612 mGrantFile = new AtomicFile(new File(systemDir, "urigrants.xml")); 2613 2614 mUserController = new UserController(this); 2615 2616 GL_ES_VERSION = SystemProperties.getInt("ro.opengles.version", 2617 ConfigurationInfo.GL_ES_VERSION_UNDEFINED); 2618 2619 mTrackingAssociations = "1".equals(SystemProperties.get("debug.track-associations")); 2620 2621 mConfiguration.setToDefaults(); 2622 mConfiguration.setLocales(LocaleList.getDefault()); 2623 2624 mConfigurationSeq = mConfiguration.seq = 1; 2625 mProcessCpuTracker.init(); 2626 2627 mCompatModePackages = new CompatModePackages(this, systemDir, mHandler); 2628 mIntentFirewall = new IntentFirewall(new IntentFirewallInterface(), mHandler); 2629 mStackSupervisor = new ActivityStackSupervisor(this); 2630 mActivityStarter = new ActivityStarter(this, mStackSupervisor); 2631 mRecentTasks = new RecentTasks(this, mStackSupervisor); 2632 2633 mProcessCpuThread = new Thread("CpuTracker") { 2634 @Override 2635 public void run() { 2636 while (true) { 2637 try { 2638 try { 2639 synchronized(this) { 2640 final long now = SystemClock.uptimeMillis(); 2641 long nextCpuDelay = (mLastCpuTime.get()+MONITOR_CPU_MAX_TIME)-now; 2642 long nextWriteDelay = (mLastWriteTime+BATTERY_STATS_TIME)-now; 2643 //Slog.i(TAG, "Cpu delay=" + nextCpuDelay 2644 // + ", write delay=" + nextWriteDelay); 2645 if (nextWriteDelay < nextCpuDelay) { 2646 nextCpuDelay = nextWriteDelay; 2647 } 2648 if (nextCpuDelay > 0) { 2649 mProcessCpuMutexFree.set(true); 2650 this.wait(nextCpuDelay); 2651 } 2652 } 2653 } catch (InterruptedException e) { 2654 } 2655 updateCpuStatsNow(); 2656 } catch (Exception e) { 2657 Slog.e(TAG, "Unexpected exception collecting process stats", e); 2658 } 2659 } 2660 } 2661 }; 2662 2663 Watchdog.getInstance().addMonitor(this); 2664 Watchdog.getInstance().addThread(mHandler); 2665 } 2666 2667 public void setSystemServiceManager(SystemServiceManager mgr) { 2668 mSystemServiceManager = mgr; 2669 } 2670 2671 public void setInstaller(Installer installer) { 2672 mInstaller = installer; 2673 } 2674 2675 private void start() { 2676 Process.removeAllProcessGroups(); 2677 mProcessCpuThread.start(); 2678 2679 mBatteryStatsService.publish(mContext); 2680 mAppOpsService.publish(mContext); 2681 Slog.d("AppOps", "AppOpsService published"); 2682 LocalServices.addService(ActivityManagerInternal.class, new LocalService()); 2683 } 2684 2685 void onUserStoppedLocked(int userId) { 2686 mRecentTasks.unloadUserDataFromMemoryLocked(userId); 2687 } 2688 2689 public void initPowerManagement() { 2690 mStackSupervisor.initPowerManagement(); 2691 mBatteryStatsService.initPowerManagement(); 2692 mLocalPowerManager = LocalServices.getService(PowerManagerInternal.class); 2693 PowerManager pm = (PowerManager)mContext.getSystemService(Context.POWER_SERVICE); 2694 mVoiceWakeLock = pm.newWakeLock(PowerManager.PARTIAL_WAKE_LOCK, "*voice*"); 2695 mVoiceWakeLock.setReferenceCounted(false); 2696 } 2697 2698 @Override 2699 public boolean onTransact(int code, Parcel data, Parcel reply, int flags) 2700 throws RemoteException { 2701 if (code == SYSPROPS_TRANSACTION) { 2702 // We need to tell all apps about the system property change. 2703 ArrayList<IBinder> procs = new ArrayList<IBinder>(); 2704 synchronized(this) { 2705 final int NP = mProcessNames.getMap().size(); 2706 for (int ip=0; ip<NP; ip++) { 2707 SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 2708 final int NA = apps.size(); 2709 for (int ia=0; ia<NA; ia++) { 2710 ProcessRecord app = apps.valueAt(ia); 2711 if (app.thread != null) { 2712 procs.add(app.thread.asBinder()); 2713 } 2714 } 2715 } 2716 } 2717 2718 int N = procs.size(); 2719 for (int i=0; i<N; i++) { 2720 Parcel data2 = Parcel.obtain(); 2721 try { 2722 procs.get(i).transact(IBinder.SYSPROPS_TRANSACTION, data2, null, 0); 2723 } catch (RemoteException e) { 2724 } 2725 data2.recycle(); 2726 } 2727 } 2728 try { 2729 return super.onTransact(code, data, reply, flags); 2730 } catch (RuntimeException e) { 2731 // The activity manager only throws security exceptions, so let's 2732 // log all others. 2733 if (!(e instanceof SecurityException)) { 2734 Slog.wtf(TAG, "Activity Manager Crash", e); 2735 } 2736 throw e; 2737 } 2738 } 2739 2740 void updateCpuStats() { 2741 final long now = SystemClock.uptimeMillis(); 2742 if (mLastCpuTime.get() >= now - MONITOR_CPU_MIN_TIME) { 2743 return; 2744 } 2745 if (mProcessCpuMutexFree.compareAndSet(true, false)) { 2746 synchronized (mProcessCpuThread) { 2747 mProcessCpuThread.notify(); 2748 } 2749 } 2750 } 2751 2752 void updateCpuStatsNow() { 2753 synchronized (mProcessCpuTracker) { 2754 mProcessCpuMutexFree.set(false); 2755 final long now = SystemClock.uptimeMillis(); 2756 boolean haveNewCpuStats = false; 2757 2758 if (MONITOR_CPU_USAGE && 2759 mLastCpuTime.get() < (now-MONITOR_CPU_MIN_TIME)) { 2760 mLastCpuTime.set(now); 2761 mProcessCpuTracker.update(); 2762 if (mProcessCpuTracker.hasGoodLastStats()) { 2763 haveNewCpuStats = true; 2764 //Slog.i(TAG, mProcessCpu.printCurrentState()); 2765 //Slog.i(TAG, "Total CPU usage: " 2766 // + mProcessCpu.getTotalCpuPercent() + "%"); 2767 2768 // Slog the cpu usage if the property is set. 2769 if ("true".equals(SystemProperties.get("events.cpu"))) { 2770 int user = mProcessCpuTracker.getLastUserTime(); 2771 int system = mProcessCpuTracker.getLastSystemTime(); 2772 int iowait = mProcessCpuTracker.getLastIoWaitTime(); 2773 int irq = mProcessCpuTracker.getLastIrqTime(); 2774 int softIrq = mProcessCpuTracker.getLastSoftIrqTime(); 2775 int idle = mProcessCpuTracker.getLastIdleTime(); 2776 2777 int total = user + system + iowait + irq + softIrq + idle; 2778 if (total == 0) total = 1; 2779 2780 EventLog.writeEvent(EventLogTags.CPU, 2781 ((user+system+iowait+irq+softIrq) * 100) / total, 2782 (user * 100) / total, 2783 (system * 100) / total, 2784 (iowait * 100) / total, 2785 (irq * 100) / total, 2786 (softIrq * 100) / total); 2787 } 2788 } 2789 } 2790 2791 final BatteryStatsImpl bstats = mBatteryStatsService.getActiveStatistics(); 2792 synchronized(bstats) { 2793 synchronized(mPidsSelfLocked) { 2794 if (haveNewCpuStats) { 2795 if (bstats.startAddingCpuLocked()) { 2796 int totalUTime = 0; 2797 int totalSTime = 0; 2798 final int N = mProcessCpuTracker.countStats(); 2799 for (int i=0; i<N; i++) { 2800 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(i); 2801 if (!st.working) { 2802 continue; 2803 } 2804 ProcessRecord pr = mPidsSelfLocked.get(st.pid); 2805 totalUTime += st.rel_utime; 2806 totalSTime += st.rel_stime; 2807 if (pr != null) { 2808 BatteryStatsImpl.Uid.Proc ps = pr.curProcBatteryStats; 2809 if (ps == null || !ps.isActive()) { 2810 pr.curProcBatteryStats = ps = bstats.getProcessStatsLocked( 2811 pr.info.uid, pr.processName); 2812 } 2813 ps.addCpuTimeLocked(st.rel_utime, st.rel_stime); 2814 pr.curCpuTime += st.rel_utime + st.rel_stime; 2815 } else { 2816 BatteryStatsImpl.Uid.Proc ps = st.batteryStats; 2817 if (ps == null || !ps.isActive()) { 2818 st.batteryStats = ps = bstats.getProcessStatsLocked( 2819 bstats.mapUid(st.uid), st.name); 2820 } 2821 ps.addCpuTimeLocked(st.rel_utime, st.rel_stime); 2822 } 2823 } 2824 final int userTime = mProcessCpuTracker.getLastUserTime(); 2825 final int systemTime = mProcessCpuTracker.getLastSystemTime(); 2826 final int iowaitTime = mProcessCpuTracker.getLastIoWaitTime(); 2827 final int irqTime = mProcessCpuTracker.getLastIrqTime(); 2828 final int softIrqTime = mProcessCpuTracker.getLastSoftIrqTime(); 2829 final int idleTime = mProcessCpuTracker.getLastIdleTime(); 2830 bstats.finishAddingCpuLocked(totalUTime, totalSTime, userTime, 2831 systemTime, iowaitTime, irqTime, softIrqTime, idleTime); 2832 } 2833 } 2834 } 2835 2836 if (mLastWriteTime < (now-BATTERY_STATS_TIME)) { 2837 mLastWriteTime = now; 2838 mBatteryStatsService.scheduleWriteToDisk(); 2839 } 2840 } 2841 } 2842 } 2843 2844 @Override 2845 public void batteryNeedsCpuUpdate() { 2846 updateCpuStatsNow(); 2847 } 2848 2849 @Override 2850 public void batteryPowerChanged(boolean onBattery) { 2851 // When plugging in, update the CPU stats first before changing 2852 // the plug state. 2853 updateCpuStatsNow(); 2854 synchronized (this) { 2855 synchronized(mPidsSelfLocked) { 2856 mOnBattery = DEBUG_POWER ? true : onBattery; 2857 } 2858 } 2859 } 2860 2861 @Override 2862 public void batterySendBroadcast(Intent intent) { 2863 broadcastIntentLocked(null, null, intent, null, null, 0, null, null, null, 2864 AppOpsManager.OP_NONE, null, false, false, 2865 -1, Process.SYSTEM_UID, UserHandle.USER_ALL); 2866 } 2867 2868 /** 2869 * Initialize the application bind args. These are passed to each 2870 * process when the bindApplication() IPC is sent to the process. They're 2871 * lazily setup to make sure the services are running when they're asked for. 2872 */ 2873 private HashMap<String, IBinder> getCommonServicesLocked(boolean isolated) { 2874 if (mAppBindArgs == null) { 2875 mAppBindArgs = new HashMap<>(); 2876 2877 // Isolated processes won't get this optimization, so that we don't 2878 // violate the rules about which services they have access to. 2879 if (!isolated) { 2880 // Setup the application init args 2881 mAppBindArgs.put("package", ServiceManager.getService("package")); 2882 mAppBindArgs.put("window", ServiceManager.getService("window")); 2883 mAppBindArgs.put(Context.ALARM_SERVICE, 2884 ServiceManager.getService(Context.ALARM_SERVICE)); 2885 } 2886 } 2887 return mAppBindArgs; 2888 } 2889 2890 boolean setFocusedActivityLocked(ActivityRecord r, String reason) { 2891 if (r == null || mFocusedActivity == r) { 2892 return false; 2893 } 2894 2895 if (!r.isFocusable()) { 2896 if (DEBUG_FOCUS) Slog.d(TAG_FOCUS, "setFocusedActivityLocked: unfocusable r=" + r); 2897 return false; 2898 } 2899 2900 if (DEBUG_FOCUS) Slog.d(TAG_FOCUS, "setFocusedActivityLocked: r=" + r); 2901 2902 final boolean wasDoingSetFocusedActivity = mDoingSetFocusedActivity; 2903 if (wasDoingSetFocusedActivity) Slog.w(TAG, 2904 "setFocusedActivityLocked: called recursively, r=" + r + ", reason=" + reason); 2905 mDoingSetFocusedActivity = true; 2906 2907 final ActivityRecord last = mFocusedActivity; 2908 mFocusedActivity = r; 2909 if (r.task.isApplicationTask()) { 2910 if (mCurAppTimeTracker != r.appTimeTracker) { 2911 // We are switching app tracking. Complete the current one. 2912 if (mCurAppTimeTracker != null) { 2913 mCurAppTimeTracker.stop(); 2914 mHandler.obtainMessage( 2915 REPORT_TIME_TRACKER_MSG, mCurAppTimeTracker).sendToTarget(); 2916 mStackSupervisor.clearOtherAppTimeTrackers(r.appTimeTracker); 2917 mCurAppTimeTracker = null; 2918 } 2919 if (r.appTimeTracker != null) { 2920 mCurAppTimeTracker = r.appTimeTracker; 2921 startTimeTrackingFocusedActivityLocked(); 2922 } 2923 } else { 2924 startTimeTrackingFocusedActivityLocked(); 2925 } 2926 } else { 2927 r.appTimeTracker = null; 2928 } 2929 // TODO: VI Maybe r.task.voiceInteractor || r.voiceInteractor != null 2930 // TODO: Probably not, because we don't want to resume voice on switching 2931 // back to this activity 2932 if (r.task.voiceInteractor != null) { 2933 startRunningVoiceLocked(r.task.voiceSession, r.info.applicationInfo.uid); 2934 } else { 2935 finishRunningVoiceLocked(); 2936 IVoiceInteractionSession session; 2937 if (last != null && ((session = last.task.voiceSession) != null 2938 || (session = last.voiceSession) != null)) { 2939 // We had been in a voice interaction session, but now focused has 2940 // move to something different. Just finish the session, we can't 2941 // return to it and retain the proper state and synchronization with 2942 // the voice interaction service. 2943 finishVoiceTask(session); 2944 } 2945 } 2946 if (mStackSupervisor.moveActivityStackToFront(r, reason + " setFocusedActivity")) { 2947 mWindowManager.setFocusedApp(r.appToken, true); 2948 } 2949 applyUpdateLockStateLocked(r); 2950 applyUpdateVrModeLocked(r); 2951 if (mFocusedActivity.userId != mLastFocusedUserId) { 2952 mHandler.removeMessages(FOREGROUND_PROFILE_CHANGED_MSG); 2953 mHandler.obtainMessage( 2954 FOREGROUND_PROFILE_CHANGED_MSG, mFocusedActivity.userId, 0).sendToTarget(); 2955 mLastFocusedUserId = mFocusedActivity.userId; 2956 } 2957 2958 // Log a warning if the focused app is changed during the process. This could 2959 // indicate a problem of the focus setting logic! 2960 if (mFocusedActivity != r) Slog.w(TAG, 2961 "setFocusedActivityLocked: r=" + r + " but focused to " + mFocusedActivity); 2962 mDoingSetFocusedActivity = wasDoingSetFocusedActivity; 2963 2964 EventLogTags.writeAmFocusedActivity( 2965 mFocusedActivity == null ? -1 : mFocusedActivity.userId, 2966 mFocusedActivity == null ? "NULL" : mFocusedActivity.shortComponentName, 2967 reason); 2968 return true; 2969 } 2970 2971 final void resetFocusedActivityIfNeededLocked(ActivityRecord goingAway) { 2972 if (mFocusedActivity != goingAway) { 2973 return; 2974 } 2975 2976 final ActivityStack focusedStack = mStackSupervisor.getFocusedStack(); 2977 if (focusedStack != null) { 2978 final ActivityRecord top = focusedStack.topActivity(); 2979 if (top != null && top.userId != mLastFocusedUserId) { 2980 mHandler.removeMessages(FOREGROUND_PROFILE_CHANGED_MSG); 2981 mHandler.sendMessage( 2982 mHandler.obtainMessage(FOREGROUND_PROFILE_CHANGED_MSG, top.userId, 0)); 2983 mLastFocusedUserId = top.userId; 2984 } 2985 } 2986 2987 // Try to move focus to another activity if possible. 2988 if (setFocusedActivityLocked( 2989 focusedStack.topRunningActivityLocked(), "resetFocusedActivityIfNeeded")) { 2990 return; 2991 } 2992 2993 if (DEBUG_FOCUS) Slog.d(TAG_FOCUS, "resetFocusedActivityIfNeeded: Setting focus to NULL " 2994 + "prev mFocusedActivity=" + mFocusedActivity + " goingAway=" + goingAway); 2995 mFocusedActivity = null; 2996 EventLogTags.writeAmFocusedActivity(-1, "NULL", "resetFocusedActivityIfNeeded"); 2997 } 2998 2999 @Override 3000 public void setFocusedStack(int stackId) { 3001 enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "setFocusedStack()"); 3002 if (DEBUG_FOCUS) Slog.d(TAG_FOCUS, "setFocusedStack: stackId=" + stackId); 3003 final long callingId = Binder.clearCallingIdentity(); 3004 try { 3005 synchronized (this) { 3006 final ActivityStack stack = mStackSupervisor.getStack(stackId); 3007 if (stack == null) { 3008 return; 3009 } 3010 final ActivityRecord r = stack.topRunningActivityLocked(); 3011 if (setFocusedActivityLocked(r, "setFocusedStack")) { 3012 mStackSupervisor.resumeFocusedStackTopActivityLocked(); 3013 } 3014 } 3015 } finally { 3016 Binder.restoreCallingIdentity(callingId); 3017 } 3018 } 3019 3020 @Override 3021 public void setFocusedTask(int taskId) { 3022 enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "setFocusedTask()"); 3023 if (DEBUG_FOCUS) Slog.d(TAG_FOCUS, "setFocusedTask: taskId=" + taskId); 3024 final long callingId = Binder.clearCallingIdentity(); 3025 try { 3026 synchronized (this) { 3027 final TaskRecord task = mStackSupervisor.anyTaskForIdLocked(taskId); 3028 if (task == null) { 3029 return; 3030 } 3031 final ActivityRecord r = task.topRunningActivityLocked(); 3032 if (setFocusedActivityLocked(r, "setFocusedTask")) { 3033 mStackSupervisor.resumeFocusedStackTopActivityLocked(); 3034 } 3035 } 3036 } finally { 3037 Binder.restoreCallingIdentity(callingId); 3038 } 3039 } 3040 3041 /** Sets the task stack listener that gets callbacks when a task stack changes. */ 3042 @Override 3043 public void registerTaskStackListener(ITaskStackListener listener) throws RemoteException { 3044 enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "registerTaskStackListener()"); 3045 synchronized (this) { 3046 if (listener != null) { 3047 mTaskStackListeners.register(listener); 3048 } 3049 } 3050 } 3051 3052 @Override 3053 public void notifyActivityDrawn(IBinder token) { 3054 if (DEBUG_VISIBILITY) Slog.d(TAG_VISIBILITY, "notifyActivityDrawn: token=" + token); 3055 synchronized (this) { 3056 ActivityRecord r = mStackSupervisor.isInAnyStackLocked(token); 3057 if (r != null) { 3058 r.task.stack.notifyActivityDrawnLocked(r); 3059 } 3060 } 3061 } 3062 3063 final void applyUpdateLockStateLocked(ActivityRecord r) { 3064 // Modifications to the UpdateLock state are done on our handler, outside 3065 // the activity manager's locks. The new state is determined based on the 3066 // state *now* of the relevant activity record. The object is passed to 3067 // the handler solely for logging detail, not to be consulted/modified. 3068 final boolean nextState = r != null && r.immersive; 3069 mHandler.sendMessage( 3070 mHandler.obtainMessage(IMMERSIVE_MODE_LOCK_MSG, (nextState) ? 1 : 0, 0, r)); 3071 } 3072 3073 final void applyUpdateVrModeLocked(ActivityRecord r) { 3074 mHandler.sendMessage( 3075 mHandler.obtainMessage(VR_MODE_CHANGE_MSG, 0, 0, r)); 3076 } 3077 3078 private void applyVrModeIfNeededLocked(ActivityRecord r, boolean enable) { 3079 mHandler.sendMessage( 3080 mHandler.obtainMessage(VR_MODE_APPLY_IF_NEEDED_MSG, enable ? 1 : 0, 0, r)); 3081 } 3082 3083 final void showAskCompatModeDialogLocked(ActivityRecord r) { 3084 Message msg = Message.obtain(); 3085 msg.what = SHOW_COMPAT_MODE_DIALOG_UI_MSG; 3086 msg.obj = r.task.askedCompatMode ? null : r; 3087 mUiHandler.sendMessage(msg); 3088 } 3089 3090 private int updateLruProcessInternalLocked(ProcessRecord app, long now, int index, 3091 String what, Object obj, ProcessRecord srcApp) { 3092 app.lastActivityTime = now; 3093 3094 if (app.activities.size() > 0) { 3095 // Don't want to touch dependent processes that are hosting activities. 3096 return index; 3097 } 3098 3099 int lrui = mLruProcesses.lastIndexOf(app); 3100 if (lrui < 0) { 3101 Slog.wtf(TAG, "Adding dependent process " + app + " not on LRU list: " 3102 + what + " " + obj + " from " + srcApp); 3103 return index; 3104 } 3105 3106 if (lrui >= index) { 3107 // Don't want to cause this to move dependent processes *back* in the 3108 // list as if they were less frequently used. 3109 return index; 3110 } 3111 3112 if (lrui >= mLruProcessActivityStart) { 3113 // Don't want to touch dependent processes that are hosting activities. 3114 return index; 3115 } 3116 3117 mLruProcesses.remove(lrui); 3118 if (index > 0) { 3119 index--; 3120 } 3121 if (DEBUG_LRU) Slog.d(TAG_LRU, "Moving dep from " + lrui + " to " + index 3122 + " in LRU list: " + app); 3123 mLruProcesses.add(index, app); 3124 return index; 3125 } 3126 3127 static void killProcessGroup(int uid, int pid) { 3128 if (sKillHandler != null) { 3129 sKillHandler.sendMessage( 3130 sKillHandler.obtainMessage(KillHandler.KILL_PROCESS_GROUP_MSG, uid, pid)); 3131 } else { 3132 Slog.w(TAG, "Asked to kill process group before system bringup!"); 3133 Process.killProcessGroup(uid, pid); 3134 } 3135 } 3136 3137 final void removeLruProcessLocked(ProcessRecord app) { 3138 int lrui = mLruProcesses.lastIndexOf(app); 3139 if (lrui >= 0) { 3140 if (!app.killed) { 3141 Slog.wtfStack(TAG, "Removing process that hasn't been killed: " + app); 3142 Process.killProcessQuiet(app.pid); 3143 killProcessGroup(app.uid, app.pid); 3144 } 3145 if (lrui <= mLruProcessActivityStart) { 3146 mLruProcessActivityStart--; 3147 } 3148 if (lrui <= mLruProcessServiceStart) { 3149 mLruProcessServiceStart--; 3150 } 3151 mLruProcesses.remove(lrui); 3152 } 3153 } 3154 3155 final void updateLruProcessLocked(ProcessRecord app, boolean activityChange, 3156 ProcessRecord client) { 3157 final boolean hasActivity = app.activities.size() > 0 || app.hasClientActivities 3158 || app.treatLikeActivity; 3159 final boolean hasService = false; // not impl yet. app.services.size() > 0; 3160 if (!activityChange && hasActivity) { 3161 // The process has activities, so we are only allowing activity-based adjustments 3162 // to move it. It should be kept in the front of the list with other 3163 // processes that have activities, and we don't want those to change their 3164 // order except due to activity operations. 3165 return; 3166 } 3167 3168 mLruSeq++; 3169 final long now = SystemClock.uptimeMillis(); 3170 app.lastActivityTime = now; 3171 3172 // First a quick reject: if the app is already at the position we will 3173 // put it, then there is nothing to do. 3174 if (hasActivity) { 3175 final int N = mLruProcesses.size(); 3176 if (N > 0 && mLruProcesses.get(N-1) == app) { 3177 if (DEBUG_LRU) Slog.d(TAG_LRU, "Not moving, already top activity: " + app); 3178 return; 3179 } 3180 } else { 3181 if (mLruProcessServiceStart > 0 3182 && mLruProcesses.get(mLruProcessServiceStart-1) == app) { 3183 if (DEBUG_LRU) Slog.d(TAG_LRU, "Not moving, already top other: " + app); 3184 return; 3185 } 3186 } 3187 3188 int lrui = mLruProcesses.lastIndexOf(app); 3189 3190 if (app.persistent && lrui >= 0) { 3191 // We don't care about the position of persistent processes, as long as 3192 // they are in the list. 3193 if (DEBUG_LRU) Slog.d(TAG_LRU, "Not moving, persistent: " + app); 3194 return; 3195 } 3196 3197 /* In progress: compute new position first, so we can avoid doing work 3198 if the process is not actually going to move. Not yet working. 3199 int addIndex; 3200 int nextIndex; 3201 boolean inActivity = false, inService = false; 3202 if (hasActivity) { 3203 // Process has activities, put it at the very tipsy-top. 3204 addIndex = mLruProcesses.size(); 3205 nextIndex = mLruProcessServiceStart; 3206 inActivity = true; 3207 } else if (hasService) { 3208 // Process has services, put it at the top of the service list. 3209 addIndex = mLruProcessActivityStart; 3210 nextIndex = mLruProcessServiceStart; 3211 inActivity = true; 3212 inService = true; 3213 } else { 3214 // Process not otherwise of interest, it goes to the top of the non-service area. 3215 addIndex = mLruProcessServiceStart; 3216 if (client != null) { 3217 int clientIndex = mLruProcesses.lastIndexOf(client); 3218 if (clientIndex < 0) Slog.d(TAG, "Unknown client " + client + " when updating " 3219 + app); 3220 if (clientIndex >= 0 && addIndex > clientIndex) { 3221 addIndex = clientIndex; 3222 } 3223 } 3224 nextIndex = addIndex > 0 ? addIndex-1 : addIndex; 3225 } 3226 3227 Slog.d(TAG, "Update LRU at " + lrui + " to " + addIndex + " (act=" 3228 + mLruProcessActivityStart + "): " + app); 3229 */ 3230 3231 if (lrui >= 0) { 3232 if (lrui < mLruProcessActivityStart) { 3233 mLruProcessActivityStart--; 3234 } 3235 if (lrui < mLruProcessServiceStart) { 3236 mLruProcessServiceStart--; 3237 } 3238 /* 3239 if (addIndex > lrui) { 3240 addIndex--; 3241 } 3242 if (nextIndex > lrui) { 3243 nextIndex--; 3244 } 3245 */ 3246 mLruProcesses.remove(lrui); 3247 } 3248 3249 /* 3250 mLruProcesses.add(addIndex, app); 3251 if (inActivity) { 3252 mLruProcessActivityStart++; 3253 } 3254 if (inService) { 3255 mLruProcessActivityStart++; 3256 } 3257 */ 3258 3259 int nextIndex; 3260 if (hasActivity) { 3261 final int N = mLruProcesses.size(); 3262 if (app.activities.size() == 0 && mLruProcessActivityStart < (N - 1)) { 3263 // Process doesn't have activities, but has clients with 3264 // activities... move it up, but one below the top (the top 3265 // should always have a real activity). 3266 if (DEBUG_LRU) Slog.d(TAG_LRU, 3267 "Adding to second-top of LRU activity list: " + app); 3268 mLruProcesses.add(N - 1, app); 3269 // To keep it from spamming the LRU list (by making a bunch of clients), 3270 // we will push down any other entries owned by the app. 3271 final int uid = app.info.uid; 3272 for (int i = N - 2; i > mLruProcessActivityStart; i--) { 3273 ProcessRecord subProc = mLruProcesses.get(i); 3274 if (subProc.info.uid == uid) { 3275 // We want to push this one down the list. If the process after 3276 // it is for the same uid, however, don't do so, because we don't 3277 // want them internally to be re-ordered. 3278 if (mLruProcesses.get(i - 1).info.uid != uid) { 3279 if (DEBUG_LRU) Slog.d(TAG_LRU, 3280 "Pushing uid " + uid + " swapping at " + i + ": " 3281 + mLruProcesses.get(i) + " : " + mLruProcesses.get(i - 1)); 3282 ProcessRecord tmp = mLruProcesses.get(i); 3283 mLruProcesses.set(i, mLruProcesses.get(i - 1)); 3284 mLruProcesses.set(i - 1, tmp); 3285 i--; 3286 } 3287 } else { 3288 // A gap, we can stop here. 3289 break; 3290 } 3291 } 3292 } else { 3293 // Process has activities, put it at the very tipsy-top. 3294 if (DEBUG_LRU) Slog.d(TAG_LRU, "Adding to top of LRU activity list: " + app); 3295 mLruProcesses.add(app); 3296 } 3297 nextIndex = mLruProcessServiceStart; 3298 } else if (hasService) { 3299 // Process has services, put it at the top of the service list. 3300 if (DEBUG_LRU) Slog.d(TAG_LRU, "Adding to top of LRU service list: " + app); 3301 mLruProcesses.add(mLruProcessActivityStart, app); 3302 nextIndex = mLruProcessServiceStart; 3303 mLruProcessActivityStart++; 3304 } else { 3305 // Process not otherwise of interest, it goes to the top of the non-service area. 3306 int index = mLruProcessServiceStart; 3307 if (client != null) { 3308 // If there is a client, don't allow the process to be moved up higher 3309 // in the list than that client. 3310 int clientIndex = mLruProcesses.lastIndexOf(client); 3311 if (DEBUG_LRU && clientIndex < 0) Slog.d(TAG_LRU, "Unknown client " + client 3312 + " when updating " + app); 3313 if (clientIndex <= lrui) { 3314 // Don't allow the client index restriction to push it down farther in the 3315 // list than it already is. 3316 clientIndex = lrui; 3317 } 3318 if (clientIndex >= 0 && index > clientIndex) { 3319 index = clientIndex; 3320 } 3321 } 3322 if (DEBUG_LRU) Slog.d(TAG_LRU, "Adding at " + index + " of LRU list: " + app); 3323 mLruProcesses.add(index, app); 3324 nextIndex = index-1; 3325 mLruProcessActivityStart++; 3326 mLruProcessServiceStart++; 3327 } 3328 3329 // If the app is currently using a content provider or service, 3330 // bump those processes as well. 3331 for (int j=app.connections.size()-1; j>=0; j--) { 3332 ConnectionRecord cr = app.connections.valueAt(j); 3333 if (cr.binding != null && !cr.serviceDead && cr.binding.service != null 3334 && cr.binding.service.app != null 3335 && cr.binding.service.app.lruSeq != mLruSeq 3336 && !cr.binding.service.app.persistent) { 3337 nextIndex = updateLruProcessInternalLocked(cr.binding.service.app, now, nextIndex, 3338 "service connection", cr, app); 3339 } 3340 } 3341 for (int j=app.conProviders.size()-1; j>=0; j--) { 3342 ContentProviderRecord cpr = app.conProviders.get(j).provider; 3343 if (cpr.proc != null && cpr.proc.lruSeq != mLruSeq && !cpr.proc.persistent) { 3344 nextIndex = updateLruProcessInternalLocked(cpr.proc, now, nextIndex, 3345 "provider reference", cpr, app); 3346 } 3347 } 3348 } 3349 3350 final ProcessRecord getProcessRecordLocked(String processName, int uid, boolean keepIfLarge) { 3351 if (uid == Process.SYSTEM_UID) { 3352 // The system gets to run in any process. If there are multiple 3353 // processes with the same uid, just pick the first (this 3354 // should never happen). 3355 SparseArray<ProcessRecord> procs = mProcessNames.getMap().get(processName); 3356 if (procs == null) return null; 3357 final int procCount = procs.size(); 3358 for (int i = 0; i < procCount; i++) { 3359 final int procUid = procs.keyAt(i); 3360 if (UserHandle.isApp(procUid) || !UserHandle.isSameUser(procUid, uid)) { 3361 // Don't use an app process or different user process for system component. 3362 continue; 3363 } 3364 return procs.valueAt(i); 3365 } 3366 } 3367 ProcessRecord proc = mProcessNames.get(processName, uid); 3368 if (false && proc != null && !keepIfLarge 3369 && proc.setProcState >= ActivityManager.PROCESS_STATE_CACHED_EMPTY 3370 && proc.lastCachedPss >= 4000) { 3371 // Turn this condition on to cause killing to happen regularly, for testing. 3372 if (proc.baseProcessTracker != null) { 3373 proc.baseProcessTracker.reportCachedKill(proc.pkgList, proc.lastCachedPss); 3374 } 3375 proc.kill(Long.toString(proc.lastCachedPss) + "k from cached", true); 3376 } else if (proc != null && !keepIfLarge 3377 && mLastMemoryLevel > ProcessStats.ADJ_MEM_FACTOR_NORMAL 3378 && proc.setProcState >= ActivityManager.PROCESS_STATE_CACHED_EMPTY) { 3379 if (DEBUG_PSS) Slog.d(TAG_PSS, "May not keep " + proc + ": pss=" + proc.lastCachedPss); 3380 if (proc.lastCachedPss >= mProcessList.getCachedRestoreThresholdKb()) { 3381 if (proc.baseProcessTracker != null) { 3382 proc.baseProcessTracker.reportCachedKill(proc.pkgList, proc.lastCachedPss); 3383 } 3384 proc.kill(Long.toString(proc.lastCachedPss) + "k from cached", true); 3385 } 3386 } 3387 return proc; 3388 } 3389 3390 void notifyPackageUse(String packageName, int reason) { 3391 IPackageManager pm = AppGlobals.getPackageManager(); 3392 try { 3393 pm.notifyPackageUse(packageName, reason); 3394 } catch (RemoteException e) { 3395 } 3396 } 3397 3398 boolean isNextTransitionForward() { 3399 int transit = mWindowManager.getPendingAppTransition(); 3400 return transit == TRANSIT_ACTIVITY_OPEN 3401 || transit == TRANSIT_TASK_OPEN 3402 || transit == TRANSIT_TASK_TO_FRONT; 3403 } 3404 3405 int startIsolatedProcess(String entryPoint, String[] entryPointArgs, 3406 String processName, String abiOverride, int uid, Runnable crashHandler) { 3407 synchronized(this) { 3408 ApplicationInfo info = new ApplicationInfo(); 3409 // In general the ApplicationInfo.uid isn't neccesarily equal to ProcessRecord.uid. 3410 // For isolated processes, the former contains the parent's uid and the latter the 3411 // actual uid of the isolated process. 3412 // In the special case introduced by this method (which is, starting an isolated 3413 // process directly from the SystemServer without an actual parent app process) the 3414 // closest thing to a parent's uid is SYSTEM_UID. 3415 // The only important thing here is to keep AI.uid != PR.uid, in order to trigger 3416 // the |isolated| logic in the ProcessRecord constructor. 3417 info.uid = Process.SYSTEM_UID; 3418 info.processName = processName; 3419 info.className = entryPoint; 3420 info.packageName = "android"; 3421 ProcessRecord proc = startProcessLocked(processName, info /* info */, 3422 false /* knownToBeDead */, 0 /* intentFlags */, "" /* hostingType */, 3423 null /* hostingName */, true /* allowWhileBooting */, true /* isolated */, 3424 uid, true /* keepIfLarge */, abiOverride, entryPoint, entryPointArgs, 3425 crashHandler); 3426 return proc != null ? proc.pid : 0; 3427 } 3428 } 3429 3430 final ProcessRecord startProcessLocked(String processName, 3431 ApplicationInfo info, boolean knownToBeDead, int intentFlags, 3432 String hostingType, ComponentName hostingName, boolean allowWhileBooting, 3433 boolean isolated, boolean keepIfLarge) { 3434 return startProcessLocked(processName, info, knownToBeDead, intentFlags, hostingType, 3435 hostingName, allowWhileBooting, isolated, 0 /* isolatedUid */, keepIfLarge, 3436 null /* ABI override */, null /* entryPoint */, null /* entryPointArgs */, 3437 null /* crashHandler */); 3438 } 3439 3440 final ProcessRecord startProcessLocked(String processName, ApplicationInfo info, 3441 boolean knownToBeDead, int intentFlags, String hostingType, ComponentName hostingName, 3442 boolean allowWhileBooting, boolean isolated, int isolatedUid, boolean keepIfLarge, 3443 String abiOverride, String entryPoint, String[] entryPointArgs, Runnable crashHandler) { 3444 long startTime = SystemClock.elapsedRealtime(); 3445 ProcessRecord app; 3446 if (!isolated) { 3447 app = getProcessRecordLocked(processName, info.uid, keepIfLarge); 3448 checkTime(startTime, "startProcess: after getProcessRecord"); 3449 3450 if ((intentFlags & Intent.FLAG_FROM_BACKGROUND) != 0) { 3451 // If we are in the background, then check to see if this process 3452 // is bad. If so, we will just silently fail. 3453 if (mAppErrors.isBadProcessLocked(info)) { 3454 if (DEBUG_PROCESSES) Slog.v(TAG, "Bad process: " + info.uid 3455 + "/" + info.processName); 3456 return null; 3457 } 3458 } else { 3459 // When the user is explicitly starting a process, then clear its 3460 // crash count so that we won't make it bad until they see at 3461 // least one crash dialog again, and make the process good again 3462 // if it had been bad. 3463 if (DEBUG_PROCESSES) Slog.v(TAG, "Clearing bad process: " + info.uid 3464 + "/" + info.processName); 3465 mAppErrors.resetProcessCrashTimeLocked(info); 3466 if (mAppErrors.isBadProcessLocked(info)) { 3467 EventLog.writeEvent(EventLogTags.AM_PROC_GOOD, 3468 UserHandle.getUserId(info.uid), info.uid, 3469 info.processName); 3470 mAppErrors.clearBadProcessLocked(info); 3471 if (app != null) { 3472 app.bad = false; 3473 } 3474 } 3475 } 3476 } else { 3477 // If this is an isolated process, it can't re-use an existing process. 3478 app = null; 3479 } 3480 3481 // app launch boost for big.little configurations 3482 // use cpusets to migrate freshly launched tasks to big cores 3483 synchronized(ActivityManagerService.this) { 3484 nativeMigrateToBoost(); 3485 mIsBoosted = true; 3486 mBoostStartTime = SystemClock.uptimeMillis(); 3487 Message msg = mHandler.obtainMessage(APP_BOOST_DEACTIVATE_MSG); 3488 mHandler.sendMessageDelayed(msg, APP_BOOST_MESSAGE_DELAY); 3489 } 3490 3491 // We don't have to do anything more if: 3492 // (1) There is an existing application record; and 3493 // (2) The caller doesn't think it is dead, OR there is no thread 3494 // object attached to it so we know it couldn't have crashed; and 3495 // (3) There is a pid assigned to it, so it is either starting or 3496 // already running. 3497 if (DEBUG_PROCESSES) Slog.v(TAG_PROCESSES, "startProcess: name=" + processName 3498 + " app=" + app + " knownToBeDead=" + knownToBeDead 3499 + " thread=" + (app != null ? app.thread : null) 3500 + " pid=" + (app != null ? app.pid : -1)); 3501 if (app != null && app.pid > 0) { 3502 if (!knownToBeDead || app.thread == null) { 3503 // We already have the app running, or are waiting for it to 3504 // come up (we have a pid but not yet its thread), so keep it. 3505 if (DEBUG_PROCESSES) Slog.v(TAG_PROCESSES, "App already running: " + app); 3506 // If this is a new package in the process, add the package to the list 3507 app.addPackage(info.packageName, info.versionCode, mProcessStats); 3508 checkTime(startTime, "startProcess: done, added package to proc"); 3509 return app; 3510 } 3511 3512 // An application record is attached to a previous process, 3513 // clean it up now. 3514 if (DEBUG_PROCESSES || DEBUG_CLEANUP) Slog.v(TAG_PROCESSES, "App died: " + app); 3515 checkTime(startTime, "startProcess: bad proc running, killing"); 3516 killProcessGroup(app.uid, app.pid); 3517 handleAppDiedLocked(app, true, true); 3518 checkTime(startTime, "startProcess: done killing old proc"); 3519 } 3520 3521 String hostingNameStr = hostingName != null 3522 ? hostingName.flattenToShortString() : null; 3523 3524 if (app == null) { 3525 checkTime(startTime, "startProcess: creating new process record"); 3526 app = newProcessRecordLocked(info, processName, isolated, isolatedUid); 3527 if (app == null) { 3528 Slog.w(TAG, "Failed making new process record for " 3529 + processName + "/" + info.uid + " isolated=" + isolated); 3530 return null; 3531 } 3532 app.crashHandler = crashHandler; 3533 checkTime(startTime, "startProcess: done creating new process record"); 3534 } else { 3535 // If this is a new package in the process, add the package to the list 3536 app.addPackage(info.packageName, info.versionCode, mProcessStats); 3537 checkTime(startTime, "startProcess: added package to existing proc"); 3538 } 3539 3540 // If the system is not ready yet, then hold off on starting this 3541 // process until it is. 3542 if (!mProcessesReady 3543 && !isAllowedWhileBooting(info) 3544 && !allowWhileBooting) { 3545 if (!mProcessesOnHold.contains(app)) { 3546 mProcessesOnHold.add(app); 3547 } 3548 if (DEBUG_PROCESSES) Slog.v(TAG_PROCESSES, 3549 "System not ready, putting on hold: " + app); 3550 checkTime(startTime, "startProcess: returning with proc on hold"); 3551 return app; 3552 } 3553 3554 checkTime(startTime, "startProcess: stepping in to startProcess"); 3555 startProcessLocked( 3556 app, hostingType, hostingNameStr, abiOverride, entryPoint, entryPointArgs); 3557 checkTime(startTime, "startProcess: done starting proc!"); 3558 return (app.pid != 0) ? app : null; 3559 } 3560 3561 boolean isAllowedWhileBooting(ApplicationInfo ai) { 3562 return (ai.flags&ApplicationInfo.FLAG_PERSISTENT) != 0; 3563 } 3564 3565 private final void startProcessLocked(ProcessRecord app, 3566 String hostingType, String hostingNameStr) { 3567 startProcessLocked(app, hostingType, hostingNameStr, null /* abiOverride */, 3568 null /* entryPoint */, null /* entryPointArgs */); 3569 } 3570 3571 private final void startProcessLocked(ProcessRecord app, String hostingType, 3572 String hostingNameStr, String abiOverride, String entryPoint, String[] entryPointArgs) { 3573 long startTime = SystemClock.elapsedRealtime(); 3574 if (app.pid > 0 && app.pid != MY_PID) { 3575 checkTime(startTime, "startProcess: removing from pids map"); 3576 synchronized (mPidsSelfLocked) { 3577 mPidsSelfLocked.remove(app.pid); 3578 mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app); 3579 } 3580 checkTime(startTime, "startProcess: done removing from pids map"); 3581 app.setPid(0); 3582 } 3583 3584 if (DEBUG_PROCESSES && mProcessesOnHold.contains(app)) Slog.v(TAG_PROCESSES, 3585 "startProcessLocked removing on hold: " + app); 3586 mProcessesOnHold.remove(app); 3587 3588 checkTime(startTime, "startProcess: starting to update cpu stats"); 3589 updateCpuStats(); 3590 checkTime(startTime, "startProcess: done updating cpu stats"); 3591 3592 try { 3593 try { 3594 final int userId = UserHandle.getUserId(app.uid); 3595 AppGlobals.getPackageManager().checkPackageStartable(app.info.packageName, userId); 3596 } catch (RemoteException e) { 3597 throw e.rethrowAsRuntimeException(); 3598 } 3599 3600 int uid = app.uid; 3601 int[] gids = null; 3602 int mountExternal = Zygote.MOUNT_EXTERNAL_NONE; 3603 if (!app.isolated) { 3604 int[] permGids = null; 3605 try { 3606 checkTime(startTime, "startProcess: getting gids from package manager"); 3607 final IPackageManager pm = AppGlobals.getPackageManager(); 3608 permGids = pm.getPackageGids(app.info.packageName, 3609 MATCH_DEBUG_TRIAGED_MISSING, app.userId); 3610 MountServiceInternal mountServiceInternal = LocalServices.getService( 3611 MountServiceInternal.class); 3612 mountExternal = mountServiceInternal.getExternalStorageMountMode(uid, 3613 app.info.packageName); 3614 } catch (RemoteException e) { 3615 throw e.rethrowAsRuntimeException(); 3616 } 3617 3618 /* 3619 * Add shared application and profile GIDs so applications can share some 3620 * resources like shared libraries and access user-wide resources 3621 */ 3622 if (ArrayUtils.isEmpty(permGids)) { 3623 gids = new int[2]; 3624 } else { 3625 gids = new int[permGids.length + 2]; 3626 System.arraycopy(permGids, 0, gids, 2, permGids.length); 3627 } 3628 gids[0] = UserHandle.getSharedAppGid(UserHandle.getAppId(uid)); 3629 gids[1] = UserHandle.getUserGid(UserHandle.getUserId(uid)); 3630 } 3631 checkTime(startTime, "startProcess: building args"); 3632 if (mFactoryTest != FactoryTest.FACTORY_TEST_OFF) { 3633 if (mFactoryTest == FactoryTest.FACTORY_TEST_LOW_LEVEL 3634 && mTopComponent != null 3635 && app.processName.equals(mTopComponent.getPackageName())) { 3636 uid = 0; 3637 } 3638 if (mFactoryTest == FactoryTest.FACTORY_TEST_HIGH_LEVEL 3639 && (app.info.flags&ApplicationInfo.FLAG_FACTORY_TEST) != 0) { 3640 uid = 0; 3641 } 3642 } 3643 int debugFlags = 0; 3644 if ((app.info.flags & ApplicationInfo.FLAG_DEBUGGABLE) != 0) { 3645 debugFlags |= Zygote.DEBUG_ENABLE_DEBUGGER; 3646 // Also turn on CheckJNI for debuggable apps. It's quite 3647 // awkward to turn on otherwise. 3648 debugFlags |= Zygote.DEBUG_ENABLE_CHECKJNI; 3649 } 3650 // Run the app in safe mode if its manifest requests so or the 3651 // system is booted in safe mode. 3652 if ((app.info.flags & ApplicationInfo.FLAG_VM_SAFE_MODE) != 0 || 3653 mSafeMode == true) { 3654 debugFlags |= Zygote.DEBUG_ENABLE_SAFEMODE; 3655 } 3656 if ("1".equals(SystemProperties.get("debug.checkjni"))) { 3657 debugFlags |= Zygote.DEBUG_ENABLE_CHECKJNI; 3658 } 3659 String genDebugInfoProperty = SystemProperties.get("debug.generate-debug-info"); 3660 if ("true".equals(genDebugInfoProperty)) { 3661 debugFlags |= Zygote.DEBUG_GENERATE_DEBUG_INFO; 3662 } 3663 if ("1".equals(SystemProperties.get("debug.jni.logging"))) { 3664 debugFlags |= Zygote.DEBUG_ENABLE_JNI_LOGGING; 3665 } 3666 if ("1".equals(SystemProperties.get("debug.assert"))) { 3667 debugFlags |= Zygote.DEBUG_ENABLE_ASSERT; 3668 } 3669 if (mNativeDebuggingApp != null && mNativeDebuggingApp.equals(app.processName)) { 3670 // Enable all debug flags required by the native debugger. 3671 debugFlags |= Zygote.DEBUG_ALWAYS_JIT; // Don't interpret anything 3672 debugFlags |= Zygote.DEBUG_GENERATE_DEBUG_INFO; // Generate debug info 3673 debugFlags |= Zygote.DEBUG_NATIVE_DEBUGGABLE; // Disbale optimizations 3674 mNativeDebuggingApp = null; 3675 } 3676 3677 String requiredAbi = (abiOverride != null) ? abiOverride : app.info.primaryCpuAbi; 3678 if (requiredAbi == null) { 3679 requiredAbi = Build.SUPPORTED_ABIS[0]; 3680 } 3681 3682 String instructionSet = null; 3683 if (app.info.primaryCpuAbi != null) { 3684 instructionSet = VMRuntime.getInstructionSet(app.info.primaryCpuAbi); 3685 } 3686 3687 app.gids = gids; 3688 app.requiredAbi = requiredAbi; 3689 app.instructionSet = instructionSet; 3690 3691 // Start the process. It will either succeed and return a result containing 3692 // the PID of the new process, or else throw a RuntimeException. 3693 boolean isActivityProcess = (entryPoint == null); 3694 if (entryPoint == null) entryPoint = "android.app.ActivityThread"; 3695 Trace.traceBegin(Trace.TRACE_TAG_ACTIVITY_MANAGER, "Start proc: " + 3696 app.processName); 3697 checkTime(startTime, "startProcess: asking zygote to start proc"); 3698 Process.ProcessStartResult startResult = Process.start(entryPoint, 3699 app.processName, uid, uid, gids, debugFlags, mountExternal, 3700 app.info.targetSdkVersion, app.info.seinfo, requiredAbi, instructionSet, 3701 app.info.dataDir, entryPointArgs); 3702 checkTime(startTime, "startProcess: returned from zygote!"); 3703 Trace.traceEnd(Trace.TRACE_TAG_ACTIVITY_MANAGER); 3704 3705 if (app.isolated) { 3706 mBatteryStatsService.addIsolatedUid(app.uid, app.info.uid); 3707 } 3708 mBatteryStatsService.noteProcessStart(app.processName, app.info.uid); 3709 checkTime(startTime, "startProcess: done updating battery stats"); 3710 3711 EventLog.writeEvent(EventLogTags.AM_PROC_START, 3712 UserHandle.getUserId(uid), startResult.pid, uid, 3713 app.processName, hostingType, 3714 hostingNameStr != null ? hostingNameStr : ""); 3715 3716 try { 3717 AppGlobals.getPackageManager().logAppProcessStartIfNeeded(app.processName, app.uid, 3718 app.info.seinfo, app.info.sourceDir, startResult.pid); 3719 } catch (RemoteException ex) { 3720 // Ignore 3721 } 3722 3723 if (app.persistent) { 3724 Watchdog.getInstance().processStarted(app.processName, startResult.pid); 3725 } 3726 3727 checkTime(startTime, "startProcess: building log message"); 3728 StringBuilder buf = mStringBuilder; 3729 buf.setLength(0); 3730 buf.append("Start proc "); 3731 buf.append(startResult.pid); 3732 buf.append(':'); 3733 buf.append(app.processName); 3734 buf.append('/'); 3735 UserHandle.formatUid(buf, uid); 3736 if (!isActivityProcess) { 3737 buf.append(" ["); 3738 buf.append(entryPoint); 3739 buf.append("]"); 3740 } 3741 buf.append(" for "); 3742 buf.append(hostingType); 3743 if (hostingNameStr != null) { 3744 buf.append(" "); 3745 buf.append(hostingNameStr); 3746 } 3747 Slog.i(TAG, buf.toString()); 3748 app.setPid(startResult.pid); 3749 app.usingWrapper = startResult.usingWrapper; 3750 app.removed = false; 3751 app.killed = false; 3752 app.killedByAm = false; 3753 checkTime(startTime, "startProcess: starting to update pids map"); 3754 synchronized (mPidsSelfLocked) { 3755 this.mPidsSelfLocked.put(startResult.pid, app); 3756 if (isActivityProcess) { 3757 Message msg = mHandler.obtainMessage(PROC_START_TIMEOUT_MSG); 3758 msg.obj = app; 3759 mHandler.sendMessageDelayed(msg, startResult.usingWrapper 3760 ? PROC_START_TIMEOUT_WITH_WRAPPER : PROC_START_TIMEOUT); 3761 } 3762 } 3763 checkTime(startTime, "startProcess: done updating pids map"); 3764 } catch (RuntimeException e) { 3765 Slog.e(TAG, "Failure starting process " + app.processName, e); 3766 3767 // Something went very wrong while trying to start this process; one 3768 // common case is when the package is frozen due to an active 3769 // upgrade. To recover, clean up any active bookkeeping related to 3770 // starting this process. (We already invoked this method once when 3771 // the package was initially frozen through KILL_APPLICATION_MSG, so 3772 // it doesn't hurt to use it again.) 3773 forceStopPackageLocked(app.info.packageName, UserHandle.getAppId(app.uid), false, 3774 false, true, false, false, UserHandle.getUserId(app.userId), "start failure"); 3775 } 3776 } 3777 3778 void updateUsageStats(ActivityRecord component, boolean resumed) { 3779 if (DEBUG_SWITCH) Slog.d(TAG_SWITCH, 3780 "updateUsageStats: comp=" + component + "res=" + resumed); 3781 final BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 3782 if (resumed) { 3783 if (mUsageStatsService != null) { 3784 mUsageStatsService.reportEvent(component.realActivity, component.userId, 3785 UsageEvents.Event.MOVE_TO_FOREGROUND); 3786 } 3787 synchronized (stats) { 3788 stats.noteActivityResumedLocked(component.app.uid); 3789 } 3790 } else { 3791 if (mUsageStatsService != null) { 3792 mUsageStatsService.reportEvent(component.realActivity, component.userId, 3793 UsageEvents.Event.MOVE_TO_BACKGROUND); 3794 } 3795 synchronized (stats) { 3796 stats.noteActivityPausedLocked(component.app.uid); 3797 } 3798 } 3799 } 3800 3801 Intent getHomeIntent() { 3802 Intent intent = new Intent(mTopAction, mTopData != null ? Uri.parse(mTopData) : null); 3803 intent.setComponent(mTopComponent); 3804 intent.addFlags(Intent.FLAG_DEBUG_TRIAGED_MISSING); 3805 if (mFactoryTest != FactoryTest.FACTORY_TEST_LOW_LEVEL) { 3806 intent.addCategory(Intent.CATEGORY_HOME); 3807 } 3808 return intent; 3809 } 3810 3811 boolean startHomeActivityLocked(int userId, String reason) { 3812 if (mFactoryTest == FactoryTest.FACTORY_TEST_LOW_LEVEL 3813 && mTopAction == null) { 3814 // We are running in factory test mode, but unable to find 3815 // the factory test app, so just sit around displaying the 3816 // error message and don't try to start anything. 3817 return false; 3818 } 3819 Intent intent = getHomeIntent(); 3820 ActivityInfo aInfo = resolveActivityInfo(intent, STOCK_PM_FLAGS, userId); 3821 if (aInfo != null) { 3822 intent.setComponent(new ComponentName(aInfo.applicationInfo.packageName, aInfo.name)); 3823 // Don't do this if the home app is currently being 3824 // instrumented. 3825 aInfo = new ActivityInfo(aInfo); 3826 aInfo.applicationInfo = getAppInfoForUser(aInfo.applicationInfo, userId); 3827 ProcessRecord app = getProcessRecordLocked(aInfo.processName, 3828 aInfo.applicationInfo.uid, true); 3829 if (app == null || app.instrumentationClass == null) { 3830 intent.setFlags(intent.getFlags() | Intent.FLAG_ACTIVITY_NEW_TASK); 3831 mActivityStarter.startHomeActivityLocked(intent, aInfo, reason); 3832 } 3833 } else { 3834 Slog.wtf(TAG, "No home screen found for " + intent, new Throwable()); 3835 } 3836 3837 return true; 3838 } 3839 3840 private ActivityInfo resolveActivityInfo(Intent intent, int flags, int userId) { 3841 ActivityInfo ai = null; 3842 ComponentName comp = intent.getComponent(); 3843 try { 3844 if (comp != null) { 3845 // Factory test. 3846 ai = AppGlobals.getPackageManager().getActivityInfo(comp, flags, userId); 3847 } else { 3848 ResolveInfo info = AppGlobals.getPackageManager().resolveIntent( 3849 intent, 3850 intent.resolveTypeIfNeeded(mContext.getContentResolver()), 3851 flags, userId); 3852 3853 if (info != null) { 3854 ai = info.activityInfo; 3855 } 3856 } 3857 } catch (RemoteException e) { 3858 // ignore 3859 } 3860 3861 return ai; 3862 } 3863 3864 /** 3865 * Starts the "new version setup screen" if appropriate. 3866 */ 3867 void startSetupActivityLocked() { 3868 // Only do this once per boot. 3869 if (mCheckedForSetup) { 3870 return; 3871 } 3872 3873 // We will show this screen if the current one is a different 3874 // version than the last one shown, and we are not running in 3875 // low-level factory test mode. 3876 final ContentResolver resolver = mContext.getContentResolver(); 3877 if (mFactoryTest != FactoryTest.FACTORY_TEST_LOW_LEVEL && 3878 Settings.Global.getInt(resolver, 3879 Settings.Global.DEVICE_PROVISIONED, 0) != 0) { 3880 mCheckedForSetup = true; 3881 3882 // See if we should be showing the platform update setup UI. 3883 final Intent intent = new Intent(Intent.ACTION_UPGRADE_SETUP); 3884 final List<ResolveInfo> ris = mContext.getPackageManager().queryIntentActivities(intent, 3885 PackageManager.MATCH_SYSTEM_ONLY | PackageManager.GET_META_DATA); 3886 if (!ris.isEmpty()) { 3887 final ResolveInfo ri = ris.get(0); 3888 String vers = ri.activityInfo.metaData != null 3889 ? ri.activityInfo.metaData.getString(Intent.METADATA_SETUP_VERSION) 3890 : null; 3891 if (vers == null && ri.activityInfo.applicationInfo.metaData != null) { 3892 vers = ri.activityInfo.applicationInfo.metaData.getString( 3893 Intent.METADATA_SETUP_VERSION); 3894 } 3895 String lastVers = Settings.Secure.getString( 3896 resolver, Settings.Secure.LAST_SETUP_SHOWN); 3897 if (vers != null && !vers.equals(lastVers)) { 3898 intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK); 3899 intent.setComponent(new ComponentName( 3900 ri.activityInfo.packageName, ri.activityInfo.name)); 3901 mActivityStarter.startActivityLocked(null, intent, null /*ephemeralIntent*/, 3902 null, ri.activityInfo, null /*rInfo*/, null, null, null, null, 0, 0, 0, 3903 null, 0, 0, 0, null, false, false, null, null, null); 3904 } 3905 } 3906 } 3907 } 3908 3909 CompatibilityInfo compatibilityInfoForPackageLocked(ApplicationInfo ai) { 3910 return mCompatModePackages.compatibilityInfoForPackageLocked(ai); 3911 } 3912 3913 void enforceNotIsolatedCaller(String caller) { 3914 if (UserHandle.isIsolated(Binder.getCallingUid())) { 3915 throw new SecurityException("Isolated process not allowed to call " + caller); 3916 } 3917 } 3918 3919 void enforceShellRestriction(String restriction, int userHandle) { 3920 if (Binder.getCallingUid() == Process.SHELL_UID) { 3921 if (userHandle < 0 || mUserController.hasUserRestriction(restriction, userHandle)) { 3922 throw new SecurityException("Shell does not have permission to access user " 3923 + userHandle); 3924 } 3925 } 3926 } 3927 3928 @Override 3929 public int getFrontActivityScreenCompatMode() { 3930 enforceNotIsolatedCaller("getFrontActivityScreenCompatMode"); 3931 synchronized (this) { 3932 return mCompatModePackages.getFrontActivityScreenCompatModeLocked(); 3933 } 3934 } 3935 3936 @Override 3937 public void setFrontActivityScreenCompatMode(int mode) { 3938 enforceCallingPermission(android.Manifest.permission.SET_SCREEN_COMPATIBILITY, 3939 "setFrontActivityScreenCompatMode"); 3940 synchronized (this) { 3941 mCompatModePackages.setFrontActivityScreenCompatModeLocked(mode); 3942 } 3943 } 3944 3945 @Override 3946 public int getPackageScreenCompatMode(String packageName) { 3947 enforceNotIsolatedCaller("getPackageScreenCompatMode"); 3948 synchronized (this) { 3949 return mCompatModePackages.getPackageScreenCompatModeLocked(packageName); 3950 } 3951 } 3952 3953 @Override 3954 public void setPackageScreenCompatMode(String packageName, int mode) { 3955 enforceCallingPermission(android.Manifest.permission.SET_SCREEN_COMPATIBILITY, 3956 "setPackageScreenCompatMode"); 3957 synchronized (this) { 3958 mCompatModePackages.setPackageScreenCompatModeLocked(packageName, mode); 3959 } 3960 } 3961 3962 @Override 3963 public boolean getPackageAskScreenCompat(String packageName) { 3964 enforceNotIsolatedCaller("getPackageAskScreenCompat"); 3965 synchronized (this) { 3966 return mCompatModePackages.getPackageAskCompatModeLocked(packageName); 3967 } 3968 } 3969 3970 @Override 3971 public void setPackageAskScreenCompat(String packageName, boolean ask) { 3972 enforceCallingPermission(android.Manifest.permission.SET_SCREEN_COMPATIBILITY, 3973 "setPackageAskScreenCompat"); 3974 synchronized (this) { 3975 mCompatModePackages.setPackageAskCompatModeLocked(packageName, ask); 3976 } 3977 } 3978 3979 private boolean hasUsageStatsPermission(String callingPackage) { 3980 final int mode = mAppOpsService.checkOperation(AppOpsManager.OP_GET_USAGE_STATS, 3981 Binder.getCallingUid(), callingPackage); 3982 if (mode == AppOpsManager.MODE_DEFAULT) { 3983 return checkCallingPermission(Manifest.permission.PACKAGE_USAGE_STATS) 3984 == PackageManager.PERMISSION_GRANTED; 3985 } 3986 return mode == AppOpsManager.MODE_ALLOWED; 3987 } 3988 3989 @Override 3990 public int getPackageProcessState(String packageName, String callingPackage) { 3991 if (!hasUsageStatsPermission(callingPackage)) { 3992 enforceCallingPermission(android.Manifest.permission.GET_PACKAGE_IMPORTANCE, 3993 "getPackageProcessState"); 3994 } 3995 3996 int procState = ActivityManager.PROCESS_STATE_NONEXISTENT; 3997 synchronized (this) { 3998 for (int i=mLruProcesses.size()-1; i>=0; i--) { 3999 final ProcessRecord proc = mLruProcesses.get(i); 4000 if (procState == ActivityManager.PROCESS_STATE_NONEXISTENT 4001 || procState > proc.setProcState) { 4002 boolean found = false; 4003 for (int j=proc.pkgList.size()-1; j>=0 && !found; j--) { 4004 if (proc.pkgList.keyAt(j).equals(packageName)) { 4005 procState = proc.setProcState; 4006 found = true; 4007 } 4008 } 4009 if (proc.pkgDeps != null && !found) { 4010 for (int j=proc.pkgDeps.size()-1; j>=0; j--) { 4011 if (proc.pkgDeps.valueAt(j).equals(packageName)) { 4012 procState = proc.setProcState; 4013 break; 4014 } 4015 } 4016 } 4017 } 4018 } 4019 } 4020 return procState; 4021 } 4022 4023 @Override 4024 public boolean setProcessMemoryTrimLevel(String process, int userId, int level) { 4025 synchronized (this) { 4026 final ProcessRecord app = findProcessLocked(process, userId, "setProcessMemoryTrimLevel"); 4027 if (app == null) { 4028 return false; 4029 } 4030 if (app.trimMemoryLevel < level && app.thread != null && 4031 (level < ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN || 4032 app.curProcState >= ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND)) { 4033 try { 4034 app.thread.scheduleTrimMemory(level); 4035 app.trimMemoryLevel = level; 4036 return true; 4037 } catch (RemoteException e) { 4038 // Fallthrough to failure case. 4039 } 4040 } 4041 } 4042 return false; 4043 } 4044 4045 private void dispatchProcessesChanged() { 4046 int N; 4047 synchronized (this) { 4048 N = mPendingProcessChanges.size(); 4049 if (mActiveProcessChanges.length < N) { 4050 mActiveProcessChanges = new ProcessChangeItem[N]; 4051 } 4052 mPendingProcessChanges.toArray(mActiveProcessChanges); 4053 mPendingProcessChanges.clear(); 4054 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG_PROCESS_OBSERVERS, 4055 "*** Delivering " + N + " process changes"); 4056 } 4057 4058 int i = mProcessObservers.beginBroadcast(); 4059 while (i > 0) { 4060 i--; 4061 final IProcessObserver observer = mProcessObservers.getBroadcastItem(i); 4062 if (observer != null) { 4063 try { 4064 for (int j=0; j<N; j++) { 4065 ProcessChangeItem item = mActiveProcessChanges[j]; 4066 if ((item.changes&ProcessChangeItem.CHANGE_ACTIVITIES) != 0) { 4067 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG_PROCESS_OBSERVERS, 4068 "ACTIVITIES CHANGED pid=" + item.pid + " uid=" 4069 + item.uid + ": " + item.foregroundActivities); 4070 observer.onForegroundActivitiesChanged(item.pid, item.uid, 4071 item.foregroundActivities); 4072 } 4073 if ((item.changes&ProcessChangeItem.CHANGE_PROCESS_STATE) != 0) { 4074 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG_PROCESS_OBSERVERS, 4075 "PROCSTATE CHANGED pid=" + item.pid + " uid=" + item.uid 4076 + ": " + item.processState); 4077 observer.onProcessStateChanged(item.pid, item.uid, item.processState); 4078 } 4079 } 4080 } catch (RemoteException e) { 4081 } 4082 } 4083 } 4084 mProcessObservers.finishBroadcast(); 4085 4086 synchronized (this) { 4087 for (int j=0; j<N; j++) { 4088 mAvailProcessChanges.add(mActiveProcessChanges[j]); 4089 } 4090 } 4091 } 4092 4093 private void dispatchProcessDied(int pid, int uid) { 4094 int i = mProcessObservers.beginBroadcast(); 4095 while (i > 0) { 4096 i--; 4097 final IProcessObserver observer = mProcessObservers.getBroadcastItem(i); 4098 if (observer != null) { 4099 try { 4100 observer.onProcessDied(pid, uid); 4101 } catch (RemoteException e) { 4102 } 4103 } 4104 } 4105 mProcessObservers.finishBroadcast(); 4106 } 4107 4108 private void dispatchUidsChanged() { 4109 int N; 4110 synchronized (this) { 4111 N = mPendingUidChanges.size(); 4112 if (mActiveUidChanges.length < N) { 4113 mActiveUidChanges = new UidRecord.ChangeItem[N]; 4114 } 4115 for (int i=0; i<N; i++) { 4116 final UidRecord.ChangeItem change = mPendingUidChanges.get(i); 4117 mActiveUidChanges[i] = change; 4118 if (change.uidRecord != null) { 4119 change.uidRecord.pendingChange = null; 4120 change.uidRecord = null; 4121 } 4122 } 4123 mPendingUidChanges.clear(); 4124 if (DEBUG_UID_OBSERVERS) Slog.i(TAG_UID_OBSERVERS, 4125 "*** Delivering " + N + " uid changes"); 4126 } 4127 4128 if (mLocalPowerManager != null) { 4129 for (int j=0; j<N; j++) { 4130 UidRecord.ChangeItem item = mActiveUidChanges[j]; 4131 if (item.change == UidRecord.CHANGE_GONE 4132 || item.change == UidRecord.CHANGE_GONE_IDLE) { 4133 mLocalPowerManager.uidGone(item.uid); 4134 } else { 4135 mLocalPowerManager.updateUidProcState(item.uid, item.processState); 4136 } 4137 } 4138 } 4139 4140 int i = mUidObservers.beginBroadcast(); 4141 while (i > 0) { 4142 i--; 4143 final IUidObserver observer = mUidObservers.getBroadcastItem(i); 4144 final int which = (Integer)mUidObservers.getBroadcastCookie(i); 4145 if (observer != null) { 4146 try { 4147 for (int j=0; j<N; j++) { 4148 UidRecord.ChangeItem item = mActiveUidChanges[j]; 4149 final int change = item.change; 4150 UidRecord validateUid = null; 4151 if (VALIDATE_UID_STATES && i == 0) { 4152 validateUid = mValidateUids.get(item.uid); 4153 if (validateUid == null && change != UidRecord.CHANGE_GONE 4154 && change != UidRecord.CHANGE_GONE_IDLE) { 4155 validateUid = new UidRecord(item.uid); 4156 mValidateUids.put(item.uid, validateUid); 4157 } 4158 } 4159 if (change == UidRecord.CHANGE_IDLE 4160 || change == UidRecord.CHANGE_GONE_IDLE) { 4161 if ((which & ActivityManager.UID_OBSERVER_IDLE) != 0) { 4162 if (DEBUG_UID_OBSERVERS) Slog.i(TAG_UID_OBSERVERS, 4163 "UID idle uid=" + item.uid); 4164 observer.onUidIdle(item.uid); 4165 } 4166 if (VALIDATE_UID_STATES && i == 0) { 4167 if (validateUid != null) { 4168 validateUid.idle = true; 4169 } 4170 } 4171 } else if (change == UidRecord.CHANGE_ACTIVE) { 4172 if ((which & ActivityManager.UID_OBSERVER_ACTIVE) != 0) { 4173 if (DEBUG_UID_OBSERVERS) Slog.i(TAG_UID_OBSERVERS, 4174 "UID active uid=" + item.uid); 4175 observer.onUidActive(item.uid); 4176 } 4177 if (VALIDATE_UID_STATES && i == 0) { 4178 validateUid.idle = false; 4179 } 4180 } 4181 if (change == UidRecord.CHANGE_GONE 4182 || change == UidRecord.CHANGE_GONE_IDLE) { 4183 if ((which & ActivityManager.UID_OBSERVER_GONE) != 0) { 4184 if (DEBUG_UID_OBSERVERS) Slog.i(TAG_UID_OBSERVERS, 4185 "UID gone uid=" + item.uid); 4186 observer.onUidGone(item.uid); 4187 } 4188 if (VALIDATE_UID_STATES && i == 0) { 4189 if (validateUid != null) { 4190 mValidateUids.remove(item.uid); 4191 } 4192 } 4193 } else { 4194 if ((which & ActivityManager.UID_OBSERVER_PROCSTATE) != 0) { 4195 if (DEBUG_UID_OBSERVERS) Slog.i(TAG_UID_OBSERVERS, 4196 "UID CHANGED uid=" + item.uid 4197 + ": " + item.processState); 4198 observer.onUidStateChanged(item.uid, item.processState); 4199 } 4200 if (VALIDATE_UID_STATES && i == 0) { 4201 validateUid.curProcState = validateUid.setProcState 4202 = item.processState; 4203 } 4204 } 4205 } 4206 } catch (RemoteException e) { 4207 } 4208 } 4209 } 4210 mUidObservers.finishBroadcast(); 4211 4212 synchronized (this) { 4213 for (int j=0; j<N; j++) { 4214 mAvailUidChanges.add(mActiveUidChanges[j]); 4215 } 4216 } 4217 } 4218 4219 @Override 4220 public final int startActivity(IApplicationThread caller, String callingPackage, 4221 Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode, 4222 int startFlags, ProfilerInfo profilerInfo, Bundle bOptions) { 4223 return startActivityAsUser(caller, callingPackage, intent, resolvedType, resultTo, 4224 resultWho, requestCode, startFlags, profilerInfo, bOptions, 4225 UserHandle.getCallingUserId()); 4226 } 4227 4228 final int startActivity(Intent intent, ActivityStackSupervisor.ActivityContainer container) { 4229 enforceNotIsolatedCaller("ActivityContainer.startActivity"); 4230 final int userId = mUserController.handleIncomingUser(Binder.getCallingPid(), 4231 Binder.getCallingUid(), mStackSupervisor.mCurrentUser, false, 4232 ActivityManagerService.ALLOW_FULL_ONLY, "ActivityContainer", null); 4233 4234 // TODO: Switch to user app stacks here. 4235 String mimeType = intent.getType(); 4236 final Uri data = intent.getData(); 4237 if (mimeType == null && data != null && "content".equals(data.getScheme())) { 4238 mimeType = getProviderMimeType(data, userId); 4239 } 4240 container.checkEmbeddedAllowedInner(userId, intent, mimeType); 4241 4242 intent.addFlags(FORCE_NEW_TASK_FLAGS); 4243 return mActivityStarter.startActivityMayWait(null, -1, null, intent, mimeType, null, null, null, 4244 null, 0, 0, null, null, null, null, false, userId, container, null); 4245 } 4246 4247 @Override 4248 public final int startActivityAsUser(IApplicationThread caller, String callingPackage, 4249 Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode, 4250 int startFlags, ProfilerInfo profilerInfo, Bundle bOptions, int userId) { 4251 enforceNotIsolatedCaller("startActivity"); 4252 userId = mUserController.handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 4253 userId, false, ALLOW_FULL_ONLY, "startActivity", null); 4254 // TODO: Switch to user app stacks here. 4255 return mActivityStarter.startActivityMayWait(caller, -1, callingPackage, intent, 4256 resolvedType, null, null, resultTo, resultWho, requestCode, startFlags, 4257 profilerInfo, null, null, bOptions, false, userId, null, null); 4258 } 4259 4260 @Override 4261 public final int startActivityAsCaller(IApplicationThread caller, String callingPackage, 4262 Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode, 4263 int startFlags, ProfilerInfo profilerInfo, Bundle bOptions, boolean ignoreTargetSecurity, 4264 int userId) { 4265 4266 // This is very dangerous -- it allows you to perform a start activity (including 4267 // permission grants) as any app that may launch one of your own activities. So 4268 // we will only allow this to be done from activities that are part of the core framework, 4269 // and then only when they are running as the system. 4270 final ActivityRecord sourceRecord; 4271 final int targetUid; 4272 final String targetPackage; 4273 synchronized (this) { 4274 if (resultTo == null) { 4275 throw new SecurityException("Must be called from an activity"); 4276 } 4277 sourceRecord = mStackSupervisor.isInAnyStackLocked(resultTo); 4278 if (sourceRecord == null) { 4279 throw new SecurityException("Called with bad activity token: " + resultTo); 4280 } 4281 if (!sourceRecord.info.packageName.equals("android")) { 4282 throw new SecurityException( 4283 "Must be called from an activity that is declared in the android package"); 4284 } 4285 if (sourceRecord.app == null) { 4286 throw new SecurityException("Called without a process attached to activity"); 4287 } 4288 if (UserHandle.getAppId(sourceRecord.app.uid) != Process.SYSTEM_UID) { 4289 // This is still okay, as long as this activity is running under the 4290 // uid of the original calling activity. 4291 if (sourceRecord.app.uid != sourceRecord.launchedFromUid) { 4292 throw new SecurityException( 4293 "Calling activity in uid " + sourceRecord.app.uid 4294 + " must be system uid or original calling uid " 4295 + sourceRecord.launchedFromUid); 4296 } 4297 } 4298 if (ignoreTargetSecurity) { 4299 if (intent.getComponent() == null) { 4300 throw new SecurityException( 4301 "Component must be specified with ignoreTargetSecurity"); 4302 } 4303 if (intent.getSelector() != null) { 4304 throw new SecurityException( 4305 "Selector not allowed with ignoreTargetSecurity"); 4306 } 4307 } 4308 targetUid = sourceRecord.launchedFromUid; 4309 targetPackage = sourceRecord.launchedFromPackage; 4310 } 4311 4312 if (userId == UserHandle.USER_NULL) { 4313 userId = UserHandle.getUserId(sourceRecord.app.uid); 4314 } 4315 4316 // TODO: Switch to user app stacks here. 4317 try { 4318 int ret = mActivityStarter.startActivityMayWait(null, targetUid, targetPackage, intent, 4319 resolvedType, null, null, resultTo, resultWho, requestCode, startFlags, null, 4320 null, null, bOptions, ignoreTargetSecurity, userId, null, null); 4321 return ret; 4322 } catch (SecurityException e) { 4323 // XXX need to figure out how to propagate to original app. 4324 // A SecurityException here is generally actually a fault of the original 4325 // calling activity (such as a fairly granting permissions), so propagate it 4326 // back to them. 4327 /* 4328 StringBuilder msg = new StringBuilder(); 4329 msg.append("While launching"); 4330 msg.append(intent.toString()); 4331 msg.append(": "); 4332 msg.append(e.getMessage()); 4333 */ 4334 throw e; 4335 } 4336 } 4337 4338 @Override 4339 public final WaitResult startActivityAndWait(IApplicationThread caller, String callingPackage, 4340 Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode, 4341 int startFlags, ProfilerInfo profilerInfo, Bundle bOptions, int userId) { 4342 enforceNotIsolatedCaller("startActivityAndWait"); 4343 userId = mUserController.handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 4344 userId, false, ALLOW_FULL_ONLY, "startActivityAndWait", null); 4345 WaitResult res = new WaitResult(); 4346 // TODO: Switch to user app stacks here. 4347 mActivityStarter.startActivityMayWait(caller, -1, callingPackage, intent, resolvedType, 4348 null, null, resultTo, resultWho, requestCode, startFlags, profilerInfo, res, null, 4349 bOptions, false, userId, null, null); 4350 return res; 4351 } 4352 4353 @Override 4354 public final int startActivityWithConfig(IApplicationThread caller, String callingPackage, 4355 Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode, 4356 int startFlags, Configuration config, Bundle bOptions, int userId) { 4357 enforceNotIsolatedCaller("startActivityWithConfig"); 4358 userId = mUserController.handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 4359 userId, false, ALLOW_FULL_ONLY, "startActivityWithConfig", null); 4360 // TODO: Switch to user app stacks here. 4361 int ret = mActivityStarter.startActivityMayWait(caller, -1, callingPackage, intent, 4362 resolvedType, null, null, resultTo, resultWho, requestCode, startFlags, 4363 null, null, config, bOptions, false, userId, null, null); 4364 return ret; 4365 } 4366 4367 @Override 4368 public int startActivityIntentSender(IApplicationThread caller, IntentSender intent, 4369 Intent fillInIntent, String resolvedType, IBinder resultTo, String resultWho, 4370 int requestCode, int flagsMask, int flagsValues, Bundle bOptions) 4371 throws TransactionTooLargeException { 4372 enforceNotIsolatedCaller("startActivityIntentSender"); 4373 // Refuse possible leaked file descriptors 4374 if (fillInIntent != null && fillInIntent.hasFileDescriptors()) { 4375 throw new IllegalArgumentException("File descriptors passed in Intent"); 4376 } 4377 4378 IIntentSender sender = intent.getTarget(); 4379 if (!(sender instanceof PendingIntentRecord)) { 4380 throw new IllegalArgumentException("Bad PendingIntent object"); 4381 } 4382 4383 PendingIntentRecord pir = (PendingIntentRecord)sender; 4384 4385 synchronized (this) { 4386 // If this is coming from the currently resumed activity, it is 4387 // effectively saying that app switches are allowed at this point. 4388 final ActivityStack stack = getFocusedStack(); 4389 if (stack.mResumedActivity != null && 4390 stack.mResumedActivity.info.applicationInfo.uid == Binder.getCallingUid()) { 4391 mAppSwitchesAllowedTime = 0; 4392 } 4393 } 4394 int ret = pir.sendInner(0, fillInIntent, resolvedType, null, null, 4395 resultTo, resultWho, requestCode, flagsMask, flagsValues, bOptions, null); 4396 return ret; 4397 } 4398 4399 @Override 4400 public int startVoiceActivity(String callingPackage, int callingPid, int callingUid, 4401 Intent intent, String resolvedType, IVoiceInteractionSession session, 4402 IVoiceInteractor interactor, int startFlags, ProfilerInfo profilerInfo, 4403 Bundle bOptions, int userId) { 4404 if (checkCallingPermission(Manifest.permission.BIND_VOICE_INTERACTION) 4405 != PackageManager.PERMISSION_GRANTED) { 4406 String msg = "Permission Denial: startVoiceActivity() from pid=" 4407 + Binder.getCallingPid() 4408 + ", uid=" + Binder.getCallingUid() 4409 + " requires " + android.Manifest.permission.BIND_VOICE_INTERACTION; 4410 Slog.w(TAG, msg); 4411 throw new SecurityException(msg); 4412 } 4413 if (session == null || interactor == null) { 4414 throw new NullPointerException("null session or interactor"); 4415 } 4416 userId = mUserController.handleIncomingUser(callingPid, callingUid, userId, false, 4417 ALLOW_FULL_ONLY, "startVoiceActivity", null); 4418 // TODO: Switch to user app stacks here. 4419 return mActivityStarter.startActivityMayWait(null, callingUid, callingPackage, intent, 4420 resolvedType, session, interactor, null, null, 0, startFlags, profilerInfo, null, 4421 null, bOptions, false, userId, null, null); 4422 } 4423 4424 @Override 4425 public void startLocalVoiceInteraction(IBinder callingActivity, Bundle options) 4426 throws RemoteException { 4427 Slog.i(TAG, "Activity tried to startVoiceInteraction"); 4428 synchronized (this) { 4429 ActivityRecord activity = getFocusedStack().topActivity(); 4430 if (ActivityRecord.forTokenLocked(callingActivity) != activity) { 4431 throw new SecurityException("Only focused activity can call startVoiceInteraction"); 4432 } 4433 if (mRunningVoice != null || activity.task.voiceSession != null 4434 || activity.voiceSession != null) { 4435 Slog.w(TAG, "Already in a voice interaction, cannot start new voice interaction"); 4436 return; 4437 } 4438 if (activity.pendingVoiceInteractionStart) { 4439 Slog.w(TAG, "Pending start of voice interaction already."); 4440 return; 4441 } 4442 activity.pendingVoiceInteractionStart = true; 4443 } 4444 LocalServices.getService(VoiceInteractionManagerInternal.class) 4445 .startLocalVoiceInteraction(callingActivity, options); 4446 } 4447 4448 @Override 4449 public void stopLocalVoiceInteraction(IBinder callingActivity) throws RemoteException { 4450 LocalServices.getService(VoiceInteractionManagerInternal.class) 4451 .stopLocalVoiceInteraction(callingActivity); 4452 } 4453 4454 @Override 4455 public boolean supportsLocalVoiceInteraction() throws RemoteException { 4456 return LocalServices.getService(VoiceInteractionManagerInternal.class) 4457 .supportsLocalVoiceInteraction(); 4458 } 4459 4460 void onLocalVoiceInteractionStartedLocked(IBinder activity, 4461 IVoiceInteractionSession voiceSession, IVoiceInteractor voiceInteractor) { 4462 ActivityRecord activityToCallback = ActivityRecord.forTokenLocked(activity); 4463 if (activityToCallback == null) return; 4464 activityToCallback.setVoiceSessionLocked(voiceSession); 4465 4466 // Inform the activity 4467 try { 4468 activityToCallback.app.thread.scheduleLocalVoiceInteractionStarted(activity, 4469 voiceInteractor); 4470 long token = Binder.clearCallingIdentity(); 4471 try { 4472 startRunningVoiceLocked(voiceSession, activityToCallback.appInfo.uid); 4473 } finally { 4474 Binder.restoreCallingIdentity(token); 4475 } 4476 // TODO: VI Should we cache the activity so that it's easier to find later 4477 // rather than scan through all the stacks and activities? 4478 } catch (RemoteException re) { 4479 activityToCallback.clearVoiceSessionLocked(); 4480 // TODO: VI Should this terminate the voice session? 4481 } 4482 } 4483 4484 @Override 4485 public void setVoiceKeepAwake(IVoiceInteractionSession session, boolean keepAwake) { 4486 synchronized (this) { 4487 if (mRunningVoice != null && mRunningVoice.asBinder() == session.asBinder()) { 4488 if (keepAwake) { 4489 mVoiceWakeLock.acquire(); 4490 } else { 4491 mVoiceWakeLock.release(); 4492 } 4493 } 4494 } 4495 } 4496 4497 @Override 4498 public boolean startNextMatchingActivity(IBinder callingActivity, 4499 Intent intent, Bundle bOptions) { 4500 // Refuse possible leaked file descriptors 4501 if (intent != null && intent.hasFileDescriptors() == true) { 4502 throw new IllegalArgumentException("File descriptors passed in Intent"); 4503 } 4504 ActivityOptions options = ActivityOptions.fromBundle(bOptions); 4505 4506 synchronized (this) { 4507 final ActivityRecord r = ActivityRecord.isInStackLocked(callingActivity); 4508 if (r == null) { 4509 ActivityOptions.abort(options); 4510 return false; 4511 } 4512 if (r.app == null || r.app.thread == null) { 4513 // The caller is not running... d'oh! 4514 ActivityOptions.abort(options); 4515 return false; 4516 } 4517 intent = new Intent(intent); 4518 // The caller is not allowed to change the data. 4519 intent.setDataAndType(r.intent.getData(), r.intent.getType()); 4520 // And we are resetting to find the next component... 4521 intent.setComponent(null); 4522 4523 final boolean debug = ((intent.getFlags() & Intent.FLAG_DEBUG_LOG_RESOLUTION) != 0); 4524 4525 ActivityInfo aInfo = null; 4526 try { 4527 List<ResolveInfo> resolves = 4528 AppGlobals.getPackageManager().queryIntentActivities( 4529 intent, r.resolvedType, 4530 PackageManager.MATCH_DEFAULT_ONLY | STOCK_PM_FLAGS, 4531 UserHandle.getCallingUserId()).getList(); 4532 4533 // Look for the original activity in the list... 4534 final int N = resolves != null ? resolves.size() : 0; 4535 for (int i=0; i<N; i++) { 4536 ResolveInfo rInfo = resolves.get(i); 4537 if (rInfo.activityInfo.packageName.equals(r.packageName) 4538 && rInfo.activityInfo.name.equals(r.info.name)) { 4539 // We found the current one... the next matching is 4540 // after it. 4541 i++; 4542 if (i<N) { 4543 aInfo = resolves.get(i).activityInfo; 4544 } 4545 if (debug) { 4546 Slog.v(TAG, "Next matching activity: found current " + r.packageName 4547 + "/" + r.info.name); 4548 Slog.v(TAG, "Next matching activity: next is " + ((aInfo == null) 4549 ? "null" : aInfo.packageName + "/" + aInfo.name)); 4550 } 4551 break; 4552 } 4553 } 4554 } catch (RemoteException e) { 4555 } 4556 4557 if (aInfo == null) { 4558 // Nobody who is next! 4559 ActivityOptions.abort(options); 4560 if (debug) Slog.d(TAG, "Next matching activity: nothing found"); 4561 return false; 4562 } 4563 4564 intent.setComponent(new ComponentName( 4565 aInfo.applicationInfo.packageName, aInfo.name)); 4566 intent.setFlags(intent.getFlags()&~( 4567 Intent.FLAG_ACTIVITY_FORWARD_RESULT| 4568 Intent.FLAG_ACTIVITY_CLEAR_TOP| 4569 Intent.FLAG_ACTIVITY_MULTIPLE_TASK| 4570 Intent.FLAG_ACTIVITY_NEW_TASK)); 4571 4572 // Okay now we need to start the new activity, replacing the 4573 // currently running activity. This is a little tricky because 4574 // we want to start the new one as if the current one is finished, 4575 // but not finish the current one first so that there is no flicker. 4576 // And thus... 4577 final boolean wasFinishing = r.finishing; 4578 r.finishing = true; 4579 4580 // Propagate reply information over to the new activity. 4581 final ActivityRecord resultTo = r.resultTo; 4582 final String resultWho = r.resultWho; 4583 final int requestCode = r.requestCode; 4584 r.resultTo = null; 4585 if (resultTo != null) { 4586 resultTo.removeResultsLocked(r, resultWho, requestCode); 4587 } 4588 4589 final long origId = Binder.clearCallingIdentity(); 4590 int res = mActivityStarter.startActivityLocked(r.app.thread, intent, 4591 null /*ephemeralIntent*/, r.resolvedType, aInfo, null /*rInfo*/, null, 4592 null, resultTo != null ? resultTo.appToken : null, resultWho, requestCode, -1, 4593 r.launchedFromUid, r.launchedFromPackage, -1, r.launchedFromUid, 0, options, 4594 false, false, null, null, null); 4595 Binder.restoreCallingIdentity(origId); 4596 4597 r.finishing = wasFinishing; 4598 if (res != ActivityManager.START_SUCCESS) { 4599 return false; 4600 } 4601 return true; 4602 } 4603 } 4604 4605 @Override 4606 public final int startActivityFromRecents(int taskId, Bundle bOptions) { 4607 if (checkCallingPermission(START_TASKS_FROM_RECENTS) != PackageManager.PERMISSION_GRANTED) { 4608 String msg = "Permission Denial: startActivityFromRecents called without " + 4609 START_TASKS_FROM_RECENTS; 4610 Slog.w(TAG, msg); 4611 throw new SecurityException(msg); 4612 } 4613 final long origId = Binder.clearCallingIdentity(); 4614 try { 4615 synchronized (this) { 4616 return mStackSupervisor.startActivityFromRecentsInner(taskId, bOptions); 4617 } 4618 } finally { 4619 Binder.restoreCallingIdentity(origId); 4620 } 4621 } 4622 4623 final int startActivityInPackage(int uid, String callingPackage, 4624 Intent intent, String resolvedType, IBinder resultTo, 4625 String resultWho, int requestCode, int startFlags, Bundle bOptions, int userId, 4626 IActivityContainer container, TaskRecord inTask) { 4627 4628 userId = mUserController.handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 4629 userId, false, ALLOW_FULL_ONLY, "startActivityInPackage", null); 4630 4631 // TODO: Switch to user app stacks here. 4632 int ret = mActivityStarter.startActivityMayWait(null, uid, callingPackage, intent, 4633 resolvedType, null, null, resultTo, resultWho, requestCode, startFlags, 4634 null, null, null, bOptions, false, userId, container, inTask); 4635 return ret; 4636 } 4637 4638 @Override 4639 public final int startActivities(IApplicationThread caller, String callingPackage, 4640 Intent[] intents, String[] resolvedTypes, IBinder resultTo, Bundle bOptions, 4641 int userId) { 4642 enforceNotIsolatedCaller("startActivities"); 4643 userId = mUserController.handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 4644 userId, false, ALLOW_FULL_ONLY, "startActivity", null); 4645 // TODO: Switch to user app stacks here. 4646 int ret = mActivityStarter.startActivities(caller, -1, callingPackage, intents, 4647 resolvedTypes, resultTo, bOptions, userId); 4648 return ret; 4649 } 4650 4651 final int startActivitiesInPackage(int uid, String callingPackage, 4652 Intent[] intents, String[] resolvedTypes, IBinder resultTo, 4653 Bundle bOptions, int userId) { 4654 4655 userId = mUserController.handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 4656 userId, false, ALLOW_FULL_ONLY, "startActivityInPackage", null); 4657 // TODO: Switch to user app stacks here. 4658 int ret = mActivityStarter.startActivities(null, uid, callingPackage, intents, resolvedTypes, 4659 resultTo, bOptions, userId); 4660 return ret; 4661 } 4662 4663 @Override 4664 public void reportActivityFullyDrawn(IBinder token) { 4665 synchronized (this) { 4666 ActivityRecord r = ActivityRecord.isInStackLocked(token); 4667 if (r == null) { 4668 return; 4669 } 4670 r.reportFullyDrawnLocked(); 4671 } 4672 } 4673 4674 @Override 4675 public void setRequestedOrientation(IBinder token, int requestedOrientation) { 4676 synchronized (this) { 4677 ActivityRecord r = ActivityRecord.isInStackLocked(token); 4678 if (r == null) { 4679 return; 4680 } 4681 TaskRecord task = r.task; 4682 if (task != null && (!task.mFullscreen || !task.stack.mFullscreen)) { 4683 // Fixed screen orientation isn't supported when activities aren't in full screen 4684 // mode. 4685 return; 4686 } 4687 final long origId = Binder.clearCallingIdentity(); 4688 mWindowManager.setAppOrientation(r.appToken, requestedOrientation); 4689 Configuration config = mWindowManager.updateOrientationFromAppTokens( 4690 mConfiguration, r.mayFreezeScreenLocked(r.app) ? r.appToken : null); 4691 if (config != null) { 4692 r.frozenBeforeDestroy = true; 4693 if (!updateConfigurationLocked(config, r, false)) { 4694 mStackSupervisor.resumeFocusedStackTopActivityLocked(); 4695 } 4696 } 4697 Binder.restoreCallingIdentity(origId); 4698 } 4699 } 4700 4701 @Override 4702 public int getRequestedOrientation(IBinder token) { 4703 synchronized (this) { 4704 ActivityRecord r = ActivityRecord.isInStackLocked(token); 4705 if (r == null) { 4706 return ActivityInfo.SCREEN_ORIENTATION_UNSPECIFIED; 4707 } 4708 return mWindowManager.getAppOrientation(r.appToken); 4709 } 4710 } 4711 4712 /** 4713 * This is the internal entry point for handling Activity.finish(). 4714 * 4715 * @param token The Binder token referencing the Activity we want to finish. 4716 * @param resultCode Result code, if any, from this Activity. 4717 * @param resultData Result data (Intent), if any, from this Activity. 4718 * @param finishTask Whether to finish the task associated with this Activity. 4719 * 4720 * @return Returns true if the activity successfully finished, or false if it is still running. 4721 */ 4722 @Override 4723 public final boolean finishActivity(IBinder token, int resultCode, Intent resultData, 4724 int finishTask) { 4725 // Refuse possible leaked file descriptors 4726 if (resultData != null && resultData.hasFileDescriptors() == true) { 4727 throw new IllegalArgumentException("File descriptors passed in Intent"); 4728 } 4729 4730 synchronized(this) { 4731 ActivityRecord r = ActivityRecord.isInStackLocked(token); 4732 if (r == null) { 4733 return true; 4734 } 4735 // Keep track of the root activity of the task before we finish it 4736 TaskRecord tr = r.task; 4737 ActivityRecord rootR = tr.getRootActivity(); 4738 if (rootR == null) { 4739 Slog.w(TAG, "Finishing task with all activities already finished"); 4740 } 4741 // Do not allow task to finish if last task in lockTask mode. Launchable priv-apps can 4742 // finish. 4743 if (tr.mLockTaskAuth != LOCK_TASK_AUTH_LAUNCHABLE_PRIV && rootR == r && 4744 mStackSupervisor.isLastLockedTask(tr)) { 4745 Slog.i(TAG, "Not finishing task in lock task mode"); 4746 mStackSupervisor.showLockTaskToast(); 4747 return false; 4748 } 4749 if (mController != null) { 4750 // Find the first activity that is not finishing. 4751 ActivityRecord next = r.task.stack.topRunningActivityLocked(token, 0); 4752 if (next != null) { 4753 // ask watcher if this is allowed 4754 boolean resumeOK = true; 4755 try { 4756 resumeOK = mController.activityResuming(next.packageName); 4757 } catch (RemoteException e) { 4758 mController = null; 4759 Watchdog.getInstance().setActivityController(null); 4760 } 4761 4762 if (!resumeOK) { 4763 Slog.i(TAG, "Not finishing activity because controller resumed"); 4764 return false; 4765 } 4766 } 4767 } 4768 final long origId = Binder.clearCallingIdentity(); 4769 try { 4770 boolean res; 4771 final boolean finishWithRootActivity = 4772 finishTask == Activity.FINISH_TASK_WITH_ROOT_ACTIVITY; 4773 if (finishTask == Activity.FINISH_TASK_WITH_ACTIVITY 4774 || (finishWithRootActivity && r == rootR)) { 4775 // If requested, remove the task that is associated to this activity only if it 4776 // was the root activity in the task. The result code and data is ignored 4777 // because we don't support returning them across task boundaries. Also, to 4778 // keep backwards compatibility we remove the task from recents when finishing 4779 // task with root activity. 4780 res = removeTaskByIdLocked(tr.taskId, false, finishWithRootActivity); 4781 if (!res) { 4782 Slog.i(TAG, "Removing task failed to finish activity"); 4783 } 4784 } else { 4785 res = tr.stack.requestFinishActivityLocked(token, resultCode, 4786 resultData, "app-request", true); 4787 if (!res) { 4788 Slog.i(TAG, "Failed to finish by app-request"); 4789 } 4790 } 4791 return res; 4792 } finally { 4793 Binder.restoreCallingIdentity(origId); 4794 } 4795 } 4796 } 4797 4798 @Override 4799 public final void finishHeavyWeightApp() { 4800 if (checkCallingPermission(android.Manifest.permission.FORCE_STOP_PACKAGES) 4801 != PackageManager.PERMISSION_GRANTED) { 4802 String msg = "Permission Denial: finishHeavyWeightApp() from pid=" 4803 + Binder.getCallingPid() 4804 + ", uid=" + Binder.getCallingUid() 4805 + " requires " + android.Manifest.permission.FORCE_STOP_PACKAGES; 4806 Slog.w(TAG, msg); 4807 throw new SecurityException(msg); 4808 } 4809 4810 synchronized(this) { 4811 if (mHeavyWeightProcess == null) { 4812 return; 4813 } 4814 4815 ArrayList<ActivityRecord> activities = new ArrayList<>(mHeavyWeightProcess.activities); 4816 for (int i = 0; i < activities.size(); i++) { 4817 ActivityRecord r = activities.get(i); 4818 if (!r.finishing && r.isInStackLocked()) { 4819 r.task.stack.finishActivityLocked(r, Activity.RESULT_CANCELED, 4820 null, "finish-heavy", true); 4821 } 4822 } 4823 4824 mHandler.sendMessage(mHandler.obtainMessage(CANCEL_HEAVY_NOTIFICATION_MSG, 4825 mHeavyWeightProcess.userId, 0)); 4826 mHeavyWeightProcess = null; 4827 } 4828 } 4829 4830 @Override 4831 public void crashApplication(int uid, int initialPid, String packageName, 4832 String message) { 4833 if (checkCallingPermission(android.Manifest.permission.FORCE_STOP_PACKAGES) 4834 != PackageManager.PERMISSION_GRANTED) { 4835 String msg = "Permission Denial: crashApplication() from pid=" 4836 + Binder.getCallingPid() 4837 + ", uid=" + Binder.getCallingUid() 4838 + " requires " + android.Manifest.permission.FORCE_STOP_PACKAGES; 4839 Slog.w(TAG, msg); 4840 throw new SecurityException(msg); 4841 } 4842 4843 synchronized(this) { 4844 mAppErrors.scheduleAppCrashLocked(uid, initialPid, packageName, message); 4845 } 4846 } 4847 4848 @Override 4849 public final void finishSubActivity(IBinder token, String resultWho, 4850 int requestCode) { 4851 synchronized(this) { 4852 final long origId = Binder.clearCallingIdentity(); 4853 ActivityRecord r = ActivityRecord.isInStackLocked(token); 4854 if (r != null) { 4855 r.task.stack.finishSubActivityLocked(r, resultWho, requestCode); 4856 } 4857 Binder.restoreCallingIdentity(origId); 4858 } 4859 } 4860 4861 @Override 4862 public boolean finishActivityAffinity(IBinder token) { 4863 synchronized(this) { 4864 final long origId = Binder.clearCallingIdentity(); 4865 try { 4866 ActivityRecord r = ActivityRecord.isInStackLocked(token); 4867 if (r == null) { 4868 return false; 4869 } 4870 4871 // Do not allow task to finish if last task in lockTask mode. Launchable priv-apps 4872 // can finish. 4873 final TaskRecord task = r.task; 4874 if (task.mLockTaskAuth != LOCK_TASK_AUTH_LAUNCHABLE_PRIV && 4875 mStackSupervisor.isLastLockedTask(task) && task.getRootActivity() == r) { 4876 mStackSupervisor.showLockTaskToast(); 4877 return false; 4878 } 4879 return task.stack.finishActivityAffinityLocked(r); 4880 } finally { 4881 Binder.restoreCallingIdentity(origId); 4882 } 4883 } 4884 } 4885 4886 @Override 4887 public void finishVoiceTask(IVoiceInteractionSession session) { 4888 synchronized (this) { 4889 final long origId = Binder.clearCallingIdentity(); 4890 try { 4891 // TODO: VI Consider treating local voice interactions and voice tasks 4892 // differently here 4893 mStackSupervisor.finishVoiceTask(session); 4894 } finally { 4895 Binder.restoreCallingIdentity(origId); 4896 } 4897 } 4898 4899 } 4900 4901 @Override 4902 public boolean releaseActivityInstance(IBinder token) { 4903 synchronized(this) { 4904 final long origId = Binder.clearCallingIdentity(); 4905 try { 4906 ActivityRecord r = ActivityRecord.isInStackLocked(token); 4907 if (r == null) { 4908 return false; 4909 } 4910 return r.task.stack.safelyDestroyActivityLocked(r, "app-req"); 4911 } finally { 4912 Binder.restoreCallingIdentity(origId); 4913 } 4914 } 4915 } 4916 4917 @Override 4918 public void releaseSomeActivities(IApplicationThread appInt) { 4919 synchronized(this) { 4920 final long origId = Binder.clearCallingIdentity(); 4921 try { 4922 ProcessRecord app = getRecordForAppLocked(appInt); 4923 mStackSupervisor.releaseSomeActivitiesLocked(app, "low-mem"); 4924 } finally { 4925 Binder.restoreCallingIdentity(origId); 4926 } 4927 } 4928 } 4929 4930 @Override 4931 public boolean willActivityBeVisible(IBinder token) { 4932 synchronized(this) { 4933 ActivityStack stack = ActivityRecord.getStackLocked(token); 4934 if (stack != null) { 4935 return stack.willActivityBeVisibleLocked(token); 4936 } 4937 return false; 4938 } 4939 } 4940 4941 @Override 4942 public void overridePendingTransition(IBinder token, String packageName, 4943 int enterAnim, int exitAnim) { 4944 synchronized(this) { 4945 ActivityRecord self = ActivityRecord.isInStackLocked(token); 4946 if (self == null) { 4947 return; 4948 } 4949 4950 final long origId = Binder.clearCallingIdentity(); 4951 4952 if (self.state == ActivityState.RESUMED 4953 || self.state == ActivityState.PAUSING) { 4954 mWindowManager.overridePendingAppTransition(packageName, 4955 enterAnim, exitAnim, null); 4956 } 4957 4958 Binder.restoreCallingIdentity(origId); 4959 } 4960 } 4961 4962 /** 4963 * Main function for removing an existing process from the activity manager 4964 * as a result of that process going away. Clears out all connections 4965 * to the process. 4966 */ 4967 private final void handleAppDiedLocked(ProcessRecord app, 4968 boolean restarting, boolean allowRestart) { 4969 int pid = app.pid; 4970 boolean kept = cleanUpApplicationRecordLocked(app, restarting, allowRestart, -1); 4971 if (!kept && !restarting) { 4972 removeLruProcessLocked(app); 4973 if (pid > 0) { 4974 ProcessList.remove(pid); 4975 } 4976 } 4977 4978 if (mProfileProc == app) { 4979 clearProfilerLocked(); 4980 } 4981 4982 // Remove this application's activities from active lists. 4983 boolean hasVisibleActivities = mStackSupervisor.handleAppDiedLocked(app); 4984 4985 app.activities.clear(); 4986 4987 if (app.instrumentationClass != null) { 4988 Slog.w(TAG, "Crash of app " + app.processName 4989 + " running instrumentation " + app.instrumentationClass); 4990 Bundle info = new Bundle(); 4991 info.putString("shortMsg", "Process crashed."); 4992 finishInstrumentationLocked(app, Activity.RESULT_CANCELED, info); 4993 } 4994 4995 if (!restarting && hasVisibleActivities 4996 && !mStackSupervisor.resumeFocusedStackTopActivityLocked()) { 4997 // If there was nothing to resume, and we are not already restarting this process, but 4998 // there is a visible activity that is hosted by the process... then make sure all 4999 // visible activities are running, taking care of restarting this process. 5000 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0, !PRESERVE_WINDOWS); 5001 } 5002 } 5003 5004 private final int getLRURecordIndexForAppLocked(IApplicationThread thread) { 5005 IBinder threadBinder = thread.asBinder(); 5006 // Find the application record. 5007 for (int i=mLruProcesses.size()-1; i>=0; i--) { 5008 ProcessRecord rec = mLruProcesses.get(i); 5009 if (rec.thread != null && rec.thread.asBinder() == threadBinder) { 5010 return i; 5011 } 5012 } 5013 return -1; 5014 } 5015 5016 final ProcessRecord getRecordForAppLocked( 5017 IApplicationThread thread) { 5018 if (thread == null) { 5019 return null; 5020 } 5021 5022 int appIndex = getLRURecordIndexForAppLocked(thread); 5023 return appIndex >= 0 ? mLruProcesses.get(appIndex) : null; 5024 } 5025 5026 final void doLowMemReportIfNeededLocked(ProcessRecord dyingProc) { 5027 // If there are no longer any background processes running, 5028 // and the app that died was not running instrumentation, 5029 // then tell everyone we are now low on memory. 5030 boolean haveBg = false; 5031 for (int i=mLruProcesses.size()-1; i>=0; i--) { 5032 ProcessRecord rec = mLruProcesses.get(i); 5033 if (rec.thread != null 5034 && rec.setProcState >= ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 5035 haveBg = true; 5036 break; 5037 } 5038 } 5039 5040 if (!haveBg) { 5041 boolean doReport = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 5042 if (doReport) { 5043 long now = SystemClock.uptimeMillis(); 5044 if (now < (mLastMemUsageReportTime+5*60*1000)) { 5045 doReport = false; 5046 } else { 5047 mLastMemUsageReportTime = now; 5048 } 5049 } 5050 final ArrayList<ProcessMemInfo> memInfos 5051 = doReport ? new ArrayList<ProcessMemInfo>(mLruProcesses.size()) : null; 5052 EventLog.writeEvent(EventLogTags.AM_LOW_MEMORY, mLruProcesses.size()); 5053 long now = SystemClock.uptimeMillis(); 5054 for (int i=mLruProcesses.size()-1; i>=0; i--) { 5055 ProcessRecord rec = mLruProcesses.get(i); 5056 if (rec == dyingProc || rec.thread == null) { 5057 continue; 5058 } 5059 if (doReport) { 5060 memInfos.add(new ProcessMemInfo(rec.processName, rec.pid, rec.setAdj, 5061 rec.setProcState, rec.adjType, rec.makeAdjReason())); 5062 } 5063 if ((rec.lastLowMemory+GC_MIN_INTERVAL) <= now) { 5064 // The low memory report is overriding any current 5065 // state for a GC request. Make sure to do 5066 // heavy/important/visible/foreground processes first. 5067 if (rec.setAdj <= ProcessList.HEAVY_WEIGHT_APP_ADJ) { 5068 rec.lastRequestedGc = 0; 5069 } else { 5070 rec.lastRequestedGc = rec.lastLowMemory; 5071 } 5072 rec.reportLowMemory = true; 5073 rec.lastLowMemory = now; 5074 mProcessesToGc.remove(rec); 5075 addProcessToGcListLocked(rec); 5076 } 5077 } 5078 if (doReport) { 5079 Message msg = mHandler.obtainMessage(REPORT_MEM_USAGE_MSG, memInfos); 5080 mHandler.sendMessage(msg); 5081 } 5082 scheduleAppGcsLocked(); 5083 } 5084 } 5085 5086 final void appDiedLocked(ProcessRecord app) { 5087 appDiedLocked(app, app.pid, app.thread, false); 5088 } 5089 5090 final void appDiedLocked(ProcessRecord app, int pid, IApplicationThread thread, 5091 boolean fromBinderDied) { 5092 // First check if this ProcessRecord is actually active for the pid. 5093 synchronized (mPidsSelfLocked) { 5094 ProcessRecord curProc = mPidsSelfLocked.get(pid); 5095 if (curProc != app) { 5096 Slog.w(TAG, "Spurious death for " + app + ", curProc for " + pid + ": " + curProc); 5097 return; 5098 } 5099 } 5100 5101 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 5102 synchronized (stats) { 5103 stats.noteProcessDiedLocked(app.info.uid, pid); 5104 } 5105 5106 if (!app.killed) { 5107 if (!fromBinderDied) { 5108 Process.killProcessQuiet(pid); 5109 } 5110 killProcessGroup(app.uid, pid); 5111 app.killed = true; 5112 } 5113 5114 // Clean up already done if the process has been re-started. 5115 if (app.pid == pid && app.thread != null && 5116 app.thread.asBinder() == thread.asBinder()) { 5117 boolean doLowMem = app.instrumentationClass == null; 5118 boolean doOomAdj = doLowMem; 5119 if (!app.killedByAm) { 5120 Slog.i(TAG, "Process " + app.processName + " (pid " + pid 5121 + ") has died"); 5122 mAllowLowerMemLevel = true; 5123 } else { 5124 // Note that we always want to do oom adj to update our state with the 5125 // new number of procs. 5126 mAllowLowerMemLevel = false; 5127 doLowMem = false; 5128 } 5129 EventLog.writeEvent(EventLogTags.AM_PROC_DIED, app.userId, app.pid, app.processName); 5130 if (DEBUG_CLEANUP) Slog.v(TAG_CLEANUP, 5131 "Dying app: " + app + ", pid: " + pid + ", thread: " + thread.asBinder()); 5132 handleAppDiedLocked(app, false, true); 5133 5134 if (doOomAdj) { 5135 updateOomAdjLocked(); 5136 } 5137 if (doLowMem) { 5138 doLowMemReportIfNeededLocked(app); 5139 } 5140 } else if (app.pid != pid) { 5141 // A new process has already been started. 5142 Slog.i(TAG, "Process " + app.processName + " (pid " + pid 5143 + ") has died and restarted (pid " + app.pid + ")."); 5144 EventLog.writeEvent(EventLogTags.AM_PROC_DIED, app.userId, app.pid, app.processName); 5145 } else if (DEBUG_PROCESSES) { 5146 Slog.d(TAG_PROCESSES, "Received spurious death notification for thread " 5147 + thread.asBinder()); 5148 } 5149 } 5150 5151 /** 5152 * If a stack trace dump file is configured, dump process stack traces. 5153 * @param clearTraces causes the dump file to be erased prior to the new 5154 * traces being written, if true; when false, the new traces will be 5155 * appended to any existing file content. 5156 * @param firstPids of dalvik VM processes to dump stack traces for first 5157 * @param lastPids of dalvik VM processes to dump stack traces for last 5158 * @param nativeProcs optional list of native process names to dump stack crawls 5159 * @return file containing stack traces, or null if no dump file is configured 5160 */ 5161 public static File dumpStackTraces(boolean clearTraces, ArrayList<Integer> firstPids, 5162 ProcessCpuTracker processCpuTracker, SparseArray<Boolean> lastPids, String[] nativeProcs) { 5163 String tracesPath = SystemProperties.get("dalvik.vm.stack-trace-file", null); 5164 if (tracesPath == null || tracesPath.length() == 0) { 5165 return null; 5166 } 5167 5168 File tracesFile = new File(tracesPath); 5169 try { 5170 if (clearTraces && tracesFile.exists()) tracesFile.delete(); 5171 tracesFile.createNewFile(); 5172 FileUtils.setPermissions(tracesFile.getPath(), 0666, -1, -1); // -rw-rw-rw- 5173 } catch (IOException e) { 5174 Slog.w(TAG, "Unable to prepare ANR traces file: " + tracesPath, e); 5175 return null; 5176 } 5177 5178 dumpStackTraces(tracesPath, firstPids, processCpuTracker, lastPids, nativeProcs); 5179 return tracesFile; 5180 } 5181 5182 private static void dumpStackTraces(String tracesPath, ArrayList<Integer> firstPids, 5183 ProcessCpuTracker processCpuTracker, SparseArray<Boolean> lastPids, String[] nativeProcs) { 5184 // Use a FileObserver to detect when traces finish writing. 5185 // The order of traces is considered important to maintain for legibility. 5186 FileObserver observer = new FileObserver(tracesPath, FileObserver.CLOSE_WRITE) { 5187 @Override 5188 public synchronized void onEvent(int event, String path) { notify(); } 5189 }; 5190 5191 try { 5192 observer.startWatching(); 5193 5194 // First collect all of the stacks of the most important pids. 5195 if (firstPids != null) { 5196 try { 5197 int num = firstPids.size(); 5198 for (int i = 0; i < num; i++) { 5199 synchronized (observer) { 5200 if (DEBUG_ANR) Slog.d(TAG, "Collecting stacks for pid " 5201 + firstPids.get(i)); 5202 final long sime = SystemClock.elapsedRealtime(); 5203 Process.sendSignal(firstPids.get(i), Process.SIGNAL_QUIT); 5204 observer.wait(1000); // Wait for write-close, give up after 1 sec 5205 if (DEBUG_ANR) Slog.d(TAG, "Done with pid " + firstPids.get(i) 5206 + " in " + (SystemClock.elapsedRealtime()-sime) + "ms"); 5207 } 5208 } 5209 } catch (InterruptedException e) { 5210 Slog.wtf(TAG, e); 5211 } 5212 } 5213 5214 // Next collect the stacks of the native pids 5215 if (nativeProcs != null) { 5216 int[] pids = Process.getPidsForCommands(nativeProcs); 5217 if (pids != null) { 5218 for (int pid : pids) { 5219 if (DEBUG_ANR) Slog.d(TAG, "Collecting stacks for native pid " + pid); 5220 final long sime = SystemClock.elapsedRealtime(); 5221 Debug.dumpNativeBacktraceToFile(pid, tracesPath); 5222 if (DEBUG_ANR) Slog.d(TAG, "Done with native pid " + pid 5223 + " in " + (SystemClock.elapsedRealtime()-sime) + "ms"); 5224 } 5225 } 5226 } 5227 5228 // Lastly, measure CPU usage. 5229 if (processCpuTracker != null) { 5230 processCpuTracker.init(); 5231 System.gc(); 5232 processCpuTracker.update(); 5233 try { 5234 synchronized (processCpuTracker) { 5235 processCpuTracker.wait(500); // measure over 1/2 second. 5236 } 5237 } catch (InterruptedException e) { 5238 } 5239 processCpuTracker.update(); 5240 5241 // We'll take the stack crawls of just the top apps using CPU. 5242 final int N = processCpuTracker.countWorkingStats(); 5243 int numProcs = 0; 5244 for (int i=0; i<N && numProcs<5; i++) { 5245 ProcessCpuTracker.Stats stats = processCpuTracker.getWorkingStats(i); 5246 if (lastPids.indexOfKey(stats.pid) >= 0) { 5247 numProcs++; 5248 try { 5249 synchronized (observer) { 5250 if (DEBUG_ANR) Slog.d(TAG, "Collecting stacks for extra pid " 5251 + stats.pid); 5252 final long stime = SystemClock.elapsedRealtime(); 5253 Process.sendSignal(stats.pid, Process.SIGNAL_QUIT); 5254 observer.wait(1000); // Wait for write-close, give up after 1 sec 5255 if (DEBUG_ANR) Slog.d(TAG, "Done with extra pid " + stats.pid 5256 + " in " + (SystemClock.elapsedRealtime()-stime) + "ms"); 5257 } 5258 } catch (InterruptedException e) { 5259 Slog.wtf(TAG, e); 5260 } 5261 } else if (DEBUG_ANR) { 5262 Slog.d(TAG, "Skipping next CPU consuming process, not a java proc: " 5263 + stats.pid); 5264 } 5265 } 5266 } 5267 } finally { 5268 observer.stopWatching(); 5269 } 5270 } 5271 5272 final void logAppTooSlow(ProcessRecord app, long startTime, String msg) { 5273 if (true || IS_USER_BUILD) { 5274 return; 5275 } 5276 String tracesPath = SystemProperties.get("dalvik.vm.stack-trace-file", null); 5277 if (tracesPath == null || tracesPath.length() == 0) { 5278 return; 5279 } 5280 5281 StrictMode.ThreadPolicy oldPolicy = StrictMode.allowThreadDiskReads(); 5282 StrictMode.allowThreadDiskWrites(); 5283 try { 5284 final File tracesFile = new File(tracesPath); 5285 final File tracesDir = tracesFile.getParentFile(); 5286 final File tracesTmp = new File(tracesDir, "__tmp__"); 5287 try { 5288 if (tracesFile.exists()) { 5289 tracesTmp.delete(); 5290 tracesFile.renameTo(tracesTmp); 5291 } 5292 StringBuilder sb = new StringBuilder(); 5293 Time tobj = new Time(); 5294 tobj.set(System.currentTimeMillis()); 5295 sb.append(tobj.format("%Y-%m-%d %H:%M:%S")); 5296 sb.append(": "); 5297 TimeUtils.formatDuration(SystemClock.uptimeMillis()-startTime, sb); 5298 sb.append(" since "); 5299 sb.append(msg); 5300 FileOutputStream fos = new FileOutputStream(tracesFile); 5301 fos.write(sb.toString().getBytes()); 5302 if (app == null) { 5303 fos.write("\n*** No application process!".getBytes()); 5304 } 5305 fos.close(); 5306 FileUtils.setPermissions(tracesFile.getPath(), 0666, -1, -1); // -rw-rw-rw- 5307 } catch (IOException e) { 5308 Slog.w(TAG, "Unable to prepare slow app traces file: " + tracesPath, e); 5309 return; 5310 } 5311 5312 if (app != null) { 5313 ArrayList<Integer> firstPids = new ArrayList<Integer>(); 5314 firstPids.add(app.pid); 5315 dumpStackTraces(tracesPath, firstPids, null, null, null); 5316 } 5317 5318 File lastTracesFile = null; 5319 File curTracesFile = null; 5320 for (int i=9; i>=0; i--) { 5321 String name = String.format(Locale.US, "slow%02d.txt", i); 5322 curTracesFile = new File(tracesDir, name); 5323 if (curTracesFile.exists()) { 5324 if (lastTracesFile != null) { 5325 curTracesFile.renameTo(lastTracesFile); 5326 } else { 5327 curTracesFile.delete(); 5328 } 5329 } 5330 lastTracesFile = curTracesFile; 5331 } 5332 tracesFile.renameTo(curTracesFile); 5333 if (tracesTmp.exists()) { 5334 tracesTmp.renameTo(tracesFile); 5335 } 5336 } finally { 5337 StrictMode.setThreadPolicy(oldPolicy); 5338 } 5339 } 5340 5341 final void showLaunchWarningLocked(final ActivityRecord cur, final ActivityRecord next) { 5342 if (!mLaunchWarningShown) { 5343 mLaunchWarningShown = true; 5344 mUiHandler.post(new Runnable() { 5345 @Override 5346 public void run() { 5347 synchronized (ActivityManagerService.this) { 5348 final Dialog d = new LaunchWarningWindow(mContext, cur, next); 5349 d.show(); 5350 mUiHandler.postDelayed(new Runnable() { 5351 @Override 5352 public void run() { 5353 synchronized (ActivityManagerService.this) { 5354 d.dismiss(); 5355 mLaunchWarningShown = false; 5356 } 5357 } 5358 }, 4000); 5359 } 5360 } 5361 }); 5362 } 5363 } 5364 5365 @Override 5366 public boolean clearApplicationUserData(final String packageName, 5367 final IPackageDataObserver observer, int userId) { 5368 enforceNotIsolatedCaller("clearApplicationUserData"); 5369 int uid = Binder.getCallingUid(); 5370 int pid = Binder.getCallingPid(); 5371 userId = mUserController.handleIncomingUser(pid, uid, userId, false, 5372 ALLOW_FULL_ONLY, "clearApplicationUserData", null); 5373 5374 final DevicePolicyManagerInternal dpmi = LocalServices 5375 .getService(DevicePolicyManagerInternal.class); 5376 if (dpmi != null && dpmi.hasDeviceOwnerOrProfileOwner(packageName, userId)) { 5377 throw new SecurityException("Cannot clear data for a device owner or a profile owner"); 5378 } 5379 5380 long callingId = Binder.clearCallingIdentity(); 5381 try { 5382 IPackageManager pm = AppGlobals.getPackageManager(); 5383 int pkgUid = -1; 5384 synchronized(this) { 5385 try { 5386 pkgUid = pm.getPackageUid(packageName, MATCH_UNINSTALLED_PACKAGES, userId); 5387 } catch (RemoteException e) { 5388 } 5389 if (pkgUid == -1) { 5390 Slog.w(TAG, "Invalid packageName: " + packageName); 5391 if (observer != null) { 5392 try { 5393 observer.onRemoveCompleted(packageName, false); 5394 } catch (RemoteException e) { 5395 Slog.i(TAG, "Observer no longer exists."); 5396 } 5397 } 5398 return false; 5399 } 5400 if (uid == pkgUid || checkComponentPermission( 5401 android.Manifest.permission.CLEAR_APP_USER_DATA, 5402 pid, uid, -1, true) 5403 == PackageManager.PERMISSION_GRANTED) { 5404 forceStopPackageLocked(packageName, pkgUid, "clear data"); 5405 } else { 5406 throw new SecurityException("PID " + pid + " does not have permission " 5407 + android.Manifest.permission.CLEAR_APP_USER_DATA + " to clear data" 5408 + " of package " + packageName); 5409 } 5410 5411 // Remove all tasks match the cleared application package and user 5412 for (int i = mRecentTasks.size() - 1; i >= 0; i--) { 5413 final TaskRecord tr = mRecentTasks.get(i); 5414 final String taskPackageName = 5415 tr.getBaseIntent().getComponent().getPackageName(); 5416 if (tr.userId != userId) continue; 5417 if (!taskPackageName.equals(packageName)) continue; 5418 removeTaskByIdLocked(tr.taskId, false, REMOVE_FROM_RECENTS); 5419 } 5420 } 5421 5422 try { 5423 // Clear application user data 5424 pm.clearApplicationUserData(packageName, observer, userId); 5425 5426 synchronized(this) { 5427 // Remove all permissions granted from/to this package 5428 removeUriPermissionsForPackageLocked(packageName, userId, true); 5429 } 5430 5431 // Remove all zen rules created by this package; revoke it's zen access. 5432 INotificationManager inm = NotificationManager.getService(); 5433 inm.removeAutomaticZenRules(packageName); 5434 inm.setNotificationPolicyAccessGranted(packageName, false); 5435 5436 Intent intent = new Intent(Intent.ACTION_PACKAGE_DATA_CLEARED, 5437 Uri.fromParts("package", packageName, null)); 5438 intent.putExtra(Intent.EXTRA_UID, pkgUid); 5439 intent.putExtra(Intent.EXTRA_USER_HANDLE, UserHandle.getUserId(pkgUid)); 5440 broadcastIntentInPackage("android", Process.SYSTEM_UID, intent, 5441 null, null, 0, null, null, null, null, false, false, userId); 5442 } catch (RemoteException e) { 5443 } 5444 } finally { 5445 Binder.restoreCallingIdentity(callingId); 5446 } 5447 return true; 5448 } 5449 5450 @Override 5451 public void killBackgroundProcesses(final String packageName, int userId) { 5452 if (checkCallingPermission(android.Manifest.permission.KILL_BACKGROUND_PROCESSES) 5453 != PackageManager.PERMISSION_GRANTED && 5454 checkCallingPermission(android.Manifest.permission.RESTART_PACKAGES) 5455 != PackageManager.PERMISSION_GRANTED) { 5456 String msg = "Permission Denial: killBackgroundProcesses() from pid=" 5457 + Binder.getCallingPid() 5458 + ", uid=" + Binder.getCallingUid() 5459 + " requires " + android.Manifest.permission.KILL_BACKGROUND_PROCESSES; 5460 Slog.w(TAG, msg); 5461 throw new SecurityException(msg); 5462 } 5463 5464 userId = mUserController.handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 5465 userId, true, ALLOW_FULL_ONLY, "killBackgroundProcesses", null); 5466 long callingId = Binder.clearCallingIdentity(); 5467 try { 5468 IPackageManager pm = AppGlobals.getPackageManager(); 5469 synchronized(this) { 5470 int appId = -1; 5471 try { 5472 appId = UserHandle.getAppId( 5473 pm.getPackageUid(packageName, MATCH_DEBUG_TRIAGED_MISSING, userId)); 5474 } catch (RemoteException e) { 5475 } 5476 if (appId == -1) { 5477 Slog.w(TAG, "Invalid packageName: " + packageName); 5478 return; 5479 } 5480 killPackageProcessesLocked(packageName, appId, userId, 5481 ProcessList.SERVICE_ADJ, false, true, true, false, "kill background"); 5482 } 5483 } finally { 5484 Binder.restoreCallingIdentity(callingId); 5485 } 5486 } 5487 5488 @Override 5489 public void killAllBackgroundProcesses() { 5490 if (checkCallingPermission(android.Manifest.permission.KILL_BACKGROUND_PROCESSES) 5491 != PackageManager.PERMISSION_GRANTED) { 5492 final String msg = "Permission Denial: killAllBackgroundProcesses() from pid=" 5493 + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid() 5494 + " requires " + android.Manifest.permission.KILL_BACKGROUND_PROCESSES; 5495 Slog.w(TAG, msg); 5496 throw new SecurityException(msg); 5497 } 5498 5499 final long callingId = Binder.clearCallingIdentity(); 5500 try { 5501 synchronized (this) { 5502 final ArrayList<ProcessRecord> procs = new ArrayList<>(); 5503 final int NP = mProcessNames.getMap().size(); 5504 for (int ip = 0; ip < NP; ip++) { 5505 final SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 5506 final int NA = apps.size(); 5507 for (int ia = 0; ia < NA; ia++) { 5508 final ProcessRecord app = apps.valueAt(ia); 5509 if (app.persistent) { 5510 // We don't kill persistent processes. 5511 continue; 5512 } 5513 if (app.removed) { 5514 procs.add(app); 5515 } else if (app.setAdj >= ProcessList.CACHED_APP_MIN_ADJ) { 5516 app.removed = true; 5517 procs.add(app); 5518 } 5519 } 5520 } 5521 5522 final int N = procs.size(); 5523 for (int i = 0; i < N; i++) { 5524 removeProcessLocked(procs.get(i), false, true, "kill all background"); 5525 } 5526 5527 mAllowLowerMemLevel = true; 5528 5529 updateOomAdjLocked(); 5530 doLowMemReportIfNeededLocked(null); 5531 } 5532 } finally { 5533 Binder.restoreCallingIdentity(callingId); 5534 } 5535 } 5536 5537 /** 5538 * Kills all background processes, except those matching any of the 5539 * specified properties. 5540 * 5541 * @param minTargetSdk the target SDK version at or above which to preserve 5542 * processes, or {@code -1} to ignore the target SDK 5543 * @param maxProcState the process state at or below which to preserve 5544 * processes, or {@code -1} to ignore the process state 5545 */ 5546 private void killAllBackgroundProcessesExcept(int minTargetSdk, int maxProcState) { 5547 if (checkCallingPermission(android.Manifest.permission.KILL_BACKGROUND_PROCESSES) 5548 != PackageManager.PERMISSION_GRANTED) { 5549 final String msg = "Permission Denial: killAllBackgroundProcessesExcept() from pid=" 5550 + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid() 5551 + " requires " + android.Manifest.permission.KILL_BACKGROUND_PROCESSES; 5552 Slog.w(TAG, msg); 5553 throw new SecurityException(msg); 5554 } 5555 5556 final long callingId = Binder.clearCallingIdentity(); 5557 try { 5558 synchronized (this) { 5559 final ArrayList<ProcessRecord> procs = new ArrayList<>(); 5560 final int NP = mProcessNames.getMap().size(); 5561 for (int ip = 0; ip < NP; ip++) { 5562 final SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 5563 final int NA = apps.size(); 5564 for (int ia = 0; ia < NA; ia++) { 5565 final ProcessRecord app = apps.valueAt(ia); 5566 if (app.removed) { 5567 procs.add(app); 5568 } else if ((minTargetSdk < 0 || app.info.targetSdkVersion < minTargetSdk) 5569 && (maxProcState < 0 || app.setProcState > maxProcState)) { 5570 app.removed = true; 5571 procs.add(app); 5572 } 5573 } 5574 } 5575 5576 final int N = procs.size(); 5577 for (int i = 0; i < N; i++) { 5578 removeProcessLocked(procs.get(i), false, true, "kill all background except"); 5579 } 5580 } 5581 } finally { 5582 Binder.restoreCallingIdentity(callingId); 5583 } 5584 } 5585 5586 @Override 5587 public void forceStopPackage(final String packageName, int userId) { 5588 if (checkCallingPermission(android.Manifest.permission.FORCE_STOP_PACKAGES) 5589 != PackageManager.PERMISSION_GRANTED) { 5590 String msg = "Permission Denial: forceStopPackage() from pid=" 5591 + Binder.getCallingPid() 5592 + ", uid=" + Binder.getCallingUid() 5593 + " requires " + android.Manifest.permission.FORCE_STOP_PACKAGES; 5594 Slog.w(TAG, msg); 5595 throw new SecurityException(msg); 5596 } 5597 final int callingPid = Binder.getCallingPid(); 5598 userId = mUserController.handleIncomingUser(callingPid, Binder.getCallingUid(), 5599 userId, true, ALLOW_FULL_ONLY, "forceStopPackage", null); 5600 long callingId = Binder.clearCallingIdentity(); 5601 try { 5602 IPackageManager pm = AppGlobals.getPackageManager(); 5603 synchronized(this) { 5604 int[] users = userId == UserHandle.USER_ALL 5605 ? mUserController.getUsers() : new int[] { userId }; 5606 for (int user : users) { 5607 int pkgUid = -1; 5608 try { 5609 pkgUid = pm.getPackageUid(packageName, MATCH_DEBUG_TRIAGED_MISSING, 5610 user); 5611 } catch (RemoteException e) { 5612 } 5613 if (pkgUid == -1) { 5614 Slog.w(TAG, "Invalid packageName: " + packageName); 5615 continue; 5616 } 5617 try { 5618 pm.setPackageStoppedState(packageName, true, user); 5619 } catch (RemoteException e) { 5620 } catch (IllegalArgumentException e) { 5621 Slog.w(TAG, "Failed trying to unstop package " 5622 + packageName + ": " + e); 5623 } 5624 if (mUserController.isUserRunningLocked(user, 0)) { 5625 forceStopPackageLocked(packageName, pkgUid, "from pid " + callingPid); 5626 } 5627 } 5628 } 5629 } finally { 5630 Binder.restoreCallingIdentity(callingId); 5631 } 5632 } 5633 5634 @Override 5635 public void addPackageDependency(String packageName) { 5636 synchronized (this) { 5637 int callingPid = Binder.getCallingPid(); 5638 if (callingPid == Process.myPid()) { 5639 // Yeah, um, no. 5640 return; 5641 } 5642 ProcessRecord proc; 5643 synchronized (mPidsSelfLocked) { 5644 proc = mPidsSelfLocked.get(Binder.getCallingPid()); 5645 } 5646 if (proc != null) { 5647 if (proc.pkgDeps == null) { 5648 proc.pkgDeps = new ArraySet<String>(1); 5649 } 5650 proc.pkgDeps.add(packageName); 5651 } 5652 } 5653 } 5654 5655 /* 5656 * The pkg name and app id have to be specified. 5657 */ 5658 @Override 5659 public void killApplicationWithAppId(String pkg, int appid, String reason) { 5660 if (pkg == null) { 5661 return; 5662 } 5663 // Make sure the uid is valid. 5664 if (appid < 0) { 5665 Slog.w(TAG, "Invalid appid specified for pkg : " + pkg); 5666 return; 5667 } 5668 int callerUid = Binder.getCallingUid(); 5669 // Only the system server can kill an application 5670 if (UserHandle.getAppId(callerUid) == Process.SYSTEM_UID) { 5671 // Post an aysnc message to kill the application 5672 Message msg = mHandler.obtainMessage(KILL_APPLICATION_MSG); 5673 msg.arg1 = appid; 5674 msg.arg2 = 0; 5675 Bundle bundle = new Bundle(); 5676 bundle.putString("pkg", pkg); 5677 bundle.putString("reason", reason); 5678 msg.obj = bundle; 5679 mHandler.sendMessage(msg); 5680 } else { 5681 throw new SecurityException(callerUid + " cannot kill pkg: " + 5682 pkg); 5683 } 5684 } 5685 5686 @Override 5687 public void closeSystemDialogs(String reason) { 5688 enforceNotIsolatedCaller("closeSystemDialogs"); 5689 5690 final int pid = Binder.getCallingPid(); 5691 final int uid = Binder.getCallingUid(); 5692 final long origId = Binder.clearCallingIdentity(); 5693 try { 5694 synchronized (this) { 5695 // Only allow this from foreground processes, so that background 5696 // applications can't abuse it to prevent system UI from being shown. 5697 if (uid >= Process.FIRST_APPLICATION_UID) { 5698 ProcessRecord proc; 5699 synchronized (mPidsSelfLocked) { 5700 proc = mPidsSelfLocked.get(pid); 5701 } 5702 if (proc.curRawAdj > ProcessList.PERCEPTIBLE_APP_ADJ) { 5703 Slog.w(TAG, "Ignoring closeSystemDialogs " + reason 5704 + " from background process " + proc); 5705 return; 5706 } 5707 } 5708 closeSystemDialogsLocked(reason); 5709 } 5710 } finally { 5711 Binder.restoreCallingIdentity(origId); 5712 } 5713 } 5714 5715 void closeSystemDialogsLocked(String reason) { 5716 Intent intent = new Intent(Intent.ACTION_CLOSE_SYSTEM_DIALOGS); 5717 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 5718 | Intent.FLAG_RECEIVER_FOREGROUND); 5719 if (reason != null) { 5720 intent.putExtra("reason", reason); 5721 } 5722 mWindowManager.closeSystemDialogs(reason); 5723 5724 mStackSupervisor.closeSystemDialogsLocked(); 5725 5726 broadcastIntentLocked(null, null, intent, null, null, 0, null, null, null, 5727 AppOpsManager.OP_NONE, null, false, false, 5728 -1, Process.SYSTEM_UID, UserHandle.USER_ALL); 5729 } 5730 5731 @Override 5732 public Debug.MemoryInfo[] getProcessMemoryInfo(int[] pids) { 5733 enforceNotIsolatedCaller("getProcessMemoryInfo"); 5734 Debug.MemoryInfo[] infos = new Debug.MemoryInfo[pids.length]; 5735 for (int i=pids.length-1; i>=0; i--) { 5736 ProcessRecord proc; 5737 int oomAdj; 5738 synchronized (this) { 5739 synchronized (mPidsSelfLocked) { 5740 proc = mPidsSelfLocked.get(pids[i]); 5741 oomAdj = proc != null ? proc.setAdj : 0; 5742 } 5743 } 5744 infos[i] = new Debug.MemoryInfo(); 5745 Debug.getMemoryInfo(pids[i], infos[i]); 5746 if (proc != null) { 5747 synchronized (this) { 5748 if (proc.thread != null && proc.setAdj == oomAdj) { 5749 // Record this for posterity if the process has been stable. 5750 proc.baseProcessTracker.addPss(infos[i].getTotalPss(), 5751 infos[i].getTotalUss(), false, proc.pkgList); 5752 } 5753 } 5754 } 5755 } 5756 return infos; 5757 } 5758 5759 @Override 5760 public long[] getProcessPss(int[] pids) { 5761 enforceNotIsolatedCaller("getProcessPss"); 5762 long[] pss = new long[pids.length]; 5763 for (int i=pids.length-1; i>=0; i--) { 5764 ProcessRecord proc; 5765 int oomAdj; 5766 synchronized (this) { 5767 synchronized (mPidsSelfLocked) { 5768 proc = mPidsSelfLocked.get(pids[i]); 5769 oomAdj = proc != null ? proc.setAdj : 0; 5770 } 5771 } 5772 long[] tmpUss = new long[1]; 5773 pss[i] = Debug.getPss(pids[i], tmpUss, null); 5774 if (proc != null) { 5775 synchronized (this) { 5776 if (proc.thread != null && proc.setAdj == oomAdj) { 5777 // Record this for posterity if the process has been stable. 5778 proc.baseProcessTracker.addPss(pss[i], tmpUss[0], false, proc.pkgList); 5779 } 5780 } 5781 } 5782 } 5783 return pss; 5784 } 5785 5786 @Override 5787 public void killApplicationProcess(String processName, int uid) { 5788 if (processName == null) { 5789 return; 5790 } 5791 5792 int callerUid = Binder.getCallingUid(); 5793 // Only the system server can kill an application 5794 if (callerUid == Process.SYSTEM_UID) { 5795 synchronized (this) { 5796 ProcessRecord app = getProcessRecordLocked(processName, uid, true); 5797 if (app != null && app.thread != null) { 5798 try { 5799 app.thread.scheduleSuicide(); 5800 } catch (RemoteException e) { 5801 // If the other end already died, then our work here is done. 5802 } 5803 } else { 5804 Slog.w(TAG, "Process/uid not found attempting kill of " 5805 + processName + " / " + uid); 5806 } 5807 } 5808 } else { 5809 throw new SecurityException(callerUid + " cannot kill app process: " + 5810 processName); 5811 } 5812 } 5813 5814 private void forceStopPackageLocked(final String packageName, int uid, String reason) { 5815 forceStopPackageLocked(packageName, UserHandle.getAppId(uid), false, 5816 false, true, false, false, UserHandle.getUserId(uid), reason); 5817 Intent intent = new Intent(Intent.ACTION_PACKAGE_RESTARTED, 5818 Uri.fromParts("package", packageName, null)); 5819 if (!mProcessesReady) { 5820 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 5821 | Intent.FLAG_RECEIVER_FOREGROUND); 5822 } 5823 intent.putExtra(Intent.EXTRA_UID, uid); 5824 intent.putExtra(Intent.EXTRA_USER_HANDLE, UserHandle.getUserId(uid)); 5825 broadcastIntentLocked(null, null, intent, 5826 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 5827 null, false, false, MY_PID, Process.SYSTEM_UID, UserHandle.getUserId(uid)); 5828 } 5829 5830 5831 private final boolean killPackageProcessesLocked(String packageName, int appId, 5832 int userId, int minOomAdj, boolean callerWillRestart, boolean allowRestart, 5833 boolean doit, boolean evenPersistent, String reason) { 5834 ArrayList<ProcessRecord> procs = new ArrayList<>(); 5835 5836 // Remove all processes this package may have touched: all with the 5837 // same UID (except for the system or root user), and all whose name 5838 // matches the package name. 5839 final int NP = mProcessNames.getMap().size(); 5840 for (int ip=0; ip<NP; ip++) { 5841 SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 5842 final int NA = apps.size(); 5843 for (int ia=0; ia<NA; ia++) { 5844 ProcessRecord app = apps.valueAt(ia); 5845 if (app.persistent && !evenPersistent) { 5846 // we don't kill persistent processes 5847 continue; 5848 } 5849 if (app.removed) { 5850 if (doit) { 5851 procs.add(app); 5852 } 5853 continue; 5854 } 5855 5856 // Skip process if it doesn't meet our oom adj requirement. 5857 if (app.setAdj < minOomAdj) { 5858 continue; 5859 } 5860 5861 // If no package is specified, we call all processes under the 5862 // give user id. 5863 if (packageName == null) { 5864 if (userId != UserHandle.USER_ALL && app.userId != userId) { 5865 continue; 5866 } 5867 if (appId >= 0 && UserHandle.getAppId(app.uid) != appId) { 5868 continue; 5869 } 5870 // Package has been specified, we want to hit all processes 5871 // that match it. We need to qualify this by the processes 5872 // that are running under the specified app and user ID. 5873 } else { 5874 final boolean isDep = app.pkgDeps != null 5875 && app.pkgDeps.contains(packageName); 5876 if (!isDep && UserHandle.getAppId(app.uid) != appId) { 5877 continue; 5878 } 5879 if (userId != UserHandle.USER_ALL && app.userId != userId) { 5880 continue; 5881 } 5882 if (!app.pkgList.containsKey(packageName) && !isDep) { 5883 continue; 5884 } 5885 } 5886 5887 // Process has passed all conditions, kill it! 5888 if (!doit) { 5889 return true; 5890 } 5891 app.removed = true; 5892 procs.add(app); 5893 } 5894 } 5895 5896 int N = procs.size(); 5897 for (int i=0; i<N; i++) { 5898 removeProcessLocked(procs.get(i), callerWillRestart, allowRestart, reason); 5899 } 5900 updateOomAdjLocked(); 5901 return N > 0; 5902 } 5903 5904 private void cleanupDisabledPackageComponentsLocked( 5905 String packageName, int userId, boolean killProcess, String[] changedClasses) { 5906 5907 Set<String> disabledClasses = null; 5908 boolean packageDisabled = false; 5909 IPackageManager pm = AppGlobals.getPackageManager(); 5910 5911 if (changedClasses == null) { 5912 // Nothing changed... 5913 return; 5914 } 5915 5916 // Determine enable/disable state of the package and its components. 5917 int enabled = PackageManager.COMPONENT_ENABLED_STATE_DEFAULT; 5918 for (int i = changedClasses.length - 1; i >= 0; i--) { 5919 final String changedClass = changedClasses[i]; 5920 5921 if (changedClass.equals(packageName)) { 5922 try { 5923 // Entire package setting changed 5924 enabled = pm.getApplicationEnabledSetting(packageName, 5925 (userId != UserHandle.USER_ALL) ? userId : UserHandle.USER_SYSTEM); 5926 } catch (Exception e) { 5927 // No such package/component; probably racing with uninstall. In any 5928 // event it means we have nothing further to do here. 5929 return; 5930 } 5931 packageDisabled = enabled != PackageManager.COMPONENT_ENABLED_STATE_ENABLED 5932 && enabled != PackageManager.COMPONENT_ENABLED_STATE_DEFAULT; 5933 if (packageDisabled) { 5934 // Entire package is disabled. 5935 // No need to continue to check component states. 5936 disabledClasses = null; 5937 break; 5938 } 5939 } else { 5940 try { 5941 enabled = pm.getComponentEnabledSetting( 5942 new ComponentName(packageName, changedClass), 5943 (userId != UserHandle.USER_ALL) ? userId : UserHandle.USER_SYSTEM); 5944 } catch (Exception e) { 5945 // As above, probably racing with uninstall. 5946 return; 5947 } 5948 if (enabled != PackageManager.COMPONENT_ENABLED_STATE_ENABLED 5949 && enabled != PackageManager.COMPONENT_ENABLED_STATE_DEFAULT) { 5950 if (disabledClasses == null) { 5951 disabledClasses = new ArraySet<>(changedClasses.length); 5952 } 5953 disabledClasses.add(changedClass); 5954 } 5955 } 5956 } 5957 5958 if (!packageDisabled && disabledClasses == null) { 5959 // Nothing to do here... 5960 return; 5961 } 5962 5963 // Clean-up disabled activities. 5964 if (mStackSupervisor.finishDisabledPackageActivitiesLocked( 5965 packageName, disabledClasses, true, false, userId) && mBooted) { 5966 mStackSupervisor.resumeFocusedStackTopActivityLocked(); 5967 mStackSupervisor.scheduleIdleLocked(); 5968 } 5969 5970 // Clean-up disabled tasks 5971 cleanupDisabledPackageTasksLocked(packageName, disabledClasses, userId); 5972 5973 // Clean-up disabled services. 5974 mServices.bringDownDisabledPackageServicesLocked( 5975 packageName, disabledClasses, userId, false, killProcess, true); 5976 5977 // Clean-up disabled providers. 5978 ArrayList<ContentProviderRecord> providers = new ArrayList<>(); 5979 mProviderMap.collectPackageProvidersLocked( 5980 packageName, disabledClasses, true, false, userId, providers); 5981 for (int i = providers.size() - 1; i >= 0; i--) { 5982 removeDyingProviderLocked(null, providers.get(i), true); 5983 } 5984 5985 // Clean-up disabled broadcast receivers. 5986 for (int i = mBroadcastQueues.length - 1; i >= 0; i--) { 5987 mBroadcastQueues[i].cleanupDisabledPackageReceiversLocked( 5988 packageName, disabledClasses, userId, true); 5989 } 5990 5991 } 5992 5993 final boolean clearBroadcastQueueForUserLocked(int userId) { 5994 boolean didSomething = false; 5995 for (int i = mBroadcastQueues.length - 1; i >= 0; i--) { 5996 didSomething |= mBroadcastQueues[i].cleanupDisabledPackageReceiversLocked( 5997 null, null, userId, true); 5998 } 5999 return didSomething; 6000 } 6001 6002 final boolean forceStopPackageLocked(String packageName, int appId, 6003 boolean callerWillRestart, boolean purgeCache, boolean doit, 6004 boolean evenPersistent, boolean uninstalling, int userId, String reason) { 6005 int i; 6006 6007 if (userId == UserHandle.USER_ALL && packageName == null) { 6008 Slog.w(TAG, "Can't force stop all processes of all users, that is insane!"); 6009 } 6010 6011 if (appId < 0 && packageName != null) { 6012 try { 6013 appId = UserHandle.getAppId(AppGlobals.getPackageManager() 6014 .getPackageUid(packageName, MATCH_DEBUG_TRIAGED_MISSING, userId)); 6015 } catch (RemoteException e) { 6016 } 6017 } 6018 6019 if (doit) { 6020 if (packageName != null) { 6021 Slog.i(TAG, "Force stopping " + packageName + " appid=" + appId 6022 + " user=" + userId + ": " + reason); 6023 } else { 6024 Slog.i(TAG, "Force stopping u" + userId + ": " + reason); 6025 } 6026 6027 mAppErrors.resetProcessCrashTimeLocked(packageName == null, appId, userId); 6028 } 6029 6030 boolean didSomething = killPackageProcessesLocked(packageName, appId, userId, 6031 ProcessList.INVALID_ADJ, callerWillRestart, true, doit, evenPersistent, 6032 packageName == null ? ("stop user " + userId) : ("stop " + packageName)); 6033 6034 if (mStackSupervisor.finishDisabledPackageActivitiesLocked( 6035 packageName, null, doit, evenPersistent, userId)) { 6036 if (!doit) { 6037 return true; 6038 } 6039 didSomething = true; 6040 } 6041 6042 if (mServices.bringDownDisabledPackageServicesLocked( 6043 packageName, null, userId, evenPersistent, true, doit)) { 6044 if (!doit) { 6045 return true; 6046 } 6047 didSomething = true; 6048 } 6049 6050 if (packageName == null) { 6051 // Remove all sticky broadcasts from this user. 6052 mStickyBroadcasts.remove(userId); 6053 } 6054 6055 ArrayList<ContentProviderRecord> providers = new ArrayList<>(); 6056 if (mProviderMap.collectPackageProvidersLocked(packageName, null, doit, evenPersistent, 6057 userId, providers)) { 6058 if (!doit) { 6059 return true; 6060 } 6061 didSomething = true; 6062 } 6063 for (i = providers.size() - 1; i >= 0; i--) { 6064 removeDyingProviderLocked(null, providers.get(i), true); 6065 } 6066 6067 // Remove transient permissions granted from/to this package/user 6068 removeUriPermissionsForPackageLocked(packageName, userId, false); 6069 6070 if (doit) { 6071 for (i = mBroadcastQueues.length - 1; i >= 0; i--) { 6072 didSomething |= mBroadcastQueues[i].cleanupDisabledPackageReceiversLocked( 6073 packageName, null, userId, doit); 6074 } 6075 } 6076 6077 if (packageName == null || uninstalling) { 6078 // Remove pending intents. For now we only do this when force 6079 // stopping users, because we have some problems when doing this 6080 // for packages -- app widgets are not currently cleaned up for 6081 // such packages, so they can be left with bad pending intents. 6082 if (mIntentSenderRecords.size() > 0) { 6083 Iterator<WeakReference<PendingIntentRecord>> it 6084 = mIntentSenderRecords.values().iterator(); 6085 while (it.hasNext()) { 6086 WeakReference<PendingIntentRecord> wpir = it.next(); 6087 if (wpir == null) { 6088 it.remove(); 6089 continue; 6090 } 6091 PendingIntentRecord pir = wpir.get(); 6092 if (pir == null) { 6093 it.remove(); 6094 continue; 6095 } 6096 if (packageName == null) { 6097 // Stopping user, remove all objects for the user. 6098 if (pir.key.userId != userId) { 6099 // Not the same user, skip it. 6100 continue; 6101 } 6102 } else { 6103 if (UserHandle.getAppId(pir.uid) != appId) { 6104 // Different app id, skip it. 6105 continue; 6106 } 6107 if (userId != UserHandle.USER_ALL && pir.key.userId != userId) { 6108 // Different user, skip it. 6109 continue; 6110 } 6111 if (!pir.key.packageName.equals(packageName)) { 6112 // Different package, skip it. 6113 continue; 6114 } 6115 } 6116 if (!doit) { 6117 return true; 6118 } 6119 didSomething = true; 6120 it.remove(); 6121 pir.canceled = true; 6122 if (pir.key.activity != null && pir.key.activity.pendingResults != null) { 6123 pir.key.activity.pendingResults.remove(pir.ref); 6124 } 6125 } 6126 } 6127 } 6128 6129 if (doit) { 6130 if (purgeCache && packageName != null) { 6131 AttributeCache ac = AttributeCache.instance(); 6132 if (ac != null) { 6133 ac.removePackage(packageName); 6134 } 6135 } 6136 if (mBooted) { 6137 mStackSupervisor.resumeFocusedStackTopActivityLocked(); 6138 mStackSupervisor.scheduleIdleLocked(); 6139 } 6140 } 6141 6142 return didSomething; 6143 } 6144 6145 private final ProcessRecord removeProcessNameLocked(final String name, final int uid) { 6146 ProcessRecord old = mProcessNames.remove(name, uid); 6147 if (old != null) { 6148 old.uidRecord.numProcs--; 6149 if (old.uidRecord.numProcs == 0) { 6150 // No more processes using this uid, tell clients it is gone. 6151 if (DEBUG_UID_OBSERVERS) Slog.i(TAG_UID_OBSERVERS, 6152 "No more processes in " + old.uidRecord); 6153 enqueueUidChangeLocked(old.uidRecord, -1, UidRecord.CHANGE_GONE); 6154 mActiveUids.remove(uid); 6155 noteUidProcessState(uid, ActivityManager.PROCESS_STATE_NONEXISTENT); 6156 } 6157 old.uidRecord = null; 6158 } 6159 mIsolatedProcesses.remove(uid); 6160 return old; 6161 } 6162 6163 private final void addProcessNameLocked(ProcessRecord proc) { 6164 // We shouldn't already have a process under this name, but just in case we 6165 // need to clean up whatever may be there now. 6166 ProcessRecord old = removeProcessNameLocked(proc.processName, proc.uid); 6167 if (old == proc && proc.persistent) { 6168 // We are re-adding a persistent process. Whatevs! Just leave it there. 6169 Slog.w(TAG, "Re-adding persistent process " + proc); 6170 } else if (old != null) { 6171 Slog.wtf(TAG, "Already have existing proc " + old + " when adding " + proc); 6172 } 6173 UidRecord uidRec = mActiveUids.get(proc.uid); 6174 if (uidRec == null) { 6175 uidRec = new UidRecord(proc.uid); 6176 // This is the first appearance of the uid, report it now! 6177 if (DEBUG_UID_OBSERVERS) Slog.i(TAG_UID_OBSERVERS, 6178 "Creating new process uid: " + uidRec); 6179 mActiveUids.put(proc.uid, uidRec); 6180 noteUidProcessState(uidRec.uid, uidRec.curProcState); 6181 enqueueUidChangeLocked(uidRec, -1, UidRecord.CHANGE_ACTIVE); 6182 } 6183 proc.uidRecord = uidRec; 6184 uidRec.numProcs++; 6185 mProcessNames.put(proc.processName, proc.uid, proc); 6186 if (proc.isolated) { 6187 mIsolatedProcesses.put(proc.uid, proc); 6188 } 6189 } 6190 6191 boolean removeProcessLocked(ProcessRecord app, 6192 boolean callerWillRestart, boolean allowRestart, String reason) { 6193 final String name = app.processName; 6194 final int uid = app.uid; 6195 if (DEBUG_PROCESSES) Slog.d(TAG_PROCESSES, 6196 "Force removing proc " + app.toShortString() + " (" + name + "/" + uid + ")"); 6197 6198 ProcessRecord old = mProcessNames.get(name, uid); 6199 if (old != app) { 6200 // This process is no longer active, so nothing to do. 6201 Slog.w(TAG, "Ignoring remove of inactive process: " + app); 6202 return false; 6203 } 6204 removeProcessNameLocked(name, uid); 6205 if (mHeavyWeightProcess == app) { 6206 mHandler.sendMessage(mHandler.obtainMessage(CANCEL_HEAVY_NOTIFICATION_MSG, 6207 mHeavyWeightProcess.userId, 0)); 6208 mHeavyWeightProcess = null; 6209 } 6210 boolean needRestart = false; 6211 if (app.pid > 0 && app.pid != MY_PID) { 6212 int pid = app.pid; 6213 synchronized (mPidsSelfLocked) { 6214 mPidsSelfLocked.remove(pid); 6215 mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app); 6216 } 6217 mBatteryStatsService.noteProcessFinish(app.processName, app.info.uid); 6218 if (app.isolated) { 6219 mBatteryStatsService.removeIsolatedUid(app.uid, app.info.uid); 6220 } 6221 boolean willRestart = false; 6222 if (app.persistent && !app.isolated) { 6223 if (!callerWillRestart) { 6224 willRestart = true; 6225 } else { 6226 needRestart = true; 6227 } 6228 } 6229 app.kill(reason, true); 6230 handleAppDiedLocked(app, willRestart, allowRestart); 6231 if (willRestart) { 6232 removeLruProcessLocked(app); 6233 addAppLocked(app.info, false, null /* ABI override */); 6234 } 6235 } else { 6236 mRemovedProcesses.add(app); 6237 } 6238 6239 return needRestart; 6240 } 6241 6242 private final void processContentProviderPublishTimedOutLocked(ProcessRecord app) { 6243 cleanupAppInLaunchingProvidersLocked(app, true); 6244 removeProcessLocked(app, false, true, "timeout publishing content providers"); 6245 } 6246 6247 private final void processStartTimedOutLocked(ProcessRecord app) { 6248 final int pid = app.pid; 6249 boolean gone = false; 6250 synchronized (mPidsSelfLocked) { 6251 ProcessRecord knownApp = mPidsSelfLocked.get(pid); 6252 if (knownApp != null && knownApp.thread == null) { 6253 mPidsSelfLocked.remove(pid); 6254 gone = true; 6255 } 6256 } 6257 6258 if (gone) { 6259 Slog.w(TAG, "Process " + app + " failed to attach"); 6260 EventLog.writeEvent(EventLogTags.AM_PROCESS_START_TIMEOUT, app.userId, 6261 pid, app.uid, app.processName); 6262 removeProcessNameLocked(app.processName, app.uid); 6263 if (mHeavyWeightProcess == app) { 6264 mHandler.sendMessage(mHandler.obtainMessage(CANCEL_HEAVY_NOTIFICATION_MSG, 6265 mHeavyWeightProcess.userId, 0)); 6266 mHeavyWeightProcess = null; 6267 } 6268 mBatteryStatsService.noteProcessFinish(app.processName, app.info.uid); 6269 if (app.isolated) { 6270 mBatteryStatsService.removeIsolatedUid(app.uid, app.info.uid); 6271 } 6272 // Take care of any launching providers waiting for this process. 6273 cleanupAppInLaunchingProvidersLocked(app, true); 6274 // Take care of any services that are waiting for the process. 6275 mServices.processStartTimedOutLocked(app); 6276 app.kill("start timeout", true); 6277 removeLruProcessLocked(app); 6278 if (mBackupTarget != null && mBackupTarget.app.pid == pid) { 6279 Slog.w(TAG, "Unattached app died before backup, skipping"); 6280 try { 6281 IBackupManager bm = IBackupManager.Stub.asInterface( 6282 ServiceManager.getService(Context.BACKUP_SERVICE)); 6283 bm.agentDisconnected(app.info.packageName); 6284 } catch (RemoteException e) { 6285 // Can't happen; the backup manager is local 6286 } 6287 } 6288 if (isPendingBroadcastProcessLocked(pid)) { 6289 Slog.w(TAG, "Unattached app died before broadcast acknowledged, skipping"); 6290 skipPendingBroadcastLocked(pid); 6291 } 6292 } else { 6293 Slog.w(TAG, "Spurious process start timeout - pid not known for " + app); 6294 } 6295 } 6296 6297 private final boolean attachApplicationLocked(IApplicationThread thread, 6298 int pid) { 6299 6300 // Find the application record that is being attached... either via 6301 // the pid if we are running in multiple processes, or just pull the 6302 // next app record if we are emulating process with anonymous threads. 6303 ProcessRecord app; 6304 if (pid != MY_PID && pid >= 0) { 6305 synchronized (mPidsSelfLocked) { 6306 app = mPidsSelfLocked.get(pid); 6307 } 6308 } else { 6309 app = null; 6310 } 6311 6312 if (app == null) { 6313 Slog.w(TAG, "No pending application record for pid " + pid 6314 + " (IApplicationThread " + thread + "); dropping process"); 6315 EventLog.writeEvent(EventLogTags.AM_DROP_PROCESS, pid); 6316 if (pid > 0 && pid != MY_PID) { 6317 Process.killProcessQuiet(pid); 6318 //TODO: killProcessGroup(app.info.uid, pid); 6319 } else { 6320 try { 6321 thread.scheduleExit(); 6322 } catch (Exception e) { 6323 // Ignore exceptions. 6324 } 6325 } 6326 return false; 6327 } 6328 6329 // If this application record is still attached to a previous 6330 // process, clean it up now. 6331 if (app.thread != null) { 6332 handleAppDiedLocked(app, true, true); 6333 } 6334 6335 // Tell the process all about itself. 6336 6337 if (DEBUG_ALL) Slog.v( 6338 TAG, "Binding process pid " + pid + " to record " + app); 6339 6340 final String processName = app.processName; 6341 try { 6342 AppDeathRecipient adr = new AppDeathRecipient( 6343 app, pid, thread); 6344 thread.asBinder().linkToDeath(adr, 0); 6345 app.deathRecipient = adr; 6346 } catch (RemoteException e) { 6347 app.resetPackageList(mProcessStats); 6348 startProcessLocked(app, "link fail", processName); 6349 return false; 6350 } 6351 6352 EventLog.writeEvent(EventLogTags.AM_PROC_BOUND, app.userId, app.pid, app.processName); 6353 6354 app.makeActive(thread, mProcessStats); 6355 app.curAdj = app.setAdj = ProcessList.INVALID_ADJ; 6356 app.curSchedGroup = app.setSchedGroup = ProcessList.SCHED_GROUP_DEFAULT; 6357 app.forcingToForeground = null; 6358 updateProcessForegroundLocked(app, false, false); 6359 app.hasShownUi = false; 6360 app.debugging = false; 6361 app.cached = false; 6362 app.killedByAm = false; 6363 6364 // We carefully use the same state that PackageManager uses for 6365 // filtering, since we use this flag to decide if we need to install 6366 // providers when user is unlocked later 6367 app.unlocked = StorageManager.isUserKeyUnlocked(app.userId); 6368 6369 mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app); 6370 6371 boolean normalMode = mProcessesReady || isAllowedWhileBooting(app.info); 6372 List<ProviderInfo> providers = normalMode ? generateApplicationProvidersLocked(app) : null; 6373 6374 if (providers != null && checkAppInLaunchingProvidersLocked(app)) { 6375 Message msg = mHandler.obtainMessage(CONTENT_PROVIDER_PUBLISH_TIMEOUT_MSG); 6376 msg.obj = app; 6377 mHandler.sendMessageDelayed(msg, CONTENT_PROVIDER_PUBLISH_TIMEOUT); 6378 } 6379 6380 if (!normalMode) { 6381 Slog.i(TAG, "Launching preboot mode app: " + app); 6382 } 6383 6384 if (DEBUG_ALL) Slog.v( 6385 TAG, "New app record " + app 6386 + " thread=" + thread.asBinder() + " pid=" + pid); 6387 try { 6388 int testMode = IApplicationThread.DEBUG_OFF; 6389 if (mDebugApp != null && mDebugApp.equals(processName)) { 6390 testMode = mWaitForDebugger 6391 ? IApplicationThread.DEBUG_WAIT 6392 : IApplicationThread.DEBUG_ON; 6393 app.debugging = true; 6394 if (mDebugTransient) { 6395 mDebugApp = mOrigDebugApp; 6396 mWaitForDebugger = mOrigWaitForDebugger; 6397 } 6398 } 6399 String profileFile = app.instrumentationProfileFile; 6400 ParcelFileDescriptor profileFd = null; 6401 int samplingInterval = 0; 6402 boolean profileAutoStop = false; 6403 if (mProfileApp != null && mProfileApp.equals(processName)) { 6404 mProfileProc = app; 6405 profileFile = mProfileFile; 6406 profileFd = mProfileFd; 6407 samplingInterval = mSamplingInterval; 6408 profileAutoStop = mAutoStopProfiler; 6409 } 6410 boolean enableTrackAllocation = false; 6411 if (mTrackAllocationApp != null && mTrackAllocationApp.equals(processName)) { 6412 enableTrackAllocation = true; 6413 mTrackAllocationApp = null; 6414 } 6415 6416 // If the app is being launched for restore or full backup, set it up specially 6417 boolean isRestrictedBackupMode = false; 6418 if (mBackupTarget != null && mBackupAppName.equals(processName)) { 6419 isRestrictedBackupMode = mBackupTarget.appInfo.uid >= Process.FIRST_APPLICATION_UID 6420 && ((mBackupTarget.backupMode == BackupRecord.RESTORE) 6421 || (mBackupTarget.backupMode == BackupRecord.RESTORE_FULL) 6422 || (mBackupTarget.backupMode == BackupRecord.BACKUP_FULL)); 6423 } 6424 6425 if (app.instrumentationClass != null) { 6426 notifyPackageUse(app.instrumentationClass.getPackageName(), 6427 PackageManager.NOTIFY_PACKAGE_USE_INSTRUMENTATION); 6428 } 6429 if (DEBUG_CONFIGURATION) Slog.v(TAG_CONFIGURATION, "Binding proc " 6430 + processName + " with config " + mConfiguration); 6431 ApplicationInfo appInfo = app.instrumentationInfo != null 6432 ? app.instrumentationInfo : app.info; 6433 app.compat = compatibilityInfoForPackageLocked(appInfo); 6434 if (profileFd != null) { 6435 profileFd = profileFd.dup(); 6436 } 6437 ProfilerInfo profilerInfo = profileFile == null ? null 6438 : new ProfilerInfo(profileFile, profileFd, samplingInterval, profileAutoStop); 6439 thread.bindApplication(processName, appInfo, providers, app.instrumentationClass, 6440 profilerInfo, app.instrumentationArguments, app.instrumentationWatcher, 6441 app.instrumentationUiAutomationConnection, testMode, 6442 mBinderTransactionTrackingEnabled, enableTrackAllocation, 6443 isRestrictedBackupMode || !normalMode, app.persistent, 6444 new Configuration(mConfiguration), app.compat, 6445 getCommonServicesLocked(app.isolated), 6446 mCoreSettingsObserver.getCoreSettingsLocked()); 6447 updateLruProcessLocked(app, false, null); 6448 app.lastRequestedGc = app.lastLowMemory = SystemClock.uptimeMillis(); 6449 } catch (Exception e) { 6450 // todo: Yikes! What should we do? For now we will try to 6451 // start another process, but that could easily get us in 6452 // an infinite loop of restarting processes... 6453 Slog.wtf(TAG, "Exception thrown during bind of " + app, e); 6454 6455 app.resetPackageList(mProcessStats); 6456 app.unlinkDeathRecipient(); 6457 startProcessLocked(app, "bind fail", processName); 6458 return false; 6459 } 6460 6461 // Remove this record from the list of starting applications. 6462 mPersistentStartingProcesses.remove(app); 6463 if (DEBUG_PROCESSES && mProcessesOnHold.contains(app)) Slog.v(TAG_PROCESSES, 6464 "Attach application locked removing on hold: " + app); 6465 mProcessesOnHold.remove(app); 6466 6467 boolean badApp = false; 6468 boolean didSomething = false; 6469 6470 // See if the top visible activity is waiting to run in this process... 6471 if (normalMode) { 6472 try { 6473 if (mStackSupervisor.attachApplicationLocked(app)) { 6474 didSomething = true; 6475 } 6476 } catch (Exception e) { 6477 Slog.wtf(TAG, "Exception thrown launching activities in " + app, e); 6478 badApp = true; 6479 } 6480 } 6481 6482 // Find any services that should be running in this process... 6483 if (!badApp) { 6484 try { 6485 didSomething |= mServices.attachApplicationLocked(app, processName); 6486 } catch (Exception e) { 6487 Slog.wtf(TAG, "Exception thrown starting services in " + app, e); 6488 badApp = true; 6489 } 6490 } 6491 6492 // Check if a next-broadcast receiver is in this process... 6493 if (!badApp && isPendingBroadcastProcessLocked(pid)) { 6494 try { 6495 didSomething |= sendPendingBroadcastsLocked(app); 6496 } catch (Exception e) { 6497 // If the app died trying to launch the receiver we declare it 'bad' 6498 Slog.wtf(TAG, "Exception thrown dispatching broadcasts in " + app, e); 6499 badApp = true; 6500 } 6501 } 6502 6503 // Check whether the next backup agent is in this process... 6504 if (!badApp && mBackupTarget != null && mBackupTarget.appInfo.uid == app.uid) { 6505 if (DEBUG_BACKUP) Slog.v(TAG_BACKUP, 6506 "New app is backup target, launching agent for " + app); 6507 notifyPackageUse(mBackupTarget.appInfo.packageName, 6508 PackageManager.NOTIFY_PACKAGE_USE_BACKUP); 6509 try { 6510 thread.scheduleCreateBackupAgent(mBackupTarget.appInfo, 6511 compatibilityInfoForPackageLocked(mBackupTarget.appInfo), 6512 mBackupTarget.backupMode); 6513 } catch (Exception e) { 6514 Slog.wtf(TAG, "Exception thrown creating backup agent in " + app, e); 6515 badApp = true; 6516 } 6517 } 6518 6519 if (badApp) { 6520 app.kill("error during init", true); 6521 handleAppDiedLocked(app, false, true); 6522 return false; 6523 } 6524 6525 if (!didSomething) { 6526 updateOomAdjLocked(); 6527 } 6528 6529 return true; 6530 } 6531 6532 @Override 6533 public final void attachApplication(IApplicationThread thread) { 6534 synchronized (this) { 6535 int callingPid = Binder.getCallingPid(); 6536 final long origId = Binder.clearCallingIdentity(); 6537 attachApplicationLocked(thread, callingPid); 6538 Binder.restoreCallingIdentity(origId); 6539 } 6540 } 6541 6542 @Override 6543 public final void activityIdle(IBinder token, Configuration config, boolean stopProfiling) { 6544 final long origId = Binder.clearCallingIdentity(); 6545 synchronized (this) { 6546 ActivityStack stack = ActivityRecord.getStackLocked(token); 6547 if (stack != null) { 6548 ActivityRecord r = 6549 mStackSupervisor.activityIdleInternalLocked(token, false, config); 6550 if (stopProfiling) { 6551 if ((mProfileProc == r.app) && (mProfileFd != null)) { 6552 try { 6553 mProfileFd.close(); 6554 } catch (IOException e) { 6555 } 6556 clearProfilerLocked(); 6557 } 6558 } 6559 } 6560 } 6561 Binder.restoreCallingIdentity(origId); 6562 } 6563 6564 void postFinishBooting(boolean finishBooting, boolean enableScreen) { 6565 mHandler.sendMessage(mHandler.obtainMessage(FINISH_BOOTING_MSG, 6566 finishBooting ? 1 : 0, enableScreen ? 1 : 0)); 6567 } 6568 6569 void enableScreenAfterBoot() { 6570 EventLog.writeEvent(EventLogTags.BOOT_PROGRESS_ENABLE_SCREEN, 6571 SystemClock.uptimeMillis()); 6572 mWindowManager.enableScreenAfterBoot(); 6573 6574 synchronized (this) { 6575 updateEventDispatchingLocked(); 6576 } 6577 } 6578 6579 @Override 6580 public void showBootMessage(final CharSequence msg, final boolean always) { 6581 if (Binder.getCallingUid() != Process.myUid()) { 6582 // These days only the core system can call this, so apps can't get in 6583 // the way of what we show about running them. 6584 } 6585 mWindowManager.showBootMessage(msg, always); 6586 } 6587 6588 @Override 6589 public void keyguardWaitingForActivityDrawn() { 6590 enforceNotIsolatedCaller("keyguardWaitingForActivityDrawn"); 6591 final long token = Binder.clearCallingIdentity(); 6592 try { 6593 synchronized (this) { 6594 if (DEBUG_LOCKSCREEN) logLockScreen(""); 6595 mWindowManager.keyguardWaitingForActivityDrawn(); 6596 if (mLockScreenShown == LOCK_SCREEN_SHOWN) { 6597 mLockScreenShown = LOCK_SCREEN_LEAVING; 6598 updateSleepIfNeededLocked(); 6599 } 6600 } 6601 } finally { 6602 Binder.restoreCallingIdentity(token); 6603 } 6604 } 6605 6606 @Override 6607 public void keyguardGoingAway(int flags) { 6608 enforceNotIsolatedCaller("keyguardGoingAway"); 6609 final long token = Binder.clearCallingIdentity(); 6610 try { 6611 synchronized (this) { 6612 if (DEBUG_LOCKSCREEN) logLockScreen(""); 6613 mWindowManager.keyguardGoingAway(flags); 6614 if (mLockScreenShown == LOCK_SCREEN_SHOWN) { 6615 mLockScreenShown = LOCK_SCREEN_HIDDEN; 6616 updateSleepIfNeededLocked(); 6617 6618 // Some stack visibility might change (e.g. docked stack) 6619 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0, !PRESERVE_WINDOWS); 6620 applyVrModeIfNeededLocked(mFocusedActivity, true); 6621 } 6622 } 6623 } finally { 6624 Binder.restoreCallingIdentity(token); 6625 } 6626 } 6627 6628 final void finishBooting() { 6629 synchronized (this) { 6630 if (!mBootAnimationComplete) { 6631 mCallFinishBooting = true; 6632 return; 6633 } 6634 mCallFinishBooting = false; 6635 } 6636 6637 ArraySet<String> completedIsas = new ArraySet<String>(); 6638 for (String abi : Build.SUPPORTED_ABIS) { 6639 Process.establishZygoteConnectionForAbi(abi); 6640 final String instructionSet = VMRuntime.getInstructionSet(abi); 6641 if (!completedIsas.contains(instructionSet)) { 6642 try { 6643 mInstaller.markBootComplete(VMRuntime.getInstructionSet(abi)); 6644 } catch (InstallerException e) { 6645 Slog.w(TAG, "Unable to mark boot complete for abi: " + abi + " (" + 6646 e.getMessage() +")"); 6647 } 6648 completedIsas.add(instructionSet); 6649 } 6650 } 6651 6652 IntentFilter pkgFilter = new IntentFilter(); 6653 pkgFilter.addAction(Intent.ACTION_QUERY_PACKAGE_RESTART); 6654 pkgFilter.addDataScheme("package"); 6655 mContext.registerReceiver(new BroadcastReceiver() { 6656 @Override 6657 public void onReceive(Context context, Intent intent) { 6658 String[] pkgs = intent.getStringArrayExtra(Intent.EXTRA_PACKAGES); 6659 if (pkgs != null) { 6660 for (String pkg : pkgs) { 6661 synchronized (ActivityManagerService.this) { 6662 if (forceStopPackageLocked(pkg, -1, false, false, false, false, false, 6663 0, "query restart")) { 6664 setResultCode(Activity.RESULT_OK); 6665 return; 6666 } 6667 } 6668 } 6669 } 6670 } 6671 }, pkgFilter); 6672 6673 IntentFilter dumpheapFilter = new IntentFilter(); 6674 dumpheapFilter.addAction(DumpHeapActivity.ACTION_DELETE_DUMPHEAP); 6675 mContext.registerReceiver(new BroadcastReceiver() { 6676 @Override 6677 public void onReceive(Context context, Intent intent) { 6678 if (intent.getBooleanExtra(DumpHeapActivity.EXTRA_DELAY_DELETE, false)) { 6679 mHandler.sendEmptyMessageDelayed(POST_DUMP_HEAP_NOTIFICATION_MSG, 5*60*1000); 6680 } else { 6681 mHandler.sendEmptyMessage(POST_DUMP_HEAP_NOTIFICATION_MSG); 6682 } 6683 } 6684 }, dumpheapFilter); 6685 6686 // Let system services know. 6687 mSystemServiceManager.startBootPhase(SystemService.PHASE_BOOT_COMPLETED); 6688 6689 synchronized (this) { 6690 // Ensure that any processes we had put on hold are now started 6691 // up. 6692 final int NP = mProcessesOnHold.size(); 6693 if (NP > 0) { 6694 ArrayList<ProcessRecord> procs = 6695 new ArrayList<ProcessRecord>(mProcessesOnHold); 6696 for (int ip=0; ip<NP; ip++) { 6697 if (DEBUG_PROCESSES) Slog.v(TAG_PROCESSES, "Starting process on hold: " 6698 + procs.get(ip)); 6699 startProcessLocked(procs.get(ip), "on-hold", null); 6700 } 6701 } 6702 6703 if (mFactoryTest != FactoryTest.FACTORY_TEST_LOW_LEVEL) { 6704 // Start looking for apps that are abusing wake locks. 6705 Message nmsg = mHandler.obtainMessage(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 6706 mHandler.sendMessageDelayed(nmsg, POWER_CHECK_DELAY); 6707 // Tell anyone interested that we are done booting! 6708 SystemProperties.set("sys.boot_completed", "1"); 6709 6710 // And trigger dev.bootcomplete if we are not showing encryption progress 6711 if (!"trigger_restart_min_framework".equals(SystemProperties.get("vold.decrypt")) 6712 || "".equals(SystemProperties.get("vold.encrypt_progress"))) { 6713 SystemProperties.set("dev.bootcomplete", "1"); 6714 } 6715 mUserController.sendBootCompletedLocked( 6716 new IIntentReceiver.Stub() { 6717 @Override 6718 public void performReceive(Intent intent, int resultCode, 6719 String data, Bundle extras, boolean ordered, 6720 boolean sticky, int sendingUser) { 6721 synchronized (ActivityManagerService.this) { 6722 requestPssAllProcsLocked(SystemClock.uptimeMillis(), 6723 true, false); 6724 } 6725 } 6726 }); 6727 scheduleStartProfilesLocked(); 6728 } 6729 } 6730 } 6731 6732 @Override 6733 public void bootAnimationComplete() { 6734 final boolean callFinishBooting; 6735 synchronized (this) { 6736 callFinishBooting = mCallFinishBooting; 6737 mBootAnimationComplete = true; 6738 } 6739 if (callFinishBooting) { 6740 Trace.traceBegin(Trace.TRACE_TAG_ACTIVITY_MANAGER, "FinishBooting"); 6741 finishBooting(); 6742 Trace.traceEnd(Trace.TRACE_TAG_ACTIVITY_MANAGER); 6743 } 6744 } 6745 6746 final void ensureBootCompleted() { 6747 boolean booting; 6748 boolean enableScreen; 6749 synchronized (this) { 6750 booting = mBooting; 6751 mBooting = false; 6752 enableScreen = !mBooted; 6753 mBooted = true; 6754 } 6755 6756 if (booting) { 6757 Trace.traceBegin(Trace.TRACE_TAG_ACTIVITY_MANAGER, "FinishBooting"); 6758 finishBooting(); 6759 Trace.traceEnd(Trace.TRACE_TAG_ACTIVITY_MANAGER); 6760 } 6761 6762 if (enableScreen) { 6763 enableScreenAfterBoot(); 6764 } 6765 } 6766 6767 @Override 6768 public final void activityResumed(IBinder token) { 6769 final long origId = Binder.clearCallingIdentity(); 6770 synchronized(this) { 6771 ActivityStack stack = ActivityRecord.getStackLocked(token); 6772 if (stack != null) { 6773 stack.activityResumedLocked(token); 6774 } 6775 } 6776 Binder.restoreCallingIdentity(origId); 6777 } 6778 6779 @Override 6780 public final void activityPaused(IBinder token) { 6781 final long origId = Binder.clearCallingIdentity(); 6782 synchronized(this) { 6783 ActivityStack stack = ActivityRecord.getStackLocked(token); 6784 if (stack != null) { 6785 stack.activityPausedLocked(token, false); 6786 } 6787 } 6788 Binder.restoreCallingIdentity(origId); 6789 } 6790 6791 @Override 6792 public final void activityStopped(IBinder token, Bundle icicle, 6793 PersistableBundle persistentState, CharSequence description) { 6794 if (DEBUG_ALL) Slog.v(TAG, "Activity stopped: token=" + token); 6795 6796 // Refuse possible leaked file descriptors 6797 if (icicle != null && icicle.hasFileDescriptors()) { 6798 throw new IllegalArgumentException("File descriptors passed in Bundle"); 6799 } 6800 6801 final long origId = Binder.clearCallingIdentity(); 6802 6803 synchronized (this) { 6804 ActivityRecord r = ActivityRecord.isInStackLocked(token); 6805 if (r != null) { 6806 r.task.stack.activityStoppedLocked(r, icicle, persistentState, description); 6807 } 6808 } 6809 6810 trimApplications(); 6811 6812 Binder.restoreCallingIdentity(origId); 6813 } 6814 6815 @Override 6816 public final void activityDestroyed(IBinder token) { 6817 if (DEBUG_SWITCH) Slog.v(TAG_SWITCH, "ACTIVITY DESTROYED: " + token); 6818 synchronized (this) { 6819 ActivityStack stack = ActivityRecord.getStackLocked(token); 6820 if (stack != null) { 6821 stack.activityDestroyedLocked(token, "activityDestroyed"); 6822 } 6823 } 6824 } 6825 6826 @Override 6827 public final void activityRelaunched(IBinder token) { 6828 final long origId = Binder.clearCallingIdentity(); 6829 synchronized (this) { 6830 mStackSupervisor.activityRelaunchedLocked(token); 6831 } 6832 Binder.restoreCallingIdentity(origId); 6833 } 6834 6835 @Override 6836 public void reportSizeConfigurations(IBinder token, int[] horizontalSizeConfiguration, 6837 int[] verticalSizeConfigurations, int[] smallestSizeConfigurations) { 6838 if (DEBUG_CONFIGURATION) Slog.v(TAG, "Report configuration: " + token + " " 6839 + horizontalSizeConfiguration + " " + verticalSizeConfigurations); 6840 synchronized (this) { 6841 ActivityRecord record = ActivityRecord.isInStackLocked(token); 6842 if (record == null) { 6843 throw new IllegalArgumentException("reportSizeConfigurations: ActivityRecord not " 6844 + "found for: " + token); 6845 } 6846 record.setSizeConfigurations(horizontalSizeConfiguration, 6847 verticalSizeConfigurations, smallestSizeConfigurations); 6848 } 6849 } 6850 6851 @Override 6852 public final void backgroundResourcesReleased(IBinder token) { 6853 final long origId = Binder.clearCallingIdentity(); 6854 try { 6855 synchronized (this) { 6856 ActivityStack stack = ActivityRecord.getStackLocked(token); 6857 if (stack != null) { 6858 stack.backgroundResourcesReleased(); 6859 } 6860 } 6861 } finally { 6862 Binder.restoreCallingIdentity(origId); 6863 } 6864 } 6865 6866 @Override 6867 public final void notifyLaunchTaskBehindComplete(IBinder token) { 6868 mStackSupervisor.scheduleLaunchTaskBehindComplete(token); 6869 } 6870 6871 @Override 6872 public final void notifyEnterAnimationComplete(IBinder token) { 6873 mHandler.sendMessage(mHandler.obtainMessage(ENTER_ANIMATION_COMPLETE_MSG, token)); 6874 } 6875 6876 @Override 6877 public String getCallingPackage(IBinder token) { 6878 synchronized (this) { 6879 ActivityRecord r = getCallingRecordLocked(token); 6880 return r != null ? r.info.packageName : null; 6881 } 6882 } 6883 6884 @Override 6885 public ComponentName getCallingActivity(IBinder token) { 6886 synchronized (this) { 6887 ActivityRecord r = getCallingRecordLocked(token); 6888 return r != null ? r.intent.getComponent() : null; 6889 } 6890 } 6891 6892 private ActivityRecord getCallingRecordLocked(IBinder token) { 6893 ActivityRecord r = ActivityRecord.isInStackLocked(token); 6894 if (r == null) { 6895 return null; 6896 } 6897 return r.resultTo; 6898 } 6899 6900 @Override 6901 public ComponentName getActivityClassForToken(IBinder token) { 6902 synchronized(this) { 6903 ActivityRecord r = ActivityRecord.isInStackLocked(token); 6904 if (r == null) { 6905 return null; 6906 } 6907 return r.intent.getComponent(); 6908 } 6909 } 6910 6911 @Override 6912 public String getPackageForToken(IBinder token) { 6913 synchronized(this) { 6914 ActivityRecord r = ActivityRecord.isInStackLocked(token); 6915 if (r == null) { 6916 return null; 6917 } 6918 return r.packageName; 6919 } 6920 } 6921 6922 @Override 6923 public boolean isRootVoiceInteraction(IBinder token) { 6924 synchronized(this) { 6925 ActivityRecord r = ActivityRecord.isInStackLocked(token); 6926 if (r == null) { 6927 return false; 6928 } 6929 return r.rootVoiceInteraction; 6930 } 6931 } 6932 6933 @Override 6934 public IIntentSender getIntentSender(int type, 6935 String packageName, IBinder token, String resultWho, 6936 int requestCode, Intent[] intents, String[] resolvedTypes, 6937 int flags, Bundle bOptions, int userId) { 6938 enforceNotIsolatedCaller("getIntentSender"); 6939 // Refuse possible leaked file descriptors 6940 if (intents != null) { 6941 if (intents.length < 1) { 6942 throw new IllegalArgumentException("Intents array length must be >= 1"); 6943 } 6944 for (int i=0; i<intents.length; i++) { 6945 Intent intent = intents[i]; 6946 if (intent != null) { 6947 if (intent.hasFileDescriptors()) { 6948 throw new IllegalArgumentException("File descriptors passed in Intent"); 6949 } 6950 if (type == ActivityManager.INTENT_SENDER_BROADCAST && 6951 (intent.getFlags()&Intent.FLAG_RECEIVER_BOOT_UPGRADE) != 0) { 6952 throw new IllegalArgumentException( 6953 "Can't use FLAG_RECEIVER_BOOT_UPGRADE here"); 6954 } 6955 intents[i] = new Intent(intent); 6956 } 6957 } 6958 if (resolvedTypes != null && resolvedTypes.length != intents.length) { 6959 throw new IllegalArgumentException( 6960 "Intent array length does not match resolvedTypes length"); 6961 } 6962 } 6963 if (bOptions != null) { 6964 if (bOptions.hasFileDescriptors()) { 6965 throw new IllegalArgumentException("File descriptors passed in options"); 6966 } 6967 } 6968 6969 synchronized(this) { 6970 int callingUid = Binder.getCallingUid(); 6971 int origUserId = userId; 6972 userId = mUserController.handleIncomingUser(Binder.getCallingPid(), callingUid, userId, 6973 type == ActivityManager.INTENT_SENDER_BROADCAST, 6974 ALLOW_NON_FULL, "getIntentSender", null); 6975 if (origUserId == UserHandle.USER_CURRENT) { 6976 // We don't want to evaluate this until the pending intent is 6977 // actually executed. However, we do want to always do the 6978 // security checking for it above. 6979 userId = UserHandle.USER_CURRENT; 6980 } 6981 try { 6982 if (callingUid != 0 && callingUid != Process.SYSTEM_UID) { 6983 final int uid = AppGlobals.getPackageManager().getPackageUid(packageName, 6984 MATCH_DEBUG_TRIAGED_MISSING, UserHandle.getUserId(callingUid)); 6985 if (!UserHandle.isSameApp(callingUid, uid)) { 6986 String msg = "Permission Denial: getIntentSender() from pid=" 6987 + Binder.getCallingPid() 6988 + ", uid=" + Binder.getCallingUid() 6989 + ", (need uid=" + uid + ")" 6990 + " is not allowed to send as package " + packageName; 6991 Slog.w(TAG, msg); 6992 throw new SecurityException(msg); 6993 } 6994 } 6995 6996 return getIntentSenderLocked(type, packageName, callingUid, userId, 6997 token, resultWho, requestCode, intents, resolvedTypes, flags, bOptions); 6998 6999 } catch (RemoteException e) { 7000 throw new SecurityException(e); 7001 } 7002 } 7003 } 7004 7005 IIntentSender getIntentSenderLocked(int type, String packageName, 7006 int callingUid, int userId, IBinder token, String resultWho, 7007 int requestCode, Intent[] intents, String[] resolvedTypes, int flags, 7008 Bundle bOptions) { 7009 if (DEBUG_MU) Slog.v(TAG_MU, "getIntentSenderLocked(): uid=" + callingUid); 7010 ActivityRecord activity = null; 7011 if (type == ActivityManager.INTENT_SENDER_ACTIVITY_RESULT) { 7012 activity = ActivityRecord.isInStackLocked(token); 7013 if (activity == null) { 7014 Slog.w(TAG, "Failed createPendingResult: activity " + token + " not in any stack"); 7015 return null; 7016 } 7017 if (activity.finishing) { 7018 Slog.w(TAG, "Failed createPendingResult: activity " + activity + " is finishing"); 7019 return null; 7020 } 7021 } 7022 7023 // We're going to be splicing together extras before sending, so we're 7024 // okay poking into any contained extras. 7025 if (intents != null) { 7026 for (int i = 0; i < intents.length; i++) { 7027 intents[i].setDefusable(true); 7028 } 7029 } 7030 Bundle.setDefusable(bOptions, true); 7031 7032 final boolean noCreate = (flags&PendingIntent.FLAG_NO_CREATE) != 0; 7033 final boolean cancelCurrent = (flags&PendingIntent.FLAG_CANCEL_CURRENT) != 0; 7034 final boolean updateCurrent = (flags&PendingIntent.FLAG_UPDATE_CURRENT) != 0; 7035 flags &= ~(PendingIntent.FLAG_NO_CREATE|PendingIntent.FLAG_CANCEL_CURRENT 7036 |PendingIntent.FLAG_UPDATE_CURRENT); 7037 7038 PendingIntentRecord.Key key = new PendingIntentRecord.Key( 7039 type, packageName, activity, resultWho, 7040 requestCode, intents, resolvedTypes, flags, bOptions, userId); 7041 WeakReference<PendingIntentRecord> ref; 7042 ref = mIntentSenderRecords.get(key); 7043 PendingIntentRecord rec = ref != null ? ref.get() : null; 7044 if (rec != null) { 7045 if (!cancelCurrent) { 7046 if (updateCurrent) { 7047 if (rec.key.requestIntent != null) { 7048 rec.key.requestIntent.replaceExtras(intents != null ? 7049 intents[intents.length - 1] : null); 7050 } 7051 if (intents != null) { 7052 intents[intents.length-1] = rec.key.requestIntent; 7053 rec.key.allIntents = intents; 7054 rec.key.allResolvedTypes = resolvedTypes; 7055 } else { 7056 rec.key.allIntents = null; 7057 rec.key.allResolvedTypes = null; 7058 } 7059 } 7060 return rec; 7061 } 7062 rec.canceled = true; 7063 mIntentSenderRecords.remove(key); 7064 } 7065 if (noCreate) { 7066 return rec; 7067 } 7068 rec = new PendingIntentRecord(this, key, callingUid); 7069 mIntentSenderRecords.put(key, rec.ref); 7070 if (type == ActivityManager.INTENT_SENDER_ACTIVITY_RESULT) { 7071 if (activity.pendingResults == null) { 7072 activity.pendingResults 7073 = new HashSet<WeakReference<PendingIntentRecord>>(); 7074 } 7075 activity.pendingResults.add(rec.ref); 7076 } 7077 return rec; 7078 } 7079 7080 @Override 7081 public int sendIntentSender(IIntentSender target, int code, Intent intent, String resolvedType, 7082 IIntentReceiver finishedReceiver, String requiredPermission, Bundle options) { 7083 if (target instanceof PendingIntentRecord) { 7084 return ((PendingIntentRecord)target).sendWithResult(code, intent, resolvedType, 7085 finishedReceiver, requiredPermission, options); 7086 } else { 7087 if (intent == null) { 7088 // Weird case: someone has given us their own custom IIntentSender, and now 7089 // they have someone else trying to send to it but of course this isn't 7090 // really a PendingIntent, so there is no base Intent, and the caller isn't 7091 // supplying an Intent... but we never want to dispatch a null Intent to 7092 // a receiver, so um... let's make something up. 7093 Slog.wtf(TAG, "Can't use null intent with direct IIntentSender call"); 7094 intent = new Intent(Intent.ACTION_MAIN); 7095 } 7096 try { 7097 target.send(code, intent, resolvedType, null, requiredPermission, options); 7098 } catch (RemoteException e) { 7099 } 7100 // Platform code can rely on getting a result back when the send is done, but if 7101 // this intent sender is from outside of the system we can't rely on it doing that. 7102 // So instead we don't give it the result receiver, and instead just directly 7103 // report the finish immediately. 7104 if (finishedReceiver != null) { 7105 try { 7106 finishedReceiver.performReceive(intent, 0, 7107 null, null, false, false, UserHandle.getCallingUserId()); 7108 } catch (RemoteException e) { 7109 } 7110 } 7111 return 0; 7112 } 7113 } 7114 7115 @Override 7116 public void cancelIntentSender(IIntentSender sender) { 7117 if (!(sender instanceof PendingIntentRecord)) { 7118 return; 7119 } 7120 synchronized(this) { 7121 PendingIntentRecord rec = (PendingIntentRecord)sender; 7122 try { 7123 final int uid = AppGlobals.getPackageManager().getPackageUid(rec.key.packageName, 7124 MATCH_DEBUG_TRIAGED_MISSING, UserHandle.getCallingUserId()); 7125 if (!UserHandle.isSameApp(uid, Binder.getCallingUid())) { 7126 String msg = "Permission Denial: cancelIntentSender() from pid=" 7127 + Binder.getCallingPid() 7128 + ", uid=" + Binder.getCallingUid() 7129 + " is not allowed to cancel packges " 7130 + rec.key.packageName; 7131 Slog.w(TAG, msg); 7132 throw new SecurityException(msg); 7133 } 7134 } catch (RemoteException e) { 7135 throw new SecurityException(e); 7136 } 7137 cancelIntentSenderLocked(rec, true); 7138 } 7139 } 7140 7141 void cancelIntentSenderLocked(PendingIntentRecord rec, boolean cleanActivity) { 7142 rec.canceled = true; 7143 mIntentSenderRecords.remove(rec.key); 7144 if (cleanActivity && rec.key.activity != null) { 7145 rec.key.activity.pendingResults.remove(rec.ref); 7146 } 7147 } 7148 7149 @Override 7150 public String getPackageForIntentSender(IIntentSender pendingResult) { 7151 if (!(pendingResult instanceof PendingIntentRecord)) { 7152 return null; 7153 } 7154 try { 7155 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 7156 return res.key.packageName; 7157 } catch (ClassCastException e) { 7158 } 7159 return null; 7160 } 7161 7162 @Override 7163 public int getUidForIntentSender(IIntentSender sender) { 7164 if (sender instanceof PendingIntentRecord) { 7165 try { 7166 PendingIntentRecord res = (PendingIntentRecord)sender; 7167 return res.uid; 7168 } catch (ClassCastException e) { 7169 } 7170 } 7171 return -1; 7172 } 7173 7174 @Override 7175 public boolean isIntentSenderTargetedToPackage(IIntentSender pendingResult) { 7176 if (!(pendingResult instanceof PendingIntentRecord)) { 7177 return false; 7178 } 7179 try { 7180 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 7181 if (res.key.allIntents == null) { 7182 return false; 7183 } 7184 for (int i=0; i<res.key.allIntents.length; i++) { 7185 Intent intent = res.key.allIntents[i]; 7186 if (intent.getPackage() != null && intent.getComponent() != null) { 7187 return false; 7188 } 7189 } 7190 return true; 7191 } catch (ClassCastException e) { 7192 } 7193 return false; 7194 } 7195 7196 @Override 7197 public boolean isIntentSenderAnActivity(IIntentSender pendingResult) { 7198 if (!(pendingResult instanceof PendingIntentRecord)) { 7199 return false; 7200 } 7201 try { 7202 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 7203 if (res.key.type == ActivityManager.INTENT_SENDER_ACTIVITY) { 7204 return true; 7205 } 7206 return false; 7207 } catch (ClassCastException e) { 7208 } 7209 return false; 7210 } 7211 7212 @Override 7213 public Intent getIntentForIntentSender(IIntentSender pendingResult) { 7214 enforceCallingPermission(Manifest.permission.GET_INTENT_SENDER_INTENT, 7215 "getIntentForIntentSender()"); 7216 if (!(pendingResult instanceof PendingIntentRecord)) { 7217 return null; 7218 } 7219 try { 7220 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 7221 return res.key.requestIntent != null ? new Intent(res.key.requestIntent) : null; 7222 } catch (ClassCastException e) { 7223 } 7224 return null; 7225 } 7226 7227 @Override 7228 public String getTagForIntentSender(IIntentSender pendingResult, String prefix) { 7229 if (!(pendingResult instanceof PendingIntentRecord)) { 7230 return null; 7231 } 7232 try { 7233 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 7234 synchronized (this) { 7235 return getTagForIntentSenderLocked(res, prefix); 7236 } 7237 } catch (ClassCastException e) { 7238 } 7239 return null; 7240 } 7241 7242 String getTagForIntentSenderLocked(PendingIntentRecord res, String prefix) { 7243 final Intent intent = res.key.requestIntent; 7244 if (intent != null) { 7245 if (res.lastTag != null && res.lastTagPrefix == prefix && (res.lastTagPrefix == null 7246 || res.lastTagPrefix.equals(prefix))) { 7247 return res.lastTag; 7248 } 7249 res.lastTagPrefix = prefix; 7250 final StringBuilder sb = new StringBuilder(128); 7251 if (prefix != null) { 7252 sb.append(prefix); 7253 } 7254 if (intent.getAction() != null) { 7255 sb.append(intent.getAction()); 7256 } else if (intent.getComponent() != null) { 7257 intent.getComponent().appendShortString(sb); 7258 } else { 7259 sb.append("?"); 7260 } 7261 return res.lastTag = sb.toString(); 7262 } 7263 return null; 7264 } 7265 7266 @Override 7267 public void setProcessLimit(int max) { 7268 enforceCallingPermission(android.Manifest.permission.SET_PROCESS_LIMIT, 7269 "setProcessLimit()"); 7270 synchronized (this) { 7271 mProcessLimit = max < 0 ? ProcessList.MAX_CACHED_APPS : max; 7272 mProcessLimitOverride = max; 7273 } 7274 trimApplications(); 7275 } 7276 7277 @Override 7278 public int getProcessLimit() { 7279 synchronized (this) { 7280 return mProcessLimitOverride; 7281 } 7282 } 7283 7284 void foregroundTokenDied(ForegroundToken token) { 7285 synchronized (ActivityManagerService.this) { 7286 synchronized (mPidsSelfLocked) { 7287 ForegroundToken cur 7288 = mForegroundProcesses.get(token.pid); 7289 if (cur != token) { 7290 return; 7291 } 7292 mForegroundProcesses.remove(token.pid); 7293 ProcessRecord pr = mPidsSelfLocked.get(token.pid); 7294 if (pr == null) { 7295 return; 7296 } 7297 pr.forcingToForeground = null; 7298 updateProcessForegroundLocked(pr, false, false); 7299 } 7300 updateOomAdjLocked(); 7301 } 7302 } 7303 7304 @Override 7305 public void setProcessForeground(IBinder token, int pid, boolean isForeground) { 7306 enforceCallingPermission(android.Manifest.permission.SET_PROCESS_LIMIT, 7307 "setProcessForeground()"); 7308 synchronized(this) { 7309 boolean changed = false; 7310 7311 synchronized (mPidsSelfLocked) { 7312 ProcessRecord pr = mPidsSelfLocked.get(pid); 7313 if (pr == null && isForeground) { 7314 Slog.w(TAG, "setProcessForeground called on unknown pid: " + pid); 7315 return; 7316 } 7317 ForegroundToken oldToken = mForegroundProcesses.get(pid); 7318 if (oldToken != null) { 7319 oldToken.token.unlinkToDeath(oldToken, 0); 7320 mForegroundProcesses.remove(pid); 7321 if (pr != null) { 7322 pr.forcingToForeground = null; 7323 } 7324 changed = true; 7325 } 7326 if (isForeground && token != null) { 7327 ForegroundToken newToken = new ForegroundToken() { 7328 @Override 7329 public void binderDied() { 7330 foregroundTokenDied(this); 7331 } 7332 }; 7333 newToken.pid = pid; 7334 newToken.token = token; 7335 try { 7336 token.linkToDeath(newToken, 0); 7337 mForegroundProcesses.put(pid, newToken); 7338 pr.forcingToForeground = token; 7339 changed = true; 7340 } catch (RemoteException e) { 7341 // If the process died while doing this, we will later 7342 // do the cleanup with the process death link. 7343 } 7344 } 7345 } 7346 7347 if (changed) { 7348 updateOomAdjLocked(); 7349 } 7350 } 7351 } 7352 7353 @Override 7354 public boolean isAppForeground(int uid) throws RemoteException { 7355 synchronized (this) { 7356 UidRecord uidRec = mActiveUids.get(uid); 7357 if (uidRec == null || uidRec.idle) { 7358 return false; 7359 } 7360 return uidRec.curProcState <= ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 7361 } 7362 } 7363 7364 // NOTE: this is an internal method used by the OnShellCommand implementation only and should 7365 // be guarded by permission checking. 7366 int getUidState(int uid) { 7367 synchronized (this) { 7368 UidRecord uidRec = mActiveUids.get(uid); 7369 return uidRec == null ? ActivityManager.PROCESS_STATE_NONEXISTENT : uidRec.curProcState; 7370 } 7371 } 7372 7373 @Override 7374 public boolean isInMultiWindowMode(IBinder token) { 7375 final long origId = Binder.clearCallingIdentity(); 7376 try { 7377 synchronized(this) { 7378 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 7379 if (r == null) { 7380 return false; 7381 } 7382 // An activity is consider to be in multi-window mode if its task isn't fullscreen. 7383 return !r.task.mFullscreen; 7384 } 7385 } finally { 7386 Binder.restoreCallingIdentity(origId); 7387 } 7388 } 7389 7390 @Override 7391 public boolean isInPictureInPictureMode(IBinder token) { 7392 final long origId = Binder.clearCallingIdentity(); 7393 try { 7394 synchronized(this) { 7395 final ActivityStack stack = ActivityRecord.getStackLocked(token); 7396 if (stack == null) { 7397 return false; 7398 } 7399 return stack.mStackId == PINNED_STACK_ID; 7400 } 7401 } finally { 7402 Binder.restoreCallingIdentity(origId); 7403 } 7404 } 7405 7406 @Override 7407 public void enterPictureInPictureMode(IBinder token) { 7408 final long origId = Binder.clearCallingIdentity(); 7409 try { 7410 synchronized(this) { 7411 if (!mSupportsPictureInPicture) { 7412 throw new IllegalStateException("enterPictureInPictureMode: " 7413 + "Device doesn't support picture-in-picture mode."); 7414 } 7415 7416 final ActivityRecord r = ActivityRecord.forTokenLocked(token); 7417 7418 if (r == null) { 7419 throw new IllegalStateException("enterPictureInPictureMode: " 7420 + "Can't find activity for token=" + token); 7421 } 7422 7423 if (!r.supportsPictureInPicture()) { 7424 throw new IllegalArgumentException("enterPictureInPictureMode: " 7425 + "Picture-In-Picture not supported for r=" + r); 7426 } 7427 7428 // Use the default launch bounds for pinned stack if it doesn't exist yet or use the 7429 // current bounds. 7430 final ActivityStack pinnedStack = mStackSupervisor.getStack(PINNED_STACK_ID); 7431 final Rect bounds = (pinnedStack != null) 7432 ? pinnedStack.mBounds : mDefaultPinnedStackBounds; 7433 7434 mStackSupervisor.moveActivityToPinnedStackLocked( 7435 r, "enterPictureInPictureMode", bounds); 7436 } 7437 } finally { 7438 Binder.restoreCallingIdentity(origId); 7439 } 7440 } 7441 7442 // ========================================================= 7443 // PROCESS INFO 7444 // ========================================================= 7445 7446 static class ProcessInfoService extends IProcessInfoService.Stub { 7447 final ActivityManagerService mActivityManagerService; 7448 ProcessInfoService(ActivityManagerService activityManagerService) { 7449 mActivityManagerService = activityManagerService; 7450 } 7451 7452 @Override 7453 public void getProcessStatesFromPids(/*in*/ int[] pids, /*out*/ int[] states) { 7454 mActivityManagerService.getProcessStatesAndOomScoresForPIDs( 7455 /*in*/ pids, /*out*/ states, null); 7456 } 7457 7458 @Override 7459 public void getProcessStatesAndOomScoresFromPids( 7460 /*in*/ int[] pids, /*out*/ int[] states, /*out*/ int[] scores) { 7461 mActivityManagerService.getProcessStatesAndOomScoresForPIDs( 7462 /*in*/ pids, /*out*/ states, /*out*/ scores); 7463 } 7464 } 7465 7466 /** 7467 * For each PID in the given input array, write the current process state 7468 * for that process into the states array, or -1 to indicate that no 7469 * process with the given PID exists. If scores array is provided, write 7470 * the oom score for the process into the scores array, with INVALID_ADJ 7471 * indicating the PID doesn't exist. 7472 */ 7473 public void getProcessStatesAndOomScoresForPIDs( 7474 /*in*/ int[] pids, /*out*/ int[] states, /*out*/ int[] scores) { 7475 if (scores != null) { 7476 enforceCallingPermission(android.Manifest.permission.GET_PROCESS_STATE_AND_OOM_SCORE, 7477 "getProcessStatesAndOomScoresForPIDs()"); 7478 } 7479 7480 if (pids == null) { 7481 throw new NullPointerException("pids"); 7482 } else if (states == null) { 7483 throw new NullPointerException("states"); 7484 } else if (pids.length != states.length) { 7485 throw new IllegalArgumentException("pids and states arrays have different lengths!"); 7486 } else if (scores != null && pids.length != scores.length) { 7487 throw new IllegalArgumentException("pids and scores arrays have different lengths!"); 7488 } 7489 7490 synchronized (mPidsSelfLocked) { 7491 for (int i = 0; i < pids.length; i++) { 7492 ProcessRecord pr = mPidsSelfLocked.get(pids[i]); 7493 states[i] = (pr == null) ? ActivityManager.PROCESS_STATE_NONEXISTENT : 7494 pr.curProcState; 7495 if (scores != null) { 7496 scores[i] = (pr == null) ? ProcessList.INVALID_ADJ : pr.curAdj; 7497 } 7498 } 7499 } 7500 } 7501 7502 // ========================================================= 7503 // PERMISSIONS 7504 // ========================================================= 7505 7506 static class PermissionController extends IPermissionController.Stub { 7507 ActivityManagerService mActivityManagerService; 7508 PermissionController(ActivityManagerService activityManagerService) { 7509 mActivityManagerService = activityManagerService; 7510 } 7511 7512 @Override 7513 public boolean checkPermission(String permission, int pid, int uid) { 7514 return mActivityManagerService.checkPermission(permission, pid, 7515 uid) == PackageManager.PERMISSION_GRANTED; 7516 } 7517 7518 @Override 7519 public String[] getPackagesForUid(int uid) { 7520 return mActivityManagerService.mContext.getPackageManager() 7521 .getPackagesForUid(uid); 7522 } 7523 7524 @Override 7525 public boolean isRuntimePermission(String permission) { 7526 try { 7527 PermissionInfo info = mActivityManagerService.mContext.getPackageManager() 7528 .getPermissionInfo(permission, 0); 7529 return info.protectionLevel == PermissionInfo.PROTECTION_DANGEROUS; 7530 } catch (NameNotFoundException nnfe) { 7531 Slog.e(TAG, "No such permission: "+ permission, nnfe); 7532 } 7533 return false; 7534 } 7535 } 7536 7537 class IntentFirewallInterface implements IntentFirewall.AMSInterface { 7538 @Override 7539 public int checkComponentPermission(String permission, int pid, int uid, 7540 int owningUid, boolean exported) { 7541 return ActivityManagerService.this.checkComponentPermission(permission, pid, uid, 7542 owningUid, exported); 7543 } 7544 7545 @Override 7546 public Object getAMSLock() { 7547 return ActivityManagerService.this; 7548 } 7549 } 7550 7551 /** 7552 * This can be called with or without the global lock held. 7553 */ 7554 int checkComponentPermission(String permission, int pid, int uid, 7555 int owningUid, boolean exported) { 7556 if (pid == MY_PID) { 7557 return PackageManager.PERMISSION_GRANTED; 7558 } 7559 return ActivityManager.checkComponentPermission(permission, uid, 7560 owningUid, exported); 7561 } 7562 7563 /** 7564 * As the only public entry point for permissions checking, this method 7565 * can enforce the semantic that requesting a check on a null global 7566 * permission is automatically denied. (Internally a null permission 7567 * string is used when calling {@link #checkComponentPermission} in cases 7568 * when only uid-based security is needed.) 7569 * 7570 * This can be called with or without the global lock held. 7571 */ 7572 @Override 7573 public int checkPermission(String permission, int pid, int uid) { 7574 if (permission == null) { 7575 return PackageManager.PERMISSION_DENIED; 7576 } 7577 return checkComponentPermission(permission, pid, uid, -1, true); 7578 } 7579 7580 @Override 7581 public int checkPermissionWithToken(String permission, int pid, int uid, IBinder callerToken) { 7582 if (permission == null) { 7583 return PackageManager.PERMISSION_DENIED; 7584 } 7585 7586 // We might be performing an operation on behalf of an indirect binder 7587 // invocation, e.g. via {@link #openContentUri}. Check and adjust the 7588 // client identity accordingly before proceeding. 7589 Identity tlsIdentity = sCallerIdentity.get(); 7590 if (tlsIdentity != null && tlsIdentity.token == callerToken) { 7591 Slog.d(TAG, "checkComponentPermission() adjusting {pid,uid} to {" 7592 + tlsIdentity.pid + "," + tlsIdentity.uid + "}"); 7593 uid = tlsIdentity.uid; 7594 pid = tlsIdentity.pid; 7595 } 7596 7597 return checkComponentPermission(permission, pid, uid, -1, true); 7598 } 7599 7600 /** 7601 * Binder IPC calls go through the public entry point. 7602 * This can be called with or without the global lock held. 7603 */ 7604 int checkCallingPermission(String permission) { 7605 return checkPermission(permission, 7606 Binder.getCallingPid(), 7607 UserHandle.getAppId(Binder.getCallingUid())); 7608 } 7609 7610 /** 7611 * This can be called with or without the global lock held. 7612 */ 7613 void enforceCallingPermission(String permission, String func) { 7614 if (checkCallingPermission(permission) 7615 == PackageManager.PERMISSION_GRANTED) { 7616 return; 7617 } 7618 7619 String msg = "Permission Denial: " + func + " from pid=" 7620 + Binder.getCallingPid() 7621 + ", uid=" + Binder.getCallingUid() 7622 + " requires " + permission; 7623 Slog.w(TAG, msg); 7624 throw new SecurityException(msg); 7625 } 7626 7627 /** 7628 * Determine if UID is holding permissions required to access {@link Uri} in 7629 * the given {@link ProviderInfo}. Final permission checking is always done 7630 * in {@link ContentProvider}. 7631 */ 7632 private final boolean checkHoldingPermissionsLocked( 7633 IPackageManager pm, ProviderInfo pi, GrantUri grantUri, int uid, final int modeFlags) { 7634 if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION, 7635 "checkHoldingPermissionsLocked: uri=" + grantUri + " uid=" + uid); 7636 if (UserHandle.getUserId(uid) != grantUri.sourceUserId) { 7637 if (ActivityManager.checkComponentPermission(INTERACT_ACROSS_USERS, uid, -1, true) 7638 != PERMISSION_GRANTED) { 7639 return false; 7640 } 7641 } 7642 return checkHoldingPermissionsInternalLocked(pm, pi, grantUri, uid, modeFlags, true); 7643 } 7644 7645 private final boolean checkHoldingPermissionsInternalLocked(IPackageManager pm, ProviderInfo pi, 7646 GrantUri grantUri, int uid, final int modeFlags, boolean considerUidPermissions) { 7647 if (pi.applicationInfo.uid == uid) { 7648 return true; 7649 } else if (!pi.exported) { 7650 return false; 7651 } 7652 7653 boolean readMet = (modeFlags & Intent.FLAG_GRANT_READ_URI_PERMISSION) == 0; 7654 boolean writeMet = (modeFlags & Intent.FLAG_GRANT_WRITE_URI_PERMISSION) == 0; 7655 try { 7656 // check if target holds top-level <provider> permissions 7657 if (!readMet && pi.readPermission != null && considerUidPermissions 7658 && (pm.checkUidPermission(pi.readPermission, uid) == PERMISSION_GRANTED)) { 7659 readMet = true; 7660 } 7661 if (!writeMet && pi.writePermission != null && considerUidPermissions 7662 && (pm.checkUidPermission(pi.writePermission, uid) == PERMISSION_GRANTED)) { 7663 writeMet = true; 7664 } 7665 7666 // track if unprotected read/write is allowed; any denied 7667 // <path-permission> below removes this ability 7668 boolean allowDefaultRead = pi.readPermission == null; 7669 boolean allowDefaultWrite = pi.writePermission == null; 7670 7671 // check if target holds any <path-permission> that match uri 7672 final PathPermission[] pps = pi.pathPermissions; 7673 if (pps != null) { 7674 final String path = grantUri.uri.getPath(); 7675 int i = pps.length; 7676 while (i > 0 && (!readMet || !writeMet)) { 7677 i--; 7678 PathPermission pp = pps[i]; 7679 if (pp.match(path)) { 7680 if (!readMet) { 7681 final String pprperm = pp.getReadPermission(); 7682 if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION, 7683 "Checking read perm for " + pprperm + " for " + pp.getPath() 7684 + ": match=" + pp.match(path) 7685 + " check=" + pm.checkUidPermission(pprperm, uid)); 7686 if (pprperm != null) { 7687 if (considerUidPermissions && pm.checkUidPermission(pprperm, uid) 7688 == PERMISSION_GRANTED) { 7689 readMet = true; 7690 } else { 7691 allowDefaultRead = false; 7692 } 7693 } 7694 } 7695 if (!writeMet) { 7696 final String ppwperm = pp.getWritePermission(); 7697 if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION, 7698 "Checking write perm " + ppwperm + " for " + pp.getPath() 7699 + ": match=" + pp.match(path) 7700 + " check=" + pm.checkUidPermission(ppwperm, uid)); 7701 if (ppwperm != null) { 7702 if (considerUidPermissions && pm.checkUidPermission(ppwperm, uid) 7703 == PERMISSION_GRANTED) { 7704 writeMet = true; 7705 } else { 7706 allowDefaultWrite = false; 7707 } 7708 } 7709 } 7710 } 7711 } 7712 } 7713 7714 // grant unprotected <provider> read/write, if not blocked by 7715 // <path-permission> above 7716 if (allowDefaultRead) readMet = true; 7717 if (allowDefaultWrite) writeMet = true; 7718 7719 } catch (RemoteException e) { 7720 return false; 7721 } 7722 7723 return readMet && writeMet; 7724 } 7725 7726 public int getAppStartMode(int uid, String packageName) { 7727 synchronized (this) { 7728 return checkAllowBackgroundLocked(uid, packageName, -1, true); 7729 } 7730 } 7731 7732 int checkAllowBackgroundLocked(int uid, String packageName, int callingPid, 7733 boolean allowWhenForeground) { 7734 UidRecord uidRec = mActiveUids.get(uid); 7735 if (!mLenientBackgroundCheck) { 7736 if (!allowWhenForeground || uidRec == null 7737 || uidRec.curProcState >= ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND) { 7738 if (mAppOpsService.noteOperation(AppOpsManager.OP_RUN_IN_BACKGROUND, uid, 7739 packageName) != AppOpsManager.MODE_ALLOWED) { 7740 return ActivityManager.APP_START_MODE_DELAYED; 7741 } 7742 } 7743 7744 } else if (uidRec == null || uidRec.idle) { 7745 if (callingPid >= 0) { 7746 ProcessRecord proc; 7747 synchronized (mPidsSelfLocked) { 7748 proc = mPidsSelfLocked.get(callingPid); 7749 } 7750 if (proc != null && proc.curProcState < ActivityManager.PROCESS_STATE_RECEIVER) { 7751 // Whoever is instigating this is in the foreground, so we will allow it 7752 // to go through. 7753 return ActivityManager.APP_START_MODE_NORMAL; 7754 } 7755 } 7756 if (mAppOpsService.noteOperation(AppOpsManager.OP_RUN_IN_BACKGROUND, uid, packageName) 7757 != AppOpsManager.MODE_ALLOWED) { 7758 return ActivityManager.APP_START_MODE_DELAYED; 7759 } 7760 } 7761 return ActivityManager.APP_START_MODE_NORMAL; 7762 } 7763 7764 private ProviderInfo getProviderInfoLocked(String authority, int userHandle) { 7765 ProviderInfo pi = null; 7766 ContentProviderRecord cpr = mProviderMap.getProviderByName(authority, userHandle); 7767 if (cpr != null) { 7768 pi = cpr.info; 7769 } else { 7770 try { 7771 pi = AppGlobals.getPackageManager().resolveContentProvider( 7772 authority, PackageManager.GET_URI_PERMISSION_PATTERNS, userHandle); 7773 } catch (RemoteException ex) { 7774 } 7775 } 7776 return pi; 7777 } 7778 7779 private UriPermission findUriPermissionLocked(int targetUid, GrantUri grantUri) { 7780 final ArrayMap<GrantUri, UriPermission> targetUris = mGrantedUriPermissions.get(targetUid); 7781 if (targetUris != null) { 7782 return targetUris.get(grantUri); 7783 } 7784 return null; 7785 } 7786 7787 private UriPermission findOrCreateUriPermissionLocked(String sourcePkg, 7788 String targetPkg, int targetUid, GrantUri grantUri) { 7789 ArrayMap<GrantUri, UriPermission> targetUris = mGrantedUriPermissions.get(targetUid); 7790 if (targetUris == null) { 7791 targetUris = Maps.newArrayMap(); 7792 mGrantedUriPermissions.put(targetUid, targetUris); 7793 } 7794 7795 UriPermission perm = targetUris.get(grantUri); 7796 if (perm == null) { 7797 perm = new UriPermission(sourcePkg, targetPkg, targetUid, grantUri); 7798 targetUris.put(grantUri, perm); 7799 } 7800 7801 return perm; 7802 } 7803 7804 private final boolean checkUriPermissionLocked(GrantUri grantUri, int uid, 7805 final int modeFlags) { 7806 final boolean persistable = (modeFlags & Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION) != 0; 7807 final int minStrength = persistable ? UriPermission.STRENGTH_PERSISTABLE 7808 : UriPermission.STRENGTH_OWNED; 7809 7810 // Root gets to do everything. 7811 if (uid == 0) { 7812 return true; 7813 } 7814 7815 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get(uid); 7816 if (perms == null) return false; 7817 7818 // First look for exact match 7819 final UriPermission exactPerm = perms.get(grantUri); 7820 if (exactPerm != null && exactPerm.getStrength(modeFlags) >= minStrength) { 7821 return true; 7822 } 7823 7824 // No exact match, look for prefixes 7825 final int N = perms.size(); 7826 for (int i = 0; i < N; i++) { 7827 final UriPermission perm = perms.valueAt(i); 7828 if (perm.uri.prefix && grantUri.uri.isPathPrefixMatch(perm.uri.uri) 7829 && perm.getStrength(modeFlags) >= minStrength) { 7830 return true; 7831 } 7832 } 7833 7834 return false; 7835 } 7836 7837 /** 7838 * @param uri This uri must NOT contain an embedded userId. 7839 * @param userId The userId in which the uri is to be resolved. 7840 */ 7841 @Override 7842 public int checkUriPermission(Uri uri, int pid, int uid, 7843 final int modeFlags, int userId, IBinder callerToken) { 7844 enforceNotIsolatedCaller("checkUriPermission"); 7845 7846 // Another redirected-binder-call permissions check as in 7847 // {@link checkPermissionWithToken}. 7848 Identity tlsIdentity = sCallerIdentity.get(); 7849 if (tlsIdentity != null && tlsIdentity.token == callerToken) { 7850 uid = tlsIdentity.uid; 7851 pid = tlsIdentity.pid; 7852 } 7853 7854 // Our own process gets to do everything. 7855 if (pid == MY_PID) { 7856 return PackageManager.PERMISSION_GRANTED; 7857 } 7858 synchronized (this) { 7859 return checkUriPermissionLocked(new GrantUri(userId, uri, false), uid, modeFlags) 7860 ? PackageManager.PERMISSION_GRANTED 7861 : PackageManager.PERMISSION_DENIED; 7862 } 7863 } 7864 7865 /** 7866 * Check if the targetPkg can be granted permission to access uri by 7867 * the callingUid using the given modeFlags. Throws a security exception 7868 * if callingUid is not allowed to do this. Returns the uid of the target 7869 * if the URI permission grant should be performed; returns -1 if it is not 7870 * needed (for example targetPkg already has permission to access the URI). 7871 * If you already know the uid of the target, you can supply it in 7872 * lastTargetUid else set that to -1. 7873 */ 7874 int checkGrantUriPermissionLocked(int callingUid, String targetPkg, GrantUri grantUri, 7875 final int modeFlags, int lastTargetUid) { 7876 if (!Intent.isAccessUriMode(modeFlags)) { 7877 return -1; 7878 } 7879 7880 if (targetPkg != null) { 7881 if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION, 7882 "Checking grant " + targetPkg + " permission to " + grantUri); 7883 } 7884 7885 final IPackageManager pm = AppGlobals.getPackageManager(); 7886 7887 // If this is not a content: uri, we can't do anything with it. 7888 if (!ContentResolver.SCHEME_CONTENT.equals(grantUri.uri.getScheme())) { 7889 if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION, 7890 "Can't grant URI permission for non-content URI: " + grantUri); 7891 return -1; 7892 } 7893 7894 final String authority = grantUri.uri.getAuthority(); 7895 final ProviderInfo pi = getProviderInfoLocked(authority, grantUri.sourceUserId); 7896 if (pi == null) { 7897 Slog.w(TAG, "No content provider found for permission check: " + 7898 grantUri.uri.toSafeString()); 7899 return -1; 7900 } 7901 7902 int targetUid = lastTargetUid; 7903 if (targetUid < 0 && targetPkg != null) { 7904 try { 7905 targetUid = pm.getPackageUid(targetPkg, MATCH_DEBUG_TRIAGED_MISSING, 7906 UserHandle.getUserId(callingUid)); 7907 if (targetUid < 0) { 7908 if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION, 7909 "Can't grant URI permission no uid for: " + targetPkg); 7910 return -1; 7911 } 7912 } catch (RemoteException ex) { 7913 return -1; 7914 } 7915 } 7916 7917 if (targetUid >= 0) { 7918 // First... does the target actually need this permission? 7919 if (checkHoldingPermissionsLocked(pm, pi, grantUri, targetUid, modeFlags)) { 7920 // No need to grant the target this permission. 7921 if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION, 7922 "Target " + targetPkg + " already has full permission to " + grantUri); 7923 return -1; 7924 } 7925 } else { 7926 // First... there is no target package, so can anyone access it? 7927 boolean allowed = pi.exported; 7928 if ((modeFlags&Intent.FLAG_GRANT_READ_URI_PERMISSION) != 0) { 7929 if (pi.readPermission != null) { 7930 allowed = false; 7931 } 7932 } 7933 if ((modeFlags&Intent.FLAG_GRANT_WRITE_URI_PERMISSION) != 0) { 7934 if (pi.writePermission != null) { 7935 allowed = false; 7936 } 7937 } 7938 if (allowed) { 7939 return -1; 7940 } 7941 } 7942 7943 /* There is a special cross user grant if: 7944 * - The target is on another user. 7945 * - Apps on the current user can access the uri without any uid permissions. 7946 * In this case, we grant a uri permission, even if the ContentProvider does not normally 7947 * grant uri permissions. 7948 */ 7949 boolean specialCrossUserGrant = UserHandle.getUserId(targetUid) != grantUri.sourceUserId 7950 && checkHoldingPermissionsInternalLocked(pm, pi, grantUri, callingUid, 7951 modeFlags, false /*without considering the uid permissions*/); 7952 7953 // Second... is the provider allowing granting of URI permissions? 7954 if (!specialCrossUserGrant) { 7955 if (!pi.grantUriPermissions) { 7956 throw new SecurityException("Provider " + pi.packageName 7957 + "/" + pi.name 7958 + " does not allow granting of Uri permissions (uri " 7959 + grantUri + ")"); 7960 } 7961 if (pi.uriPermissionPatterns != null) { 7962 final int N = pi.uriPermissionPatterns.length; 7963 boolean allowed = false; 7964 for (int i=0; i<N; i++) { 7965 if (pi.uriPermissionPatterns[i] != null 7966 && pi.uriPermissionPatterns[i].match(grantUri.uri.getPath())) { 7967 allowed = true; 7968 break; 7969 } 7970 } 7971 if (!allowed) { 7972 throw new SecurityException("Provider " + pi.packageName 7973 + "/" + pi.name 7974 + " does not allow granting of permission to path of Uri " 7975 + grantUri); 7976 } 7977 } 7978 } 7979 7980 // Third... does the caller itself have permission to access 7981 // this uri? 7982 if (UserHandle.getAppId(callingUid) != Process.SYSTEM_UID) { 7983 if (!checkHoldingPermissionsLocked(pm, pi, grantUri, callingUid, modeFlags)) { 7984 // Require they hold a strong enough Uri permission 7985 if (!checkUriPermissionLocked(grantUri, callingUid, modeFlags)) { 7986 throw new SecurityException("Uid " + callingUid 7987 + " does not have permission to uri " + grantUri); 7988 } 7989 } 7990 } 7991 return targetUid; 7992 } 7993 7994 /** 7995 * @param uri This uri must NOT contain an embedded userId. 7996 * @param userId The userId in which the uri is to be resolved. 7997 */ 7998 @Override 7999 public int checkGrantUriPermission(int callingUid, String targetPkg, Uri uri, 8000 final int modeFlags, int userId) { 8001 enforceNotIsolatedCaller("checkGrantUriPermission"); 8002 synchronized(this) { 8003 return checkGrantUriPermissionLocked(callingUid, targetPkg, 8004 new GrantUri(userId, uri, false), modeFlags, -1); 8005 } 8006 } 8007 8008 void grantUriPermissionUncheckedLocked(int targetUid, String targetPkg, GrantUri grantUri, 8009 final int modeFlags, UriPermissionOwner owner) { 8010 if (!Intent.isAccessUriMode(modeFlags)) { 8011 return; 8012 } 8013 8014 // So here we are: the caller has the assumed permission 8015 // to the uri, and the target doesn't. Let's now give this to 8016 // the target. 8017 8018 if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION, 8019 "Granting " + targetPkg + "/" + targetUid + " permission to " + grantUri); 8020 8021 final String authority = grantUri.uri.getAuthority(); 8022 final ProviderInfo pi = getProviderInfoLocked(authority, grantUri.sourceUserId); 8023 if (pi == null) { 8024 Slog.w(TAG, "No content provider found for grant: " + grantUri.toSafeString()); 8025 return; 8026 } 8027 8028 if ((modeFlags & Intent.FLAG_GRANT_PREFIX_URI_PERMISSION) != 0) { 8029 grantUri.prefix = true; 8030 } 8031 final UriPermission perm = findOrCreateUriPermissionLocked( 8032 pi.packageName, targetPkg, targetUid, grantUri); 8033 perm.grantModes(modeFlags, owner); 8034 } 8035 8036 void grantUriPermissionLocked(int callingUid, String targetPkg, GrantUri grantUri, 8037 final int modeFlags, UriPermissionOwner owner, int targetUserId) { 8038 if (targetPkg == null) { 8039 throw new NullPointerException("targetPkg"); 8040 } 8041 int targetUid; 8042 final IPackageManager pm = AppGlobals.getPackageManager(); 8043 try { 8044 targetUid = pm.getPackageUid(targetPkg, MATCH_DEBUG_TRIAGED_MISSING, targetUserId); 8045 } catch (RemoteException ex) { 8046 return; 8047 } 8048 8049 targetUid = checkGrantUriPermissionLocked(callingUid, targetPkg, grantUri, modeFlags, 8050 targetUid); 8051 if (targetUid < 0) { 8052 return; 8053 } 8054 8055 grantUriPermissionUncheckedLocked(targetUid, targetPkg, grantUri, modeFlags, 8056 owner); 8057 } 8058 8059 static class NeededUriGrants extends ArrayList<GrantUri> { 8060 final String targetPkg; 8061 final int targetUid; 8062 final int flags; 8063 8064 NeededUriGrants(String targetPkg, int targetUid, int flags) { 8065 this.targetPkg = targetPkg; 8066 this.targetUid = targetUid; 8067 this.flags = flags; 8068 } 8069 } 8070 8071 /** 8072 * Like checkGrantUriPermissionLocked, but takes an Intent. 8073 */ 8074 NeededUriGrants checkGrantUriPermissionFromIntentLocked(int callingUid, 8075 String targetPkg, Intent intent, int mode, NeededUriGrants needed, int targetUserId) { 8076 if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION, 8077 "Checking URI perm to data=" + (intent != null ? intent.getData() : null) 8078 + " clip=" + (intent != null ? intent.getClipData() : null) 8079 + " from " + intent + "; flags=0x" 8080 + Integer.toHexString(intent != null ? intent.getFlags() : 0)); 8081 8082 if (targetPkg == null) { 8083 throw new NullPointerException("targetPkg"); 8084 } 8085 8086 if (intent == null) { 8087 return null; 8088 } 8089 Uri data = intent.getData(); 8090 ClipData clip = intent.getClipData(); 8091 if (data == null && clip == null) { 8092 return null; 8093 } 8094 // Default userId for uris in the intent (if they don't specify it themselves) 8095 int contentUserHint = intent.getContentUserHint(); 8096 if (contentUserHint == UserHandle.USER_CURRENT) { 8097 contentUserHint = UserHandle.getUserId(callingUid); 8098 } 8099 final IPackageManager pm = AppGlobals.getPackageManager(); 8100 int targetUid; 8101 if (needed != null) { 8102 targetUid = needed.targetUid; 8103 } else { 8104 try { 8105 targetUid = pm.getPackageUid(targetPkg, MATCH_DEBUG_TRIAGED_MISSING, 8106 targetUserId); 8107 } catch (RemoteException ex) { 8108 return null; 8109 } 8110 if (targetUid < 0) { 8111 if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION, 8112 "Can't grant URI permission no uid for: " + targetPkg 8113 + " on user " + targetUserId); 8114 return null; 8115 } 8116 } 8117 if (data != null) { 8118 GrantUri grantUri = GrantUri.resolve(contentUserHint, data); 8119 targetUid = checkGrantUriPermissionLocked(callingUid, targetPkg, grantUri, mode, 8120 targetUid); 8121 if (targetUid > 0) { 8122 if (needed == null) { 8123 needed = new NeededUriGrants(targetPkg, targetUid, mode); 8124 } 8125 needed.add(grantUri); 8126 } 8127 } 8128 if (clip != null) { 8129 for (int i=0; i<clip.getItemCount(); i++) { 8130 Uri uri = clip.getItemAt(i).getUri(); 8131 if (uri != null) { 8132 GrantUri grantUri = GrantUri.resolve(contentUserHint, uri); 8133 targetUid = checkGrantUriPermissionLocked(callingUid, targetPkg, grantUri, mode, 8134 targetUid); 8135 if (targetUid > 0) { 8136 if (needed == null) { 8137 needed = new NeededUriGrants(targetPkg, targetUid, mode); 8138 } 8139 needed.add(grantUri); 8140 } 8141 } else { 8142 Intent clipIntent = clip.getItemAt(i).getIntent(); 8143 if (clipIntent != null) { 8144 NeededUriGrants newNeeded = checkGrantUriPermissionFromIntentLocked( 8145 callingUid, targetPkg, clipIntent, mode, needed, targetUserId); 8146 if (newNeeded != null) { 8147 needed = newNeeded; 8148 } 8149 } 8150 } 8151 } 8152 } 8153 8154 return needed; 8155 } 8156 8157 /** 8158 * Like grantUriPermissionUncheckedLocked, but takes an Intent. 8159 */ 8160 void grantUriPermissionUncheckedFromIntentLocked(NeededUriGrants needed, 8161 UriPermissionOwner owner) { 8162 if (needed != null) { 8163 for (int i=0; i<needed.size(); i++) { 8164 GrantUri grantUri = needed.get(i); 8165 grantUriPermissionUncheckedLocked(needed.targetUid, needed.targetPkg, 8166 grantUri, needed.flags, owner); 8167 } 8168 } 8169 } 8170 8171 void grantUriPermissionFromIntentLocked(int callingUid, 8172 String targetPkg, Intent intent, UriPermissionOwner owner, int targetUserId) { 8173 NeededUriGrants needed = checkGrantUriPermissionFromIntentLocked(callingUid, targetPkg, 8174 intent, intent != null ? intent.getFlags() : 0, null, targetUserId); 8175 if (needed == null) { 8176 return; 8177 } 8178 8179 grantUriPermissionUncheckedFromIntentLocked(needed, owner); 8180 } 8181 8182 /** 8183 * @param uri This uri must NOT contain an embedded userId. 8184 * @param userId The userId in which the uri is to be resolved. 8185 */ 8186 @Override 8187 public void grantUriPermission(IApplicationThread caller, String targetPkg, Uri uri, 8188 final int modeFlags, int userId) { 8189 enforceNotIsolatedCaller("grantUriPermission"); 8190 GrantUri grantUri = new GrantUri(userId, uri, false); 8191 synchronized(this) { 8192 final ProcessRecord r = getRecordForAppLocked(caller); 8193 if (r == null) { 8194 throw new SecurityException("Unable to find app for caller " 8195 + caller 8196 + " when granting permission to uri " + grantUri); 8197 } 8198 if (targetPkg == null) { 8199 throw new IllegalArgumentException("null target"); 8200 } 8201 if (grantUri == null) { 8202 throw new IllegalArgumentException("null uri"); 8203 } 8204 8205 Preconditions.checkFlagsArgument(modeFlags, Intent.FLAG_GRANT_READ_URI_PERMISSION 8206 | Intent.FLAG_GRANT_WRITE_URI_PERMISSION 8207 | Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION 8208 | Intent.FLAG_GRANT_PREFIX_URI_PERMISSION); 8209 8210 grantUriPermissionLocked(r.uid, targetPkg, grantUri, modeFlags, null, 8211 UserHandle.getUserId(r.uid)); 8212 } 8213 } 8214 8215 void removeUriPermissionIfNeededLocked(UriPermission perm) { 8216 if (perm.modeFlags == 0) { 8217 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get( 8218 perm.targetUid); 8219 if (perms != null) { 8220 if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION, 8221 "Removing " + perm.targetUid + " permission to " + perm.uri); 8222 8223 perms.remove(perm.uri); 8224 if (perms.isEmpty()) { 8225 mGrantedUriPermissions.remove(perm.targetUid); 8226 } 8227 } 8228 } 8229 } 8230 8231 private void revokeUriPermissionLocked(int callingUid, GrantUri grantUri, final int modeFlags) { 8232 if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION, 8233 "Revoking all granted permissions to " + grantUri); 8234 8235 final IPackageManager pm = AppGlobals.getPackageManager(); 8236 final String authority = grantUri.uri.getAuthority(); 8237 final ProviderInfo pi = getProviderInfoLocked(authority, grantUri.sourceUserId); 8238 if (pi == null) { 8239 Slog.w(TAG, "No content provider found for permission revoke: " 8240 + grantUri.toSafeString()); 8241 return; 8242 } 8243 8244 // Does the caller have this permission on the URI? 8245 if (!checkHoldingPermissionsLocked(pm, pi, grantUri, callingUid, modeFlags)) { 8246 // If they don't have direct access to the URI, then revoke any 8247 // ownerless URI permissions that have been granted to them. 8248 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get(callingUid); 8249 if (perms != null) { 8250 boolean persistChanged = false; 8251 for (Iterator<UriPermission> it = perms.values().iterator(); it.hasNext();) { 8252 final UriPermission perm = it.next(); 8253 if (perm.uri.sourceUserId == grantUri.sourceUserId 8254 && perm.uri.uri.isPathPrefixMatch(grantUri.uri)) { 8255 if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION, 8256 "Revoking non-owned " + perm.targetUid 8257 + " permission to " + perm.uri); 8258 persistChanged |= perm.revokeModes( 8259 modeFlags | Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION, false); 8260 if (perm.modeFlags == 0) { 8261 it.remove(); 8262 } 8263 } 8264 } 8265 if (perms.isEmpty()) { 8266 mGrantedUriPermissions.remove(callingUid); 8267 } 8268 if (persistChanged) { 8269 schedulePersistUriGrants(); 8270 } 8271 } 8272 return; 8273 } 8274 8275 boolean persistChanged = false; 8276 8277 // Go through all of the permissions and remove any that match. 8278 int N = mGrantedUriPermissions.size(); 8279 for (int i = 0; i < N; i++) { 8280 final int targetUid = mGrantedUriPermissions.keyAt(i); 8281 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i); 8282 8283 for (Iterator<UriPermission> it = perms.values().iterator(); it.hasNext();) { 8284 final UriPermission perm = it.next(); 8285 if (perm.uri.sourceUserId == grantUri.sourceUserId 8286 && perm.uri.uri.isPathPrefixMatch(grantUri.uri)) { 8287 if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION, 8288 "Revoking " + perm.targetUid + " permission to " + perm.uri); 8289 persistChanged |= perm.revokeModes( 8290 modeFlags | Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION, true); 8291 if (perm.modeFlags == 0) { 8292 it.remove(); 8293 } 8294 } 8295 } 8296 8297 if (perms.isEmpty()) { 8298 mGrantedUriPermissions.remove(targetUid); 8299 N--; 8300 i--; 8301 } 8302 } 8303 8304 if (persistChanged) { 8305 schedulePersistUriGrants(); 8306 } 8307 } 8308 8309 /** 8310 * @param uri This uri must NOT contain an embedded userId. 8311 * @param userId The userId in which the uri is to be resolved. 8312 */ 8313 @Override 8314 public void revokeUriPermission(IApplicationThread caller, Uri uri, final int modeFlags, 8315 int userId) { 8316 enforceNotIsolatedCaller("revokeUriPermission"); 8317 synchronized(this) { 8318 final ProcessRecord r = getRecordForAppLocked(caller); 8319 if (r == null) { 8320 throw new SecurityException("Unable to find app for caller " 8321 + caller 8322 + " when revoking permission to uri " + uri); 8323 } 8324 if (uri == null) { 8325 Slog.w(TAG, "revokeUriPermission: null uri"); 8326 return; 8327 } 8328 8329 if (!Intent.isAccessUriMode(modeFlags)) { 8330 return; 8331 } 8332 8333 final String authority = uri.getAuthority(); 8334 final ProviderInfo pi = getProviderInfoLocked(authority, userId); 8335 if (pi == null) { 8336 Slog.w(TAG, "No content provider found for permission revoke: " 8337 + uri.toSafeString()); 8338 return; 8339 } 8340 8341 revokeUriPermissionLocked(r.uid, new GrantUri(userId, uri, false), modeFlags); 8342 } 8343 } 8344 8345 /** 8346 * Remove any {@link UriPermission} granted <em>from</em> or <em>to</em> the 8347 * given package. 8348 * 8349 * @param packageName Package name to match, or {@code null} to apply to all 8350 * packages. 8351 * @param userHandle User to match, or {@link UserHandle#USER_ALL} to apply 8352 * to all users. 8353 * @param persistable If persistable grants should be removed. 8354 */ 8355 private void removeUriPermissionsForPackageLocked( 8356 String packageName, int userHandle, boolean persistable) { 8357 if (userHandle == UserHandle.USER_ALL && packageName == null) { 8358 throw new IllegalArgumentException("Must narrow by either package or user"); 8359 } 8360 8361 boolean persistChanged = false; 8362 8363 int N = mGrantedUriPermissions.size(); 8364 for (int i = 0; i < N; i++) { 8365 final int targetUid = mGrantedUriPermissions.keyAt(i); 8366 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i); 8367 8368 // Only inspect grants matching user 8369 if (userHandle == UserHandle.USER_ALL 8370 || userHandle == UserHandle.getUserId(targetUid)) { 8371 for (Iterator<UriPermission> it = perms.values().iterator(); it.hasNext();) { 8372 final UriPermission perm = it.next(); 8373 8374 // Only inspect grants matching package 8375 if (packageName == null || perm.sourcePkg.equals(packageName) 8376 || perm.targetPkg.equals(packageName)) { 8377 persistChanged |= perm.revokeModes(persistable 8378 ? ~0 : ~Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION, true); 8379 8380 // Only remove when no modes remain; any persisted grants 8381 // will keep this alive. 8382 if (perm.modeFlags == 0) { 8383 it.remove(); 8384 } 8385 } 8386 } 8387 8388 if (perms.isEmpty()) { 8389 mGrantedUriPermissions.remove(targetUid); 8390 N--; 8391 i--; 8392 } 8393 } 8394 } 8395 8396 if (persistChanged) { 8397 schedulePersistUriGrants(); 8398 } 8399 } 8400 8401 @Override 8402 public IBinder newUriPermissionOwner(String name) { 8403 enforceNotIsolatedCaller("newUriPermissionOwner"); 8404 synchronized(this) { 8405 UriPermissionOwner owner = new UriPermissionOwner(this, name); 8406 return owner.getExternalTokenLocked(); 8407 } 8408 } 8409 8410 @Override 8411 public IBinder getUriPermissionOwnerForActivity(IBinder activityToken) { 8412 enforceNotIsolatedCaller("getUriPermissionOwnerForActivity"); 8413 synchronized(this) { 8414 ActivityRecord r = ActivityRecord.isInStackLocked(activityToken); 8415 if (r == null) { 8416 throw new IllegalArgumentException("Activity does not exist; token=" 8417 + activityToken); 8418 } 8419 return r.getUriPermissionsLocked().getExternalTokenLocked(); 8420 } 8421 } 8422 /** 8423 * @param uri This uri must NOT contain an embedded userId. 8424 * @param sourceUserId The userId in which the uri is to be resolved. 8425 * @param targetUserId The userId of the app that receives the grant. 8426 */ 8427 @Override 8428 public void grantUriPermissionFromOwner(IBinder token, int fromUid, String targetPkg, Uri uri, 8429 final int modeFlags, int sourceUserId, int targetUserId) { 8430 targetUserId = mUserController.handleIncomingUser(Binder.getCallingPid(), 8431 Binder.getCallingUid(), targetUserId, false, ALLOW_FULL_ONLY, 8432 "grantUriPermissionFromOwner", null); 8433 synchronized(this) { 8434 UriPermissionOwner owner = UriPermissionOwner.fromExternalToken(token); 8435 if (owner == null) { 8436 throw new IllegalArgumentException("Unknown owner: " + token); 8437 } 8438 if (fromUid != Binder.getCallingUid()) { 8439 if (Binder.getCallingUid() != Process.myUid()) { 8440 // Only system code can grant URI permissions on behalf 8441 // of other users. 8442 throw new SecurityException("nice try"); 8443 } 8444 } 8445 if (targetPkg == null) { 8446 throw new IllegalArgumentException("null target"); 8447 } 8448 if (uri == null) { 8449 throw new IllegalArgumentException("null uri"); 8450 } 8451 8452 grantUriPermissionLocked(fromUid, targetPkg, new GrantUri(sourceUserId, uri, false), 8453 modeFlags, owner, targetUserId); 8454 } 8455 } 8456 8457 /** 8458 * @param uri This uri must NOT contain an embedded userId. 8459 * @param userId The userId in which the uri is to be resolved. 8460 */ 8461 @Override 8462 public void revokeUriPermissionFromOwner(IBinder token, Uri uri, int mode, int userId) { 8463 synchronized(this) { 8464 UriPermissionOwner owner = UriPermissionOwner.fromExternalToken(token); 8465 if (owner == null) { 8466 throw new IllegalArgumentException("Unknown owner: " + token); 8467 } 8468 8469 if (uri == null) { 8470 owner.removeUriPermissionsLocked(mode); 8471 } else { 8472 owner.removeUriPermissionLocked(new GrantUri(userId, uri, false), mode); 8473 } 8474 } 8475 } 8476 8477 private void schedulePersistUriGrants() { 8478 if (!mHandler.hasMessages(PERSIST_URI_GRANTS_MSG)) { 8479 mHandler.sendMessageDelayed(mHandler.obtainMessage(PERSIST_URI_GRANTS_MSG), 8480 10 * DateUtils.SECOND_IN_MILLIS); 8481 } 8482 } 8483 8484 private void writeGrantedUriPermissions() { 8485 if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION, "writeGrantedUriPermissions()"); 8486 8487 // Snapshot permissions so we can persist without lock 8488 ArrayList<UriPermission.Snapshot> persist = Lists.newArrayList(); 8489 synchronized (this) { 8490 final int size = mGrantedUriPermissions.size(); 8491 for (int i = 0; i < size; i++) { 8492 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i); 8493 for (UriPermission perm : perms.values()) { 8494 if (perm.persistedModeFlags != 0) { 8495 persist.add(perm.snapshot()); 8496 } 8497 } 8498 } 8499 } 8500 8501 FileOutputStream fos = null; 8502 try { 8503 fos = mGrantFile.startWrite(); 8504 8505 XmlSerializer out = new FastXmlSerializer(); 8506 out.setOutput(fos, StandardCharsets.UTF_8.name()); 8507 out.startDocument(null, true); 8508 out.startTag(null, TAG_URI_GRANTS); 8509 for (UriPermission.Snapshot perm : persist) { 8510 out.startTag(null, TAG_URI_GRANT); 8511 writeIntAttribute(out, ATTR_SOURCE_USER_ID, perm.uri.sourceUserId); 8512 writeIntAttribute(out, ATTR_TARGET_USER_ID, perm.targetUserId); 8513 out.attribute(null, ATTR_SOURCE_PKG, perm.sourcePkg); 8514 out.attribute(null, ATTR_TARGET_PKG, perm.targetPkg); 8515 out.attribute(null, ATTR_URI, String.valueOf(perm.uri.uri)); 8516 writeBooleanAttribute(out, ATTR_PREFIX, perm.uri.prefix); 8517 writeIntAttribute(out, ATTR_MODE_FLAGS, perm.persistedModeFlags); 8518 writeLongAttribute(out, ATTR_CREATED_TIME, perm.persistedCreateTime); 8519 out.endTag(null, TAG_URI_GRANT); 8520 } 8521 out.endTag(null, TAG_URI_GRANTS); 8522 out.endDocument(); 8523 8524 mGrantFile.finishWrite(fos); 8525 } catch (IOException e) { 8526 if (fos != null) { 8527 mGrantFile.failWrite(fos); 8528 } 8529 } 8530 } 8531 8532 private void readGrantedUriPermissionsLocked() { 8533 if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION, "readGrantedUriPermissions()"); 8534 8535 final long now = System.currentTimeMillis(); 8536 8537 FileInputStream fis = null; 8538 try { 8539 fis = mGrantFile.openRead(); 8540 final XmlPullParser in = Xml.newPullParser(); 8541 in.setInput(fis, StandardCharsets.UTF_8.name()); 8542 8543 int type; 8544 while ((type = in.next()) != END_DOCUMENT) { 8545 final String tag = in.getName(); 8546 if (type == START_TAG) { 8547 if (TAG_URI_GRANT.equals(tag)) { 8548 final int sourceUserId; 8549 final int targetUserId; 8550 final int userHandle = readIntAttribute(in, 8551 ATTR_USER_HANDLE, UserHandle.USER_NULL); 8552 if (userHandle != UserHandle.USER_NULL) { 8553 // For backwards compatibility. 8554 sourceUserId = userHandle; 8555 targetUserId = userHandle; 8556 } else { 8557 sourceUserId = readIntAttribute(in, ATTR_SOURCE_USER_ID); 8558 targetUserId = readIntAttribute(in, ATTR_TARGET_USER_ID); 8559 } 8560 final String sourcePkg = in.getAttributeValue(null, ATTR_SOURCE_PKG); 8561 final String targetPkg = in.getAttributeValue(null, ATTR_TARGET_PKG); 8562 final Uri uri = Uri.parse(in.getAttributeValue(null, ATTR_URI)); 8563 final boolean prefix = readBooleanAttribute(in, ATTR_PREFIX); 8564 final int modeFlags = readIntAttribute(in, ATTR_MODE_FLAGS); 8565 final long createdTime = readLongAttribute(in, ATTR_CREATED_TIME, now); 8566 8567 // Sanity check that provider still belongs to source package 8568 final ProviderInfo pi = getProviderInfoLocked( 8569 uri.getAuthority(), sourceUserId); 8570 if (pi != null && sourcePkg.equals(pi.packageName)) { 8571 int targetUid = -1; 8572 try { 8573 targetUid = AppGlobals.getPackageManager().getPackageUid( 8574 targetPkg, MATCH_UNINSTALLED_PACKAGES, targetUserId); 8575 } catch (RemoteException e) { 8576 } 8577 if (targetUid != -1) { 8578 final UriPermission perm = findOrCreateUriPermissionLocked( 8579 sourcePkg, targetPkg, targetUid, 8580 new GrantUri(sourceUserId, uri, prefix)); 8581 perm.initPersistedModes(modeFlags, createdTime); 8582 } 8583 } else { 8584 Slog.w(TAG, "Persisted grant for " + uri + " had source " + sourcePkg 8585 + " but instead found " + pi); 8586 } 8587 } 8588 } 8589 } 8590 } catch (FileNotFoundException e) { 8591 // Missing grants is okay 8592 } catch (IOException e) { 8593 Slog.wtf(TAG, "Failed reading Uri grants", e); 8594 } catch (XmlPullParserException e) { 8595 Slog.wtf(TAG, "Failed reading Uri grants", e); 8596 } finally { 8597 IoUtils.closeQuietly(fis); 8598 } 8599 } 8600 8601 /** 8602 * @param uri This uri must NOT contain an embedded userId. 8603 * @param userId The userId in which the uri is to be resolved. 8604 */ 8605 @Override 8606 public void takePersistableUriPermission(Uri uri, final int modeFlags, int userId) { 8607 enforceNotIsolatedCaller("takePersistableUriPermission"); 8608 8609 Preconditions.checkFlagsArgument(modeFlags, 8610 Intent.FLAG_GRANT_READ_URI_PERMISSION | Intent.FLAG_GRANT_WRITE_URI_PERMISSION); 8611 8612 synchronized (this) { 8613 final int callingUid = Binder.getCallingUid(); 8614 boolean persistChanged = false; 8615 GrantUri grantUri = new GrantUri(userId, uri, false); 8616 8617 UriPermission exactPerm = findUriPermissionLocked(callingUid, 8618 new GrantUri(userId, uri, false)); 8619 UriPermission prefixPerm = findUriPermissionLocked(callingUid, 8620 new GrantUri(userId, uri, true)); 8621 8622 final boolean exactValid = (exactPerm != null) 8623 && ((modeFlags & exactPerm.persistableModeFlags) == modeFlags); 8624 final boolean prefixValid = (prefixPerm != null) 8625 && ((modeFlags & prefixPerm.persistableModeFlags) == modeFlags); 8626 8627 if (!(exactValid || prefixValid)) { 8628 throw new SecurityException("No persistable permission grants found for UID " 8629 + callingUid + " and Uri " + grantUri.toSafeString()); 8630 } 8631 8632 if (exactValid) { 8633 persistChanged |= exactPerm.takePersistableModes(modeFlags); 8634 } 8635 if (prefixValid) { 8636 persistChanged |= prefixPerm.takePersistableModes(modeFlags); 8637 } 8638 8639 persistChanged |= maybePrunePersistedUriGrantsLocked(callingUid); 8640 8641 if (persistChanged) { 8642 schedulePersistUriGrants(); 8643 } 8644 } 8645 } 8646 8647 /** 8648 * @param uri This uri must NOT contain an embedded userId. 8649 * @param userId The userId in which the uri is to be resolved. 8650 */ 8651 @Override 8652 public void releasePersistableUriPermission(Uri uri, final int modeFlags, int userId) { 8653 enforceNotIsolatedCaller("releasePersistableUriPermission"); 8654 8655 Preconditions.checkFlagsArgument(modeFlags, 8656 Intent.FLAG_GRANT_READ_URI_PERMISSION | Intent.FLAG_GRANT_WRITE_URI_PERMISSION); 8657 8658 synchronized (this) { 8659 final int callingUid = Binder.getCallingUid(); 8660 boolean persistChanged = false; 8661 8662 UriPermission exactPerm = findUriPermissionLocked(callingUid, 8663 new GrantUri(userId, uri, false)); 8664 UriPermission prefixPerm = findUriPermissionLocked(callingUid, 8665 new GrantUri(userId, uri, true)); 8666 if (exactPerm == null && prefixPerm == null) { 8667 throw new SecurityException("No permission grants found for UID " + callingUid 8668 + " and Uri " + uri.toSafeString()); 8669 } 8670 8671 if (exactPerm != null) { 8672 persistChanged |= exactPerm.releasePersistableModes(modeFlags); 8673 removeUriPermissionIfNeededLocked(exactPerm); 8674 } 8675 if (prefixPerm != null) { 8676 persistChanged |= prefixPerm.releasePersistableModes(modeFlags); 8677 removeUriPermissionIfNeededLocked(prefixPerm); 8678 } 8679 8680 if (persistChanged) { 8681 schedulePersistUriGrants(); 8682 } 8683 } 8684 } 8685 8686 /** 8687 * Prune any older {@link UriPermission} for the given UID until outstanding 8688 * persisted grants are below {@link #MAX_PERSISTED_URI_GRANTS}. 8689 * 8690 * @return if any mutations occured that require persisting. 8691 */ 8692 private boolean maybePrunePersistedUriGrantsLocked(int uid) { 8693 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get(uid); 8694 if (perms == null) return false; 8695 if (perms.size() < MAX_PERSISTED_URI_GRANTS) return false; 8696 8697 final ArrayList<UriPermission> persisted = Lists.newArrayList(); 8698 for (UriPermission perm : perms.values()) { 8699 if (perm.persistedModeFlags != 0) { 8700 persisted.add(perm); 8701 } 8702 } 8703 8704 final int trimCount = persisted.size() - MAX_PERSISTED_URI_GRANTS; 8705 if (trimCount <= 0) return false; 8706 8707 Collections.sort(persisted, new UriPermission.PersistedTimeComparator()); 8708 for (int i = 0; i < trimCount; i++) { 8709 final UriPermission perm = persisted.get(i); 8710 8711 if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION, 8712 "Trimming grant created at " + perm.persistedCreateTime); 8713 8714 perm.releasePersistableModes(~0); 8715 removeUriPermissionIfNeededLocked(perm); 8716 } 8717 8718 return true; 8719 } 8720 8721 @Override 8722 public ParceledListSlice<android.content.UriPermission> getPersistedUriPermissions( 8723 String packageName, boolean incoming) { 8724 enforceNotIsolatedCaller("getPersistedUriPermissions"); 8725 Preconditions.checkNotNull(packageName, "packageName"); 8726 8727 final int callingUid = Binder.getCallingUid(); 8728 final IPackageManager pm = AppGlobals.getPackageManager(); 8729 try { 8730 final int packageUid = pm.getPackageUid(packageName, MATCH_DEBUG_TRIAGED_MISSING, 8731 UserHandle.getUserId(callingUid)); 8732 if (packageUid != callingUid) { 8733 throw new SecurityException( 8734 "Package " + packageName + " does not belong to calling UID " + callingUid); 8735 } 8736 } catch (RemoteException e) { 8737 throw new SecurityException("Failed to verify package name ownership"); 8738 } 8739 8740 final ArrayList<android.content.UriPermission> result = Lists.newArrayList(); 8741 synchronized (this) { 8742 if (incoming) { 8743 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get( 8744 callingUid); 8745 if (perms == null) { 8746 Slog.w(TAG, "No permission grants found for " + packageName); 8747 } else { 8748 for (UriPermission perm : perms.values()) { 8749 if (packageName.equals(perm.targetPkg) && perm.persistedModeFlags != 0) { 8750 result.add(perm.buildPersistedPublicApiObject()); 8751 } 8752 } 8753 } 8754 } else { 8755 final int size = mGrantedUriPermissions.size(); 8756 for (int i = 0; i < size; i++) { 8757 final ArrayMap<GrantUri, UriPermission> perms = 8758 mGrantedUriPermissions.valueAt(i); 8759 for (UriPermission perm : perms.values()) { 8760 if (packageName.equals(perm.sourcePkg) && perm.persistedModeFlags != 0) { 8761 result.add(perm.buildPersistedPublicApiObject()); 8762 } 8763 } 8764 } 8765 } 8766 } 8767 return new ParceledListSlice<android.content.UriPermission>(result); 8768 } 8769 8770 @Override 8771 public ParceledListSlice<android.content.UriPermission> getGrantedUriPermissions( 8772 String packageName, int userId) { 8773 enforceCallingPermission(android.Manifest.permission.GET_APP_GRANTED_URI_PERMISSIONS, 8774 "getGrantedUriPermissions"); 8775 8776 final ArrayList<android.content.UriPermission> result = Lists.newArrayList(); 8777 synchronized (this) { 8778 final int size = mGrantedUriPermissions.size(); 8779 for (int i = 0; i < size; i++) { 8780 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i); 8781 for (UriPermission perm : perms.values()) { 8782 if (packageName.equals(perm.targetPkg) && perm.targetUserId == userId 8783 && perm.persistedModeFlags != 0) { 8784 result.add(perm.buildPersistedPublicApiObject()); 8785 } 8786 } 8787 } 8788 } 8789 return new ParceledListSlice<android.content.UriPermission>(result); 8790 } 8791 8792 @Override 8793 public void clearGrantedUriPermissions(String packageName, int userId) { 8794 enforceCallingPermission(android.Manifest.permission.CLEAR_APP_GRANTED_URI_PERMISSIONS, 8795 "clearGrantedUriPermissions"); 8796 removeUriPermissionsForPackageLocked(packageName, userId, true); 8797 } 8798 8799 @Override 8800 public void showWaitingForDebugger(IApplicationThread who, boolean waiting) { 8801 synchronized (this) { 8802 ProcessRecord app = 8803 who != null ? getRecordForAppLocked(who) : null; 8804 if (app == null) return; 8805 8806 Message msg = Message.obtain(); 8807 msg.what = WAIT_FOR_DEBUGGER_UI_MSG; 8808 msg.obj = app; 8809 msg.arg1 = waiting ? 1 : 0; 8810 mUiHandler.sendMessage(msg); 8811 } 8812 } 8813 8814 @Override 8815 public void getMemoryInfo(ActivityManager.MemoryInfo outInfo) { 8816 final long homeAppMem = mProcessList.getMemLevel(ProcessList.HOME_APP_ADJ); 8817 final long cachedAppMem = mProcessList.getMemLevel(ProcessList.CACHED_APP_MIN_ADJ); 8818 outInfo.availMem = Process.getFreeMemory(); 8819 outInfo.totalMem = Process.getTotalMemory(); 8820 outInfo.threshold = homeAppMem; 8821 outInfo.lowMemory = outInfo.availMem < (homeAppMem + ((cachedAppMem-homeAppMem)/2)); 8822 outInfo.hiddenAppThreshold = cachedAppMem; 8823 outInfo.secondaryServerThreshold = mProcessList.getMemLevel( 8824 ProcessList.SERVICE_ADJ); 8825 outInfo.visibleAppThreshold = mProcessList.getMemLevel( 8826 ProcessList.VISIBLE_APP_ADJ); 8827 outInfo.foregroundAppThreshold = mProcessList.getMemLevel( 8828 ProcessList.FOREGROUND_APP_ADJ); 8829 } 8830 8831 // ========================================================= 8832 // TASK MANAGEMENT 8833 // ========================================================= 8834 8835 @Override 8836 public List<IAppTask> getAppTasks(String callingPackage) { 8837 int callingUid = Binder.getCallingUid(); 8838 long ident = Binder.clearCallingIdentity(); 8839 8840 synchronized(this) { 8841 ArrayList<IAppTask> list = new ArrayList<IAppTask>(); 8842 try { 8843 if (DEBUG_ALL) Slog.v(TAG, "getAppTasks"); 8844 8845 final int N = mRecentTasks.size(); 8846 for (int i = 0; i < N; i++) { 8847 TaskRecord tr = mRecentTasks.get(i); 8848 // Skip tasks that do not match the caller. We don't need to verify 8849 // callingPackage, because we are also limiting to callingUid and know 8850 // that will limit to the correct security sandbox. 8851 if (tr.effectiveUid != callingUid) { 8852 continue; 8853 } 8854 Intent intent = tr.getBaseIntent(); 8855 if (intent == null || 8856 !callingPackage.equals(intent.getComponent().getPackageName())) { 8857 continue; 8858 } 8859 ActivityManager.RecentTaskInfo taskInfo = 8860 createRecentTaskInfoFromTaskRecord(tr); 8861 AppTaskImpl taskImpl = new AppTaskImpl(taskInfo.persistentId, callingUid); 8862 list.add(taskImpl); 8863 } 8864 } finally { 8865 Binder.restoreCallingIdentity(ident); 8866 } 8867 return list; 8868 } 8869 } 8870 8871 @Override 8872 public List<RunningTaskInfo> getTasks(int maxNum, int flags) { 8873 final int callingUid = Binder.getCallingUid(); 8874 ArrayList<RunningTaskInfo> list = new ArrayList<RunningTaskInfo>(); 8875 8876 synchronized(this) { 8877 if (DEBUG_ALL) Slog.v( 8878 TAG, "getTasks: max=" + maxNum + ", flags=" + flags); 8879 8880 final boolean allowed = isGetTasksAllowed("getTasks", Binder.getCallingPid(), 8881 callingUid); 8882 8883 // TODO: Improve with MRU list from all ActivityStacks. 8884 mStackSupervisor.getTasksLocked(maxNum, list, callingUid, allowed); 8885 } 8886 8887 return list; 8888 } 8889 8890 /** 8891 * Creates a new RecentTaskInfo from a TaskRecord. 8892 */ 8893 private ActivityManager.RecentTaskInfo createRecentTaskInfoFromTaskRecord(TaskRecord tr) { 8894 // Update the task description to reflect any changes in the task stack 8895 tr.updateTaskDescription(); 8896 8897 // Compose the recent task info 8898 ActivityManager.RecentTaskInfo rti = new ActivityManager.RecentTaskInfo(); 8899 rti.id = tr.getTopActivity() == null ? INVALID_TASK_ID : tr.taskId; 8900 rti.persistentId = tr.taskId; 8901 rti.baseIntent = new Intent(tr.getBaseIntent()); 8902 rti.origActivity = tr.origActivity; 8903 rti.realActivity = tr.realActivity; 8904 rti.description = tr.lastDescription; 8905 rti.stackId = tr.stack != null ? tr.stack.mStackId : -1; 8906 rti.userId = tr.userId; 8907 rti.taskDescription = new ActivityManager.TaskDescription(tr.lastTaskDescription); 8908 rti.firstActiveTime = tr.firstActiveTime; 8909 rti.lastActiveTime = tr.lastActiveTime; 8910 rti.affiliatedTaskId = tr.mAffiliatedTaskId; 8911 rti.affiliatedTaskColor = tr.mAffiliatedTaskColor; 8912 rti.numActivities = 0; 8913 if (tr.mBounds != null) { 8914 rti.bounds = new Rect(tr.mBounds); 8915 } 8916 rti.isDockable = tr.canGoInDockedStack(); 8917 rti.resizeMode = tr.mResizeMode; 8918 8919 ActivityRecord base = null; 8920 ActivityRecord top = null; 8921 ActivityRecord tmp; 8922 8923 for (int i = tr.mActivities.size() - 1; i >= 0; --i) { 8924 tmp = tr.mActivities.get(i); 8925 if (tmp.finishing) { 8926 continue; 8927 } 8928 base = tmp; 8929 if (top == null || (top.state == ActivityState.INITIALIZING)) { 8930 top = base; 8931 } 8932 rti.numActivities++; 8933 } 8934 8935 rti.baseActivity = (base != null) ? base.intent.getComponent() : null; 8936 rti.topActivity = (top != null) ? top.intent.getComponent() : null; 8937 8938 return rti; 8939 } 8940 8941 private boolean isGetTasksAllowed(String caller, int callingPid, int callingUid) { 8942 boolean allowed = checkPermission(android.Manifest.permission.REAL_GET_TASKS, 8943 callingPid, callingUid) == PackageManager.PERMISSION_GRANTED; 8944 if (!allowed) { 8945 if (checkPermission(android.Manifest.permission.GET_TASKS, 8946 callingPid, callingUid) == PackageManager.PERMISSION_GRANTED) { 8947 // Temporary compatibility: some existing apps on the system image may 8948 // still be requesting the old permission and not switched to the new 8949 // one; if so, we'll still allow them full access. This means we need 8950 // to see if they are holding the old permission and are a system app. 8951 try { 8952 if (AppGlobals.getPackageManager().isUidPrivileged(callingUid)) { 8953 allowed = true; 8954 if (DEBUG_TASKS) Slog.w(TAG, caller + ": caller " + callingUid 8955 + " is using old GET_TASKS but privileged; allowing"); 8956 } 8957 } catch (RemoteException e) { 8958 } 8959 } 8960 } 8961 if (!allowed) { 8962 if (DEBUG_TASKS) Slog.w(TAG, caller + ": caller " + callingUid 8963 + " does not hold REAL_GET_TASKS; limiting output"); 8964 } 8965 return allowed; 8966 } 8967 8968 @Override 8969 public List<ActivityManager.RecentTaskInfo> getRecentTasks(int maxNum, int flags, int userId) { 8970 final int callingUid = Binder.getCallingUid(); 8971 userId = mUserController.handleIncomingUser(Binder.getCallingPid(), callingUid, userId, 8972 false, ALLOW_FULL_ONLY, "getRecentTasks", null); 8973 8974 final boolean includeProfiles = (flags & ActivityManager.RECENT_INCLUDE_PROFILES) != 0; 8975 final boolean withExcluded = (flags&ActivityManager.RECENT_WITH_EXCLUDED) != 0; 8976 synchronized (this) { 8977 final boolean allowed = isGetTasksAllowed("getRecentTasks", Binder.getCallingPid(), 8978 callingUid); 8979 final boolean detailed = checkCallingPermission( 8980 android.Manifest.permission.GET_DETAILED_TASKS) 8981 == PackageManager.PERMISSION_GRANTED; 8982 8983 if (!isUserRunning(userId, ActivityManager.FLAG_AND_UNLOCKED)) { 8984 Slog.i(TAG, "user " + userId + " is still locked. Cannot load recents"); 8985 return Collections.emptyList(); 8986 } 8987 mRecentTasks.loadUserRecentsLocked(userId); 8988 8989 final int recentsCount = mRecentTasks.size(); 8990 ArrayList<ActivityManager.RecentTaskInfo> res = 8991 new ArrayList<>(maxNum < recentsCount ? maxNum : recentsCount); 8992 8993 final Set<Integer> includedUsers; 8994 if (includeProfiles) { 8995 includedUsers = mUserController.getProfileIds(userId); 8996 } else { 8997 includedUsers = new HashSet<>(); 8998 } 8999 includedUsers.add(Integer.valueOf(userId)); 9000 9001 for (int i = 0; i < recentsCount && maxNum > 0; i++) { 9002 TaskRecord tr = mRecentTasks.get(i); 9003 // Only add calling user or related users recent tasks 9004 if (!includedUsers.contains(Integer.valueOf(tr.userId))) { 9005 if (DEBUG_RECENTS) Slog.d(TAG_RECENTS, "Skipping, not user: " + tr); 9006 continue; 9007 } 9008 9009 if (tr.realActivitySuspended) { 9010 if (DEBUG_RECENTS) Slog.d(TAG_RECENTS, "Skipping, activity suspended: " + tr); 9011 continue; 9012 } 9013 9014 // Return the entry if desired by the caller. We always return 9015 // the first entry, because callers always expect this to be the 9016 // foreground app. We may filter others if the caller has 9017 // not supplied RECENT_WITH_EXCLUDED and there is some reason 9018 // we should exclude the entry. 9019 9020 if (i == 0 9021 || withExcluded 9022 || (tr.intent == null) 9023 || ((tr.intent.getFlags() & Intent.FLAG_ACTIVITY_EXCLUDE_FROM_RECENTS) 9024 == 0)) { 9025 if (!allowed) { 9026 // If the caller doesn't have the GET_TASKS permission, then only 9027 // allow them to see a small subset of tasks -- their own and home. 9028 if (!tr.isHomeTask() && tr.effectiveUid != callingUid) { 9029 if (DEBUG_RECENTS) Slog.d(TAG_RECENTS, "Skipping, not allowed: " + tr); 9030 continue; 9031 } 9032 } 9033 if ((flags & ActivityManager.RECENT_IGNORE_HOME_STACK_TASKS) != 0) { 9034 if (tr.stack != null && tr.stack.isHomeStack()) { 9035 if (DEBUG_RECENTS) Slog.d(TAG_RECENTS, 9036 "Skipping, home stack task: " + tr); 9037 continue; 9038 } 9039 } 9040 if ((flags & ActivityManager.RECENT_INGORE_DOCKED_STACK_TOP_TASK) != 0) { 9041 final ActivityStack stack = tr.stack; 9042 if (stack != null && stack.isDockedStack() && stack.topTask() == tr) { 9043 if (DEBUG_RECENTS) Slog.d(TAG_RECENTS, 9044 "Skipping, top task in docked stack: " + tr); 9045 continue; 9046 } 9047 } 9048 if ((flags & ActivityManager.RECENT_INGORE_PINNED_STACK_TASKS) != 0) { 9049 if (tr.stack != null && tr.stack.isPinnedStack()) { 9050 if (DEBUG_RECENTS) Slog.d(TAG_RECENTS, 9051 "Skipping, pinned stack task: " + tr); 9052 continue; 9053 } 9054 } 9055 if (tr.autoRemoveRecents && tr.getTopActivity() == null) { 9056 // Don't include auto remove tasks that are finished or finishing. 9057 if (DEBUG_RECENTS) Slog.d(TAG_RECENTS, 9058 "Skipping, auto-remove without activity: " + tr); 9059 continue; 9060 } 9061 if ((flags&ActivityManager.RECENT_IGNORE_UNAVAILABLE) != 0 9062 && !tr.isAvailable) { 9063 if (DEBUG_RECENTS) Slog.d(TAG_RECENTS, 9064 "Skipping, unavail real act: " + tr); 9065 continue; 9066 } 9067 9068 if (!tr.mUserSetupComplete) { 9069 // Don't include task launched while user is not done setting-up. 9070 if (DEBUG_RECENTS) Slog.d(TAG_RECENTS, 9071 "Skipping, user setup not complete: " + tr); 9072 continue; 9073 } 9074 9075 ActivityManager.RecentTaskInfo rti = createRecentTaskInfoFromTaskRecord(tr); 9076 if (!detailed) { 9077 rti.baseIntent.replaceExtras((Bundle)null); 9078 } 9079 9080 res.add(rti); 9081 maxNum--; 9082 } 9083 } 9084 return res; 9085 } 9086 } 9087 9088 @Override 9089 public ActivityManager.TaskThumbnail getTaskThumbnail(int id) { 9090 synchronized (this) { 9091 enforceCallingPermission(android.Manifest.permission.READ_FRAME_BUFFER, 9092 "getTaskThumbnail()"); 9093 final TaskRecord tr = mStackSupervisor.anyTaskForIdLocked( 9094 id, !RESTORE_FROM_RECENTS, INVALID_STACK_ID); 9095 if (tr != null) { 9096 return tr.getTaskThumbnailLocked(); 9097 } 9098 } 9099 return null; 9100 } 9101 9102 @Override 9103 public int addAppTask(IBinder activityToken, Intent intent, 9104 ActivityManager.TaskDescription description, Bitmap thumbnail) throws RemoteException { 9105 final int callingUid = Binder.getCallingUid(); 9106 final long callingIdent = Binder.clearCallingIdentity(); 9107 9108 try { 9109 synchronized (this) { 9110 ActivityRecord r = ActivityRecord.isInStackLocked(activityToken); 9111 if (r == null) { 9112 throw new IllegalArgumentException("Activity does not exist; token=" 9113 + activityToken); 9114 } 9115 ComponentName comp = intent.getComponent(); 9116 if (comp == null) { 9117 throw new IllegalArgumentException("Intent " + intent 9118 + " must specify explicit component"); 9119 } 9120 if (thumbnail.getWidth() != mThumbnailWidth 9121 || thumbnail.getHeight() != mThumbnailHeight) { 9122 throw new IllegalArgumentException("Bad thumbnail size: got " 9123 + thumbnail.getWidth() + "x" + thumbnail.getHeight() + ", require " 9124 + mThumbnailWidth + "x" + mThumbnailHeight); 9125 } 9126 if (intent.getSelector() != null) { 9127 intent.setSelector(null); 9128 } 9129 if (intent.getSourceBounds() != null) { 9130 intent.setSourceBounds(null); 9131 } 9132 if ((intent.getFlags()&Intent.FLAG_ACTIVITY_NEW_DOCUMENT) != 0) { 9133 if ((intent.getFlags()&Intent.FLAG_ACTIVITY_RETAIN_IN_RECENTS) == 0) { 9134 // The caller has added this as an auto-remove task... that makes no 9135 // sense, so turn off auto-remove. 9136 intent.addFlags(Intent.FLAG_ACTIVITY_RETAIN_IN_RECENTS); 9137 } 9138 } else if ((intent.getFlags()&Intent.FLAG_ACTIVITY_NEW_TASK) != 0) { 9139 // Must be a new task. 9140 intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK); 9141 } 9142 if (!comp.equals(mLastAddedTaskComponent) || callingUid != mLastAddedTaskUid) { 9143 mLastAddedTaskActivity = null; 9144 } 9145 ActivityInfo ainfo = mLastAddedTaskActivity; 9146 if (ainfo == null) { 9147 ainfo = mLastAddedTaskActivity = AppGlobals.getPackageManager().getActivityInfo( 9148 comp, 0, UserHandle.getUserId(callingUid)); 9149 if (ainfo.applicationInfo.uid != callingUid) { 9150 throw new SecurityException( 9151 "Can't add task for another application: target uid=" 9152 + ainfo.applicationInfo.uid + ", calling uid=" + callingUid); 9153 } 9154 } 9155 9156 // Use the full screen as the context for the task thumbnail 9157 final Point displaySize = new Point(); 9158 final TaskThumbnailInfo thumbnailInfo = new TaskThumbnailInfo(); 9159 r.task.stack.getDisplaySize(displaySize); 9160 thumbnailInfo.taskWidth = displaySize.x; 9161 thumbnailInfo.taskHeight = displaySize.y; 9162 thumbnailInfo.screenOrientation = mConfiguration.orientation; 9163 9164 TaskRecord task = new TaskRecord(this, 9165 mStackSupervisor.getNextTaskIdForUserLocked(r.userId), 9166 ainfo, intent, description, thumbnailInfo); 9167 9168 int trimIdx = mRecentTasks.trimForTaskLocked(task, false); 9169 if (trimIdx >= 0) { 9170 // If this would have caused a trim, then we'll abort because that 9171 // means it would be added at the end of the list but then just removed. 9172 return INVALID_TASK_ID; 9173 } 9174 9175 final int N = mRecentTasks.size(); 9176 if (N >= (ActivityManager.getMaxRecentTasksStatic()-1)) { 9177 final TaskRecord tr = mRecentTasks.remove(N - 1); 9178 tr.removedFromRecents(); 9179 } 9180 9181 task.inRecents = true; 9182 mRecentTasks.add(task); 9183 r.task.stack.addTask(task, false, "addAppTask"); 9184 9185 task.setLastThumbnailLocked(thumbnail); 9186 task.freeLastThumbnail(); 9187 9188 return task.taskId; 9189 } 9190 } finally { 9191 Binder.restoreCallingIdentity(callingIdent); 9192 } 9193 } 9194 9195 @Override 9196 public Point getAppTaskThumbnailSize() { 9197 synchronized (this) { 9198 return new Point(mThumbnailWidth, mThumbnailHeight); 9199 } 9200 } 9201 9202 @Override 9203 public void setTaskDescription(IBinder token, ActivityManager.TaskDescription td) { 9204 synchronized (this) { 9205 ActivityRecord r = ActivityRecord.isInStackLocked(token); 9206 if (r != null) { 9207 r.setTaskDescription(td); 9208 r.task.updateTaskDescription(); 9209 } 9210 } 9211 } 9212 9213 @Override 9214 public void setTaskResizeable(int taskId, int resizeableMode) { 9215 synchronized (this) { 9216 final TaskRecord task = mStackSupervisor.anyTaskForIdLocked( 9217 taskId, !RESTORE_FROM_RECENTS, INVALID_STACK_ID); 9218 if (task == null) { 9219 Slog.w(TAG, "setTaskResizeable: taskId=" + taskId + " not found"); 9220 return; 9221 } 9222 if (task.mResizeMode != resizeableMode) { 9223 task.mResizeMode = resizeableMode; 9224 mWindowManager.setTaskResizeable(taskId, resizeableMode); 9225 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0, !PRESERVE_WINDOWS); 9226 mStackSupervisor.resumeFocusedStackTopActivityLocked(); 9227 } 9228 } 9229 } 9230 9231 @Override 9232 public void resizeTask(int taskId, Rect bounds, int resizeMode) { 9233 enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "resizeTask()"); 9234 long ident = Binder.clearCallingIdentity(); 9235 try { 9236 synchronized (this) { 9237 TaskRecord task = mStackSupervisor.anyTaskForIdLocked(taskId); 9238 if (task == null) { 9239 Slog.w(TAG, "resizeTask: taskId=" + taskId + " not found"); 9240 return; 9241 } 9242 int stackId = task.stack.mStackId; 9243 // We allow the task to scroll instead of resizing if this is a non-resizeable task 9244 // in crop windows resize mode or if the task size is affected by the docked stack 9245 // changing size. No need to update configuration. 9246 if (bounds != null && task.inCropWindowsResizeMode() 9247 && mStackSupervisor.isStackDockedInEffect(stackId)) { 9248 mWindowManager.scrollTask(task.taskId, bounds); 9249 return; 9250 } 9251 9252 // Place the task in the right stack if it isn't there already based on 9253 // the requested bounds. 9254 // The stack transition logic is: 9255 // - a null bounds on a freeform task moves that task to fullscreen 9256 // - a non-null bounds on a non-freeform (fullscreen OR docked) task moves 9257 // that task to freeform 9258 // - otherwise the task is not moved 9259 if (!StackId.isTaskResizeAllowed(stackId)) { 9260 throw new IllegalArgumentException("resizeTask not allowed on task=" + task); 9261 } 9262 if (bounds == null && stackId == FREEFORM_WORKSPACE_STACK_ID) { 9263 stackId = FULLSCREEN_WORKSPACE_STACK_ID; 9264 } else if (bounds != null && stackId != FREEFORM_WORKSPACE_STACK_ID ) { 9265 stackId = FREEFORM_WORKSPACE_STACK_ID; 9266 } 9267 boolean preserveWindow = (resizeMode & RESIZE_MODE_PRESERVE_WINDOW) != 0; 9268 if (stackId != task.stack.mStackId) { 9269 mStackSupervisor.moveTaskToStackUncheckedLocked( 9270 task, stackId, ON_TOP, !FORCE_FOCUS, "resizeTask"); 9271 preserveWindow = false; 9272 } 9273 9274 mStackSupervisor.resizeTaskLocked(task, bounds, resizeMode, preserveWindow, 9275 false /* deferResume */); 9276 } 9277 } finally { 9278 Binder.restoreCallingIdentity(ident); 9279 } 9280 } 9281 9282 @Override 9283 public Rect getTaskBounds(int taskId) { 9284 enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "getTaskBounds()"); 9285 long ident = Binder.clearCallingIdentity(); 9286 Rect rect = new Rect(); 9287 try { 9288 synchronized (this) { 9289 final TaskRecord task = mStackSupervisor.anyTaskForIdLocked( 9290 taskId, !RESTORE_FROM_RECENTS, INVALID_STACK_ID); 9291 if (task == null) { 9292 Slog.w(TAG, "getTaskBounds: taskId=" + taskId + " not found"); 9293 return rect; 9294 } 9295 if (task.stack != null) { 9296 // Return the bounds from window manager since it will be adjusted for various 9297 // things like the presense of a docked stack for tasks that aren't resizeable. 9298 mWindowManager.getTaskBounds(task.taskId, rect); 9299 } else { 9300 // Task isn't in window manager yet since it isn't associated with a stack. 9301 // Return the persist value from activity manager 9302 if (task.mBounds != null) { 9303 rect.set(task.mBounds); 9304 } else if (task.mLastNonFullscreenBounds != null) { 9305 rect.set(task.mLastNonFullscreenBounds); 9306 } 9307 } 9308 } 9309 } finally { 9310 Binder.restoreCallingIdentity(ident); 9311 } 9312 return rect; 9313 } 9314 9315 @Override 9316 public Bitmap getTaskDescriptionIcon(String filePath, int userId) { 9317 if (userId != UserHandle.getCallingUserId()) { 9318 enforceCallingPermission(android.Manifest.permission.INTERACT_ACROSS_USERS_FULL, 9319 "getTaskDescriptionIcon"); 9320 } 9321 final File passedIconFile = new File(filePath); 9322 final File legitIconFile = new File(TaskPersister.getUserImagesDir(userId), 9323 passedIconFile.getName()); 9324 if (!legitIconFile.getPath().equals(filePath) 9325 || !filePath.contains(ActivityRecord.ACTIVITY_ICON_SUFFIX)) { 9326 throw new IllegalArgumentException("Bad file path: " + filePath 9327 + " passed for userId " + userId); 9328 } 9329 return mRecentTasks.getTaskDescriptionIcon(filePath); 9330 } 9331 9332 @Override 9333 public void startInPlaceAnimationOnFrontMostApplication(ActivityOptions opts) 9334 throws RemoteException { 9335 if (opts.getAnimationType() != ActivityOptions.ANIM_CUSTOM_IN_PLACE || 9336 opts.getCustomInPlaceResId() == 0) { 9337 throw new IllegalArgumentException("Expected in-place ActivityOption " + 9338 "with valid animation"); 9339 } 9340 mWindowManager.prepareAppTransition(TRANSIT_TASK_IN_PLACE, false); 9341 mWindowManager.overridePendingAppTransitionInPlace(opts.getPackageName(), 9342 opts.getCustomInPlaceResId()); 9343 mWindowManager.executeAppTransition(); 9344 } 9345 9346 private void cleanUpRemovedTaskLocked(TaskRecord tr, boolean killProcess, 9347 boolean removeFromRecents) { 9348 if (removeFromRecents) { 9349 mRecentTasks.remove(tr); 9350 tr.removedFromRecents(); 9351 } 9352 ComponentName component = tr.getBaseIntent().getComponent(); 9353 if (component == null) { 9354 Slog.w(TAG, "No component for base intent of task: " + tr); 9355 return; 9356 } 9357 9358 // Find any running services associated with this app and stop if needed. 9359 mServices.cleanUpRemovedTaskLocked(tr, component, new Intent(tr.getBaseIntent())); 9360 9361 if (!killProcess) { 9362 return; 9363 } 9364 9365 // Determine if the process(es) for this task should be killed. 9366 final String pkg = component.getPackageName(); 9367 ArrayList<ProcessRecord> procsToKill = new ArrayList<>(); 9368 ArrayMap<String, SparseArray<ProcessRecord>> pmap = mProcessNames.getMap(); 9369 for (int i = 0; i < pmap.size(); i++) { 9370 9371 SparseArray<ProcessRecord> uids = pmap.valueAt(i); 9372 for (int j = 0; j < uids.size(); j++) { 9373 ProcessRecord proc = uids.valueAt(j); 9374 if (proc.userId != tr.userId) { 9375 // Don't kill process for a different user. 9376 continue; 9377 } 9378 if (proc == mHomeProcess) { 9379 // Don't kill the home process along with tasks from the same package. 9380 continue; 9381 } 9382 if (!proc.pkgList.containsKey(pkg)) { 9383 // Don't kill process that is not associated with this task. 9384 continue; 9385 } 9386 9387 for (int k = 0; k < proc.activities.size(); k++) { 9388 TaskRecord otherTask = proc.activities.get(k).task; 9389 if (tr.taskId != otherTask.taskId && otherTask.inRecents) { 9390 // Don't kill process(es) that has an activity in a different task that is 9391 // also in recents. 9392 return; 9393 } 9394 } 9395 9396 if (proc.foregroundServices) { 9397 // Don't kill process(es) with foreground service. 9398 return; 9399 } 9400 9401 // Add process to kill list. 9402 procsToKill.add(proc); 9403 } 9404 } 9405 9406 // Kill the running processes. 9407 for (int i = 0; i < procsToKill.size(); i++) { 9408 ProcessRecord pr = procsToKill.get(i); 9409 if (pr.setSchedGroup == ProcessList.SCHED_GROUP_BACKGROUND 9410 && pr.curReceiver == null) { 9411 pr.kill("remove task", true); 9412 } else { 9413 // We delay killing processes that are not in the background or running a receiver. 9414 pr.waitingToKill = "remove task"; 9415 } 9416 } 9417 } 9418 9419 private void removeTasksByPackageNameLocked(String packageName, int userId) { 9420 // Remove all tasks with activities in the specified package from the list of recent tasks 9421 for (int i = mRecentTasks.size() - 1; i >= 0; i--) { 9422 TaskRecord tr = mRecentTasks.get(i); 9423 if (tr.userId != userId) continue; 9424 9425 ComponentName cn = tr.intent.getComponent(); 9426 if (cn != null && cn.getPackageName().equals(packageName)) { 9427 // If the package name matches, remove the task. 9428 removeTaskByIdLocked(tr.taskId, true, REMOVE_FROM_RECENTS); 9429 } 9430 } 9431 } 9432 9433 private void cleanupDisabledPackageTasksLocked(String packageName, Set<String> filterByClasses, 9434 int userId) { 9435 9436 for (int i = mRecentTasks.size() - 1; i >= 0; i--) { 9437 TaskRecord tr = mRecentTasks.get(i); 9438 if (userId != UserHandle.USER_ALL && tr.userId != userId) { 9439 continue; 9440 } 9441 9442 ComponentName cn = tr.intent.getComponent(); 9443 final boolean sameComponent = cn != null && cn.getPackageName().equals(packageName) 9444 && (filterByClasses == null || filterByClasses.contains(cn.getClassName())); 9445 if (sameComponent) { 9446 removeTaskByIdLocked(tr.taskId, false, REMOVE_FROM_RECENTS); 9447 } 9448 } 9449 } 9450 9451 /** 9452 * Removes the task with the specified task id. 9453 * 9454 * @param taskId Identifier of the task to be removed. 9455 * @param killProcess Kill any process associated with the task if possible. 9456 * @param removeFromRecents Whether to also remove the task from recents. 9457 * @return Returns true if the given task was found and removed. 9458 */ 9459 private boolean removeTaskByIdLocked(int taskId, boolean killProcess, 9460 boolean removeFromRecents) { 9461 final TaskRecord tr = mStackSupervisor.anyTaskForIdLocked( 9462 taskId, !RESTORE_FROM_RECENTS, INVALID_STACK_ID); 9463 if (tr != null) { 9464 tr.removeTaskActivitiesLocked(); 9465 cleanUpRemovedTaskLocked(tr, killProcess, removeFromRecents); 9466 if (tr.isPersistable) { 9467 notifyTaskPersisterLocked(null, true); 9468 } 9469 return true; 9470 } 9471 Slog.w(TAG, "Request to remove task ignored for non-existent task " + taskId); 9472 return false; 9473 } 9474 9475 @Override 9476 public void removeStack(int stackId) { 9477 enforceCallingPermission(Manifest.permission.MANAGE_ACTIVITY_STACKS, "removeStack()"); 9478 if (stackId == HOME_STACK_ID) { 9479 throw new IllegalArgumentException("Removing home stack is not allowed."); 9480 } 9481 9482 synchronized (this) { 9483 final long ident = Binder.clearCallingIdentity(); 9484 try { 9485 final ActivityStack stack = mStackSupervisor.getStack(stackId); 9486 if (stack == null) { 9487 return; 9488 } 9489 final ArrayList<TaskRecord> tasks = stack.getAllTasks(); 9490 for (int i = tasks.size() - 1; i >= 0; i--) { 9491 removeTaskByIdLocked( 9492 tasks.get(i).taskId, true /* killProcess */, REMOVE_FROM_RECENTS); 9493 } 9494 } finally { 9495 Binder.restoreCallingIdentity(ident); 9496 } 9497 } 9498 } 9499 9500 @Override 9501 public boolean removeTask(int taskId) { 9502 enforceCallingPermission(android.Manifest.permission.REMOVE_TASKS, "removeTask()"); 9503 synchronized (this) { 9504 final long ident = Binder.clearCallingIdentity(); 9505 try { 9506 return removeTaskByIdLocked(taskId, true, REMOVE_FROM_RECENTS); 9507 } finally { 9508 Binder.restoreCallingIdentity(ident); 9509 } 9510 } 9511 } 9512 9513 /** 9514 * TODO: Add mController hook 9515 */ 9516 @Override 9517 public void moveTaskToFront(int taskId, int flags, Bundle bOptions) { 9518 enforceCallingPermission(android.Manifest.permission.REORDER_TASKS, "moveTaskToFront()"); 9519 9520 if (DEBUG_STACK) Slog.d(TAG_STACK, "moveTaskToFront: moving taskId=" + taskId); 9521 synchronized(this) { 9522 moveTaskToFrontLocked(taskId, flags, bOptions); 9523 } 9524 } 9525 9526 void moveTaskToFrontLocked(int taskId, int flags, Bundle bOptions) { 9527 ActivityOptions options = ActivityOptions.fromBundle(bOptions); 9528 9529 if (!checkAppSwitchAllowedLocked(Binder.getCallingPid(), 9530 Binder.getCallingUid(), -1, -1, "Task to front")) { 9531 ActivityOptions.abort(options); 9532 return; 9533 } 9534 final long origId = Binder.clearCallingIdentity(); 9535 try { 9536 final TaskRecord task = mStackSupervisor.anyTaskForIdLocked(taskId); 9537 if (task == null) { 9538 Slog.d(TAG, "Could not find task for id: "+ taskId); 9539 return; 9540 } 9541 if (mStackSupervisor.isLockTaskModeViolation(task)) { 9542 mStackSupervisor.showLockTaskToast(); 9543 Slog.e(TAG, "moveTaskToFront: Attempt to violate Lock Task Mode"); 9544 return; 9545 } 9546 final ActivityRecord prev = mStackSupervisor.topRunningActivityLocked(); 9547 if (prev != null && prev.isRecentsActivity()) { 9548 task.setTaskToReturnTo(ActivityRecord.RECENTS_ACTIVITY_TYPE); 9549 } 9550 mStackSupervisor.findTaskToMoveToFrontLocked(task, flags, options, "moveTaskToFront", 9551 false /* forceNonResizable */); 9552 } finally { 9553 Binder.restoreCallingIdentity(origId); 9554 } 9555 ActivityOptions.abort(options); 9556 } 9557 9558 /** 9559 * Moves an activity, and all of the other activities within the same task, to the bottom 9560 * of the history stack. The activity's order within the task is unchanged. 9561 * 9562 * @param token A reference to the activity we wish to move 9563 * @param nonRoot If false then this only works if the activity is the root 9564 * of a task; if true it will work for any activity in a task. 9565 * @return Returns true if the move completed, false if not. 9566 */ 9567 @Override 9568 public boolean moveActivityTaskToBack(IBinder token, boolean nonRoot) { 9569 enforceNotIsolatedCaller("moveActivityTaskToBack"); 9570 synchronized(this) { 9571 final long origId = Binder.clearCallingIdentity(); 9572 try { 9573 int taskId = ActivityRecord.getTaskForActivityLocked(token, !nonRoot); 9574 final TaskRecord task = mStackSupervisor.anyTaskForIdLocked(taskId); 9575 if (task != null) { 9576 if (mStackSupervisor.isLockedTask(task)) { 9577 mStackSupervisor.showLockTaskToast(); 9578 return false; 9579 } 9580 return ActivityRecord.getStackLocked(token).moveTaskToBackLocked(taskId); 9581 } 9582 } finally { 9583 Binder.restoreCallingIdentity(origId); 9584 } 9585 } 9586 return false; 9587 } 9588 9589 @Override 9590 public void moveTaskBackwards(int task) { 9591 enforceCallingPermission(android.Manifest.permission.REORDER_TASKS, 9592 "moveTaskBackwards()"); 9593 9594 synchronized(this) { 9595 if (!checkAppSwitchAllowedLocked(Binder.getCallingPid(), 9596 Binder.getCallingUid(), -1, -1, "Task backwards")) { 9597 return; 9598 } 9599 final long origId = Binder.clearCallingIdentity(); 9600 moveTaskBackwardsLocked(task); 9601 Binder.restoreCallingIdentity(origId); 9602 } 9603 } 9604 9605 private final void moveTaskBackwardsLocked(int task) { 9606 Slog.e(TAG, "moveTaskBackwards not yet implemented!"); 9607 } 9608 9609 @Override 9610 public IActivityContainer createVirtualActivityContainer(IBinder parentActivityToken, 9611 IActivityContainerCallback callback) throws RemoteException { 9612 enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "createActivityContainer()"); 9613 synchronized (this) { 9614 if (parentActivityToken == null) { 9615 throw new IllegalArgumentException("parent token must not be null"); 9616 } 9617 ActivityRecord r = ActivityRecord.forTokenLocked(parentActivityToken); 9618 if (r == null) { 9619 return null; 9620 } 9621 if (callback == null) { 9622 throw new IllegalArgumentException("callback must not be null"); 9623 } 9624 return mStackSupervisor.createVirtualActivityContainer(r, callback); 9625 } 9626 } 9627 9628 @Override 9629 public void deleteActivityContainer(IActivityContainer container) throws RemoteException { 9630 enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "deleteActivityContainer()"); 9631 synchronized (this) { 9632 mStackSupervisor.deleteActivityContainer(container); 9633 } 9634 } 9635 9636 @Override 9637 public IActivityContainer createStackOnDisplay(int displayId) throws RemoteException { 9638 enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "createStackOnDisplay()"); 9639 synchronized (this) { 9640 final int stackId = mStackSupervisor.getNextStackId(); 9641 final ActivityStack stack = 9642 mStackSupervisor.createStackOnDisplay(stackId, displayId, true /*onTop*/); 9643 if (stack == null) { 9644 return null; 9645 } 9646 return stack.mActivityContainer; 9647 } 9648 } 9649 9650 @Override 9651 public int getActivityDisplayId(IBinder activityToken) throws RemoteException { 9652 synchronized (this) { 9653 ActivityStack stack = ActivityRecord.getStackLocked(activityToken); 9654 if (stack != null && stack.mActivityContainer.isAttachedLocked()) { 9655 return stack.mActivityContainer.getDisplayId(); 9656 } 9657 return Display.DEFAULT_DISPLAY; 9658 } 9659 } 9660 9661 @Override 9662 public int getActivityStackId(IBinder token) throws RemoteException { 9663 synchronized (this) { 9664 ActivityStack stack = ActivityRecord.getStackLocked(token); 9665 if (stack == null) { 9666 return INVALID_STACK_ID; 9667 } 9668 return stack.mStackId; 9669 } 9670 } 9671 9672 @Override 9673 public void exitFreeformMode(IBinder token) throws RemoteException { 9674 synchronized (this) { 9675 long ident = Binder.clearCallingIdentity(); 9676 try { 9677 final ActivityRecord r = ActivityRecord.forTokenLocked(token); 9678 if (r == null) { 9679 throw new IllegalArgumentException( 9680 "exitFreeformMode: No activity record matching token=" + token); 9681 } 9682 final ActivityStack stack = r.getStackLocked(token); 9683 if (stack == null || stack.mStackId != FREEFORM_WORKSPACE_STACK_ID) { 9684 throw new IllegalStateException( 9685 "exitFreeformMode: You can only go fullscreen from freeform."); 9686 } 9687 if (DEBUG_STACK) Slog.d(TAG_STACK, "exitFreeformMode: " + r); 9688 mStackSupervisor.moveTaskToStackLocked(r.task.taskId, FULLSCREEN_WORKSPACE_STACK_ID, 9689 ON_TOP, !FORCE_FOCUS, "exitFreeformMode", ANIMATE); 9690 } finally { 9691 Binder.restoreCallingIdentity(ident); 9692 } 9693 } 9694 } 9695 9696 @Override 9697 public void moveTaskToStack(int taskId, int stackId, boolean toTop) { 9698 enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "moveTaskToStack()"); 9699 if (stackId == HOME_STACK_ID) { 9700 throw new IllegalArgumentException( 9701 "moveTaskToStack: Attempt to move task " + taskId + " to home stack"); 9702 } 9703 synchronized (this) { 9704 long ident = Binder.clearCallingIdentity(); 9705 try { 9706 if (DEBUG_STACK) Slog.d(TAG_STACK, "moveTaskToStack: moving task=" + taskId 9707 + " to stackId=" + stackId + " toTop=" + toTop); 9708 if (stackId == DOCKED_STACK_ID) { 9709 mWindowManager.setDockedStackCreateState(DOCKED_STACK_CREATE_MODE_TOP_OR_LEFT, 9710 null /* initialBounds */); 9711 } 9712 boolean result = mStackSupervisor.moveTaskToStackLocked(taskId, stackId, toTop, 9713 !FORCE_FOCUS, "moveTaskToStack", ANIMATE); 9714 if (result && stackId == DOCKED_STACK_ID) { 9715 // If task moved to docked stack - show recents if needed. 9716 mStackSupervisor.moveHomeStackTaskToTop(RECENTS_ACTIVITY_TYPE, 9717 "moveTaskToDockedStack"); 9718 } 9719 } finally { 9720 Binder.restoreCallingIdentity(ident); 9721 } 9722 } 9723 } 9724 9725 @Override 9726 public void swapDockedAndFullscreenStack() throws RemoteException { 9727 enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "swapDockedAndFullscreenStack()"); 9728 synchronized (this) { 9729 long ident = Binder.clearCallingIdentity(); 9730 try { 9731 final ActivityStack fullscreenStack = mStackSupervisor.getStack( 9732 FULLSCREEN_WORKSPACE_STACK_ID); 9733 final TaskRecord topTask = fullscreenStack != null ? fullscreenStack.topTask() 9734 : null; 9735 final ActivityStack dockedStack = mStackSupervisor.getStack(DOCKED_STACK_ID); 9736 final ArrayList<TaskRecord> tasks = dockedStack != null ? dockedStack.getAllTasks() 9737 : null; 9738 if (topTask == null || tasks == null || tasks.size() == 0) { 9739 Slog.w(TAG, 9740 "Unable to swap tasks, either docked or fullscreen stack is empty."); 9741 return; 9742 } 9743 9744 // TODO: App transition 9745 mWindowManager.prepareAppTransition(TRANSIT_ACTIVITY_RELAUNCH, false); 9746 9747 // Defer the resume so resume/pausing while moving stacks is dangerous. 9748 mStackSupervisor.moveTaskToStackLocked(topTask.taskId, DOCKED_STACK_ID, 9749 false /* toTop */, !FORCE_FOCUS, "swapDockedAndFullscreenStack", 9750 ANIMATE, true /* deferResume */); 9751 final int size = tasks.size(); 9752 for (int i = 0; i < size; i++) { 9753 final int id = tasks.get(i).taskId; 9754 if (id == topTask.taskId) { 9755 continue; 9756 } 9757 mStackSupervisor.moveTaskToStackLocked(id, 9758 FULLSCREEN_WORKSPACE_STACK_ID, true /* toTop */, !FORCE_FOCUS, 9759 "swapDockedAndFullscreenStack", ANIMATE, true /* deferResume */); 9760 } 9761 9762 // Because we deferred the resume, to avoid conflicts with stack switches while 9763 // resuming, we need to do it after all the tasks are moved. 9764 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0, !PRESERVE_WINDOWS); 9765 mStackSupervisor.resumeFocusedStackTopActivityLocked(); 9766 9767 mWindowManager.executeAppTransition(); 9768 } finally { 9769 Binder.restoreCallingIdentity(ident); 9770 } 9771 } 9772 } 9773 9774 /** 9775 * Moves the input task to the docked stack. 9776 * 9777 * @param taskId Id of task to move. 9778 * @param createMode The mode the docked stack should be created in if it doesn't exist 9779 * already. See 9780 * {@link android.app.ActivityManager#DOCKED_STACK_CREATE_MODE_TOP_OR_LEFT} 9781 * and 9782 * {@link android.app.ActivityManager#DOCKED_STACK_CREATE_MODE_BOTTOM_OR_RIGHT} 9783 * @param toTop If the task and stack should be moved to the top. 9784 * @param animate Whether we should play an animation for the moving the task 9785 * @param initialBounds If the docked stack gets created, it will use these bounds for the 9786 * docked stack. Pass {@code null} to use default bounds. 9787 */ 9788 @Override 9789 public boolean moveTaskToDockedStack(int taskId, int createMode, boolean toTop, boolean animate, 9790 Rect initialBounds, boolean moveHomeStackFront) { 9791 enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "moveTaskToDockedStack()"); 9792 synchronized (this) { 9793 long ident = Binder.clearCallingIdentity(); 9794 try { 9795 if (DEBUG_STACK) Slog.d(TAG_STACK, "moveTaskToDockedStack: moving task=" + taskId 9796 + " to createMode=" + createMode + " toTop=" + toTop); 9797 mWindowManager.setDockedStackCreateState(createMode, initialBounds); 9798 final boolean moved = mStackSupervisor.moveTaskToStackLocked( 9799 taskId, DOCKED_STACK_ID, toTop, !FORCE_FOCUS, "moveTaskToDockedStack", 9800 animate, DEFER_RESUME); 9801 if (moved) { 9802 if (moveHomeStackFront) { 9803 mStackSupervisor.moveHomeStackToFront("moveTaskToDockedStack"); 9804 } 9805 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0, !PRESERVE_WINDOWS); 9806 } 9807 return moved; 9808 } finally { 9809 Binder.restoreCallingIdentity(ident); 9810 } 9811 } 9812 } 9813 9814 /** 9815 * Moves the top activity in the input stackId to the pinned stack. 9816 * 9817 * @param stackId Id of stack to move the top activity to pinned stack. 9818 * @param bounds Bounds to use for pinned stack. 9819 * 9820 * @return True if the top activity of the input stack was successfully moved to the pinned 9821 * stack. 9822 */ 9823 @Override 9824 public boolean moveTopActivityToPinnedStack(int stackId, Rect bounds) { 9825 enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "moveTopActivityToPinnedStack()"); 9826 synchronized (this) { 9827 if (!mSupportsPictureInPicture) { 9828 throw new IllegalStateException("moveTopActivityToPinnedStack:" 9829 + "Device doesn't support picture-in-pciture mode"); 9830 } 9831 9832 long ident = Binder.clearCallingIdentity(); 9833 try { 9834 return mStackSupervisor.moveTopStackActivityToPinnedStackLocked(stackId, bounds); 9835 } finally { 9836 Binder.restoreCallingIdentity(ident); 9837 } 9838 } 9839 } 9840 9841 @Override 9842 public void resizeStack(int stackId, Rect bounds, boolean allowResizeInDockedMode, 9843 boolean preserveWindows, boolean animate, int animationDuration) { 9844 enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "resizeStack()"); 9845 long ident = Binder.clearCallingIdentity(); 9846 try { 9847 synchronized (this) { 9848 if (animate) { 9849 if (stackId == PINNED_STACK_ID) { 9850 mWindowManager.animateResizePinnedStack(bounds, animationDuration); 9851 } else { 9852 throw new IllegalArgumentException("Stack: " + stackId 9853 + " doesn't support animated resize."); 9854 } 9855 } else { 9856 mStackSupervisor.resizeStackLocked(stackId, bounds, null /* tempTaskBounds */, 9857 null /* tempTaskInsetBounds */, preserveWindows, 9858 allowResizeInDockedMode, !DEFER_RESUME); 9859 } 9860 } 9861 } finally { 9862 Binder.restoreCallingIdentity(ident); 9863 } 9864 } 9865 9866 @Override 9867 public void resizeDockedStack(Rect dockedBounds, Rect tempDockedTaskBounds, 9868 Rect tempDockedTaskInsetBounds, 9869 Rect tempOtherTaskBounds, Rect tempOtherTaskInsetBounds) { 9870 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 9871 "resizeDockedStack()"); 9872 long ident = Binder.clearCallingIdentity(); 9873 try { 9874 synchronized (this) { 9875 mStackSupervisor.resizeDockedStackLocked(dockedBounds, tempDockedTaskBounds, 9876 tempDockedTaskInsetBounds, tempOtherTaskBounds, tempOtherTaskInsetBounds, 9877 PRESERVE_WINDOWS); 9878 } 9879 } finally { 9880 Binder.restoreCallingIdentity(ident); 9881 } 9882 } 9883 9884 @Override 9885 public void resizePinnedStack(Rect pinnedBounds, Rect tempPinnedTaskBounds) { 9886 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 9887 "resizePinnedStack()"); 9888 final long ident = Binder.clearCallingIdentity(); 9889 try { 9890 synchronized (this) { 9891 mStackSupervisor.resizePinnedStackLocked(pinnedBounds, tempPinnedTaskBounds); 9892 } 9893 } finally { 9894 Binder.restoreCallingIdentity(ident); 9895 } 9896 } 9897 9898 @Override 9899 public void positionTaskInStack(int taskId, int stackId, int position) { 9900 enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "positionTaskInStack()"); 9901 if (stackId == HOME_STACK_ID) { 9902 throw new IllegalArgumentException( 9903 "positionTaskInStack: Attempt to change the position of task " 9904 + taskId + " in/to home stack"); 9905 } 9906 synchronized (this) { 9907 long ident = Binder.clearCallingIdentity(); 9908 try { 9909 if (DEBUG_STACK) Slog.d(TAG_STACK, 9910 "positionTaskInStack: positioning task=" + taskId 9911 + " in stackId=" + stackId + " at position=" + position); 9912 mStackSupervisor.positionTaskInStackLocked(taskId, stackId, position); 9913 } finally { 9914 Binder.restoreCallingIdentity(ident); 9915 } 9916 } 9917 } 9918 9919 @Override 9920 public List<StackInfo> getAllStackInfos() { 9921 enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "getAllStackInfos()"); 9922 long ident = Binder.clearCallingIdentity(); 9923 try { 9924 synchronized (this) { 9925 return mStackSupervisor.getAllStackInfosLocked(); 9926 } 9927 } finally { 9928 Binder.restoreCallingIdentity(ident); 9929 } 9930 } 9931 9932 @Override 9933 public StackInfo getStackInfo(int stackId) { 9934 enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "getStackInfo()"); 9935 long ident = Binder.clearCallingIdentity(); 9936 try { 9937 synchronized (this) { 9938 return mStackSupervisor.getStackInfoLocked(stackId); 9939 } 9940 } finally { 9941 Binder.restoreCallingIdentity(ident); 9942 } 9943 } 9944 9945 @Override 9946 public boolean isInHomeStack(int taskId) { 9947 enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "getStackInfo()"); 9948 long ident = Binder.clearCallingIdentity(); 9949 try { 9950 synchronized (this) { 9951 final TaskRecord tr = mStackSupervisor.anyTaskForIdLocked( 9952 taskId, !RESTORE_FROM_RECENTS, INVALID_STACK_ID); 9953 return tr != null && tr.stack != null && tr.stack.isHomeStack(); 9954 } 9955 } finally { 9956 Binder.restoreCallingIdentity(ident); 9957 } 9958 } 9959 9960 @Override 9961 public int getTaskForActivity(IBinder token, boolean onlyRoot) { 9962 synchronized(this) { 9963 return ActivityRecord.getTaskForActivityLocked(token, onlyRoot); 9964 } 9965 } 9966 9967 @Override 9968 public void updateDeviceOwner(String packageName) { 9969 final int callingUid = Binder.getCallingUid(); 9970 if (callingUid != 0 && callingUid != Process.SYSTEM_UID) { 9971 throw new SecurityException("updateDeviceOwner called from non-system process"); 9972 } 9973 synchronized (this) { 9974 mDeviceOwnerName = packageName; 9975 } 9976 } 9977 9978 @Override 9979 public void updateLockTaskPackages(int userId, String[] packages) { 9980 final int callingUid = Binder.getCallingUid(); 9981 if (callingUid != 0 && callingUid != Process.SYSTEM_UID) { 9982 enforceCallingPermission(android.Manifest.permission.UPDATE_LOCK_TASK_PACKAGES, 9983 "updateLockTaskPackages()"); 9984 } 9985 synchronized (this) { 9986 if (DEBUG_LOCKTASK) Slog.w(TAG_LOCKTASK, "Whitelisting " + userId + ":" + 9987 Arrays.toString(packages)); 9988 mLockTaskPackages.put(userId, packages); 9989 mStackSupervisor.onLockTaskPackagesUpdatedLocked(); 9990 } 9991 } 9992 9993 9994 void startLockTaskModeLocked(TaskRecord task) { 9995 if (DEBUG_LOCKTASK) Slog.w(TAG_LOCKTASK, "startLockTaskModeLocked: " + task); 9996 if (task.mLockTaskAuth == LOCK_TASK_AUTH_DONT_LOCK) { 9997 return; 9998 } 9999 10000 // isSystemInitiated is used to distinguish between locked and pinned mode, as pinned mode 10001 // is initiated by system after the pinning request was shown and locked mode is initiated 10002 // by an authorized app directly 10003 final int callingUid = Binder.getCallingUid(); 10004 boolean isSystemInitiated = callingUid == Process.SYSTEM_UID; 10005 long ident = Binder.clearCallingIdentity(); 10006 try { 10007 if (!isSystemInitiated) { 10008 task.mLockTaskUid = callingUid; 10009 if (task.mLockTaskAuth == LOCK_TASK_AUTH_PINNABLE) { 10010 // startLockTask() called by app and task mode is lockTaskModeDefault. 10011 if (DEBUG_LOCKTASK) Slog.w(TAG_LOCKTASK, "Mode default, asking user"); 10012 StatusBarManagerInternal statusBarManager = 10013 LocalServices.getService(StatusBarManagerInternal.class); 10014 if (statusBarManager != null) { 10015 statusBarManager.showScreenPinningRequest(task.taskId); 10016 } 10017 return; 10018 } 10019 10020 final ActivityStack stack = mStackSupervisor.getFocusedStack(); 10021 if (stack == null || task != stack.topTask()) { 10022 throw new IllegalArgumentException("Invalid task, not in foreground"); 10023 } 10024 } 10025 if (DEBUG_LOCKTASK) Slog.w(TAG_LOCKTASK, isSystemInitiated ? "Locking pinned" : 10026 "Locking fully"); 10027 mStackSupervisor.setLockTaskModeLocked(task, isSystemInitiated ? 10028 ActivityManager.LOCK_TASK_MODE_PINNED : 10029 ActivityManager.LOCK_TASK_MODE_LOCKED, 10030 "startLockTask", true); 10031 } finally { 10032 Binder.restoreCallingIdentity(ident); 10033 } 10034 } 10035 10036 @Override 10037 public void startLockTaskMode(int taskId) { 10038 synchronized (this) { 10039 final TaskRecord task = mStackSupervisor.anyTaskForIdLocked(taskId); 10040 if (task != null) { 10041 startLockTaskModeLocked(task); 10042 } 10043 } 10044 } 10045 10046 @Override 10047 public void startLockTaskMode(IBinder token) { 10048 synchronized (this) { 10049 final ActivityRecord r = ActivityRecord.forTokenLocked(token); 10050 if (r == null) { 10051 return; 10052 } 10053 final TaskRecord task = r.task; 10054 if (task != null) { 10055 startLockTaskModeLocked(task); 10056 } 10057 } 10058 } 10059 10060 @Override 10061 public void startSystemLockTaskMode(int taskId) throws RemoteException { 10062 enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "startSystemLockTaskMode"); 10063 // This makes inner call to look as if it was initiated by system. 10064 long ident = Binder.clearCallingIdentity(); 10065 try { 10066 synchronized (this) { 10067 startLockTaskMode(taskId); 10068 } 10069 } finally { 10070 Binder.restoreCallingIdentity(ident); 10071 } 10072 } 10073 10074 @Override 10075 public void stopLockTaskMode() { 10076 final TaskRecord lockTask = mStackSupervisor.getLockedTaskLocked(); 10077 if (lockTask == null) { 10078 // Our work here is done. 10079 return; 10080 } 10081 10082 final int callingUid = Binder.getCallingUid(); 10083 final int lockTaskUid = lockTask.mLockTaskUid; 10084 final int lockTaskModeState = mStackSupervisor.getLockTaskModeState(); 10085 if (lockTaskModeState == ActivityManager.LOCK_TASK_MODE_NONE) { 10086 // Done. 10087 return; 10088 } else { 10089 // Ensure the same caller for startLockTaskMode and stopLockTaskMode. 10090 // It is possible lockTaskMode was started by the system process because 10091 // android:lockTaskMode is set to a locking value in the application manifest 10092 // instead of the app calling startLockTaskMode. In this case 10093 // {@link TaskRecord.mLockTaskUid} will be 0, so we compare the callingUid to the 10094 // {@link TaskRecord.effectiveUid} instead. Also caller with 10095 // {@link MANAGE_ACTIVITY_STACKS} can stop any lock task. 10096 if (checkCallingPermission(MANAGE_ACTIVITY_STACKS) != PERMISSION_GRANTED 10097 && callingUid != lockTaskUid 10098 && (lockTaskUid != 0 || callingUid != lockTask.effectiveUid)) { 10099 throw new SecurityException("Invalid uid, expected " + lockTaskUid 10100 + " callingUid=" + callingUid + " effectiveUid=" + lockTask.effectiveUid); 10101 } 10102 } 10103 long ident = Binder.clearCallingIdentity(); 10104 try { 10105 Log.d(TAG, "stopLockTaskMode"); 10106 // Stop lock task 10107 synchronized (this) { 10108 mStackSupervisor.setLockTaskModeLocked(null, ActivityManager.LOCK_TASK_MODE_NONE, 10109 "stopLockTask", true); 10110 } 10111 } finally { 10112 Binder.restoreCallingIdentity(ident); 10113 } 10114 } 10115 10116 /** 10117 * This API should be called by SystemUI only when user perform certain action to dismiss 10118 * lock task mode. We should only dismiss pinned lock task mode in this case. 10119 */ 10120 @Override 10121 public void stopSystemLockTaskMode() throws RemoteException { 10122 if (mStackSupervisor.getLockTaskModeState() == ActivityManager.LOCK_TASK_MODE_PINNED) { 10123 stopLockTaskMode(); 10124 } else { 10125 mStackSupervisor.showLockTaskToast(); 10126 } 10127 } 10128 10129 @Override 10130 public boolean isInLockTaskMode() { 10131 return getLockTaskModeState() != ActivityManager.LOCK_TASK_MODE_NONE; 10132 } 10133 10134 @Override 10135 public int getLockTaskModeState() { 10136 synchronized (this) { 10137 return mStackSupervisor.getLockTaskModeState(); 10138 } 10139 } 10140 10141 @Override 10142 public void showLockTaskEscapeMessage(IBinder token) { 10143 synchronized (this) { 10144 final ActivityRecord r = ActivityRecord.forTokenLocked(token); 10145 if (r == null) { 10146 return; 10147 } 10148 mStackSupervisor.showLockTaskEscapeMessageLocked(r.task); 10149 } 10150 } 10151 10152 // ========================================================= 10153 // CONTENT PROVIDERS 10154 // ========================================================= 10155 10156 private final List<ProviderInfo> generateApplicationProvidersLocked(ProcessRecord app) { 10157 List<ProviderInfo> providers = null; 10158 try { 10159 providers = AppGlobals.getPackageManager() 10160 .queryContentProviders(app.processName, app.uid, 10161 STOCK_PM_FLAGS | PackageManager.GET_URI_PERMISSION_PATTERNS 10162 | MATCH_DEBUG_TRIAGED_MISSING) 10163 .getList(); 10164 } catch (RemoteException ex) { 10165 } 10166 if (DEBUG_MU) Slog.v(TAG_MU, 10167 "generateApplicationProvidersLocked, app.info.uid = " + app.uid); 10168 int userId = app.userId; 10169 if (providers != null) { 10170 int N = providers.size(); 10171 app.pubProviders.ensureCapacity(N + app.pubProviders.size()); 10172 for (int i=0; i<N; i++) { 10173 // TODO: keep logic in sync with installEncryptionUnawareProviders 10174 ProviderInfo cpi = 10175 (ProviderInfo)providers.get(i); 10176 boolean singleton = isSingleton(cpi.processName, cpi.applicationInfo, 10177 cpi.name, cpi.flags); 10178 if (singleton && UserHandle.getUserId(app.uid) != UserHandle.USER_SYSTEM) { 10179 // This is a singleton provider, but a user besides the 10180 // default user is asking to initialize a process it runs 10181 // in... well, no, it doesn't actually run in this process, 10182 // it runs in the process of the default user. Get rid of it. 10183 providers.remove(i); 10184 N--; 10185 i--; 10186 continue; 10187 } 10188 10189 ComponentName comp = new ComponentName(cpi.packageName, cpi.name); 10190 ContentProviderRecord cpr = mProviderMap.getProviderByClass(comp, userId); 10191 if (cpr == null) { 10192 cpr = new ContentProviderRecord(this, cpi, app.info, comp, singleton); 10193 mProviderMap.putProviderByClass(comp, cpr); 10194 } 10195 if (DEBUG_MU) Slog.v(TAG_MU, 10196 "generateApplicationProvidersLocked, cpi.uid = " + cpr.uid); 10197 app.pubProviders.put(cpi.name, cpr); 10198 if (!cpi.multiprocess || !"android".equals(cpi.packageName)) { 10199 // Don't add this if it is a platform component that is marked 10200 // to run in multiple processes, because this is actually 10201 // part of the framework so doesn't make sense to track as a 10202 // separate apk in the process. 10203 app.addPackage(cpi.applicationInfo.packageName, cpi.applicationInfo.versionCode, 10204 mProcessStats); 10205 } 10206 notifyPackageUse(cpi.applicationInfo.packageName, 10207 PackageManager.NOTIFY_PACKAGE_USE_CONTENT_PROVIDER); 10208 } 10209 } 10210 return providers; 10211 } 10212 10213 /** 10214 * Check if {@link ProcessRecord} has a possible chance at accessing the 10215 * given {@link ProviderInfo}. Final permission checking is always done 10216 * in {@link ContentProvider}. 10217 */ 10218 private final String checkContentProviderPermissionLocked( 10219 ProviderInfo cpi, ProcessRecord r, int userId, boolean checkUser) { 10220 final int callingPid = (r != null) ? r.pid : Binder.getCallingPid(); 10221 final int callingUid = (r != null) ? r.uid : Binder.getCallingUid(); 10222 boolean checkedGrants = false; 10223 if (checkUser) { 10224 // Looking for cross-user grants before enforcing the typical cross-users permissions 10225 int tmpTargetUserId = mUserController.unsafeConvertIncomingUserLocked(userId); 10226 if (tmpTargetUserId != UserHandle.getUserId(callingUid)) { 10227 if (checkAuthorityGrants(callingUid, cpi, tmpTargetUserId, checkUser)) { 10228 return null; 10229 } 10230 checkedGrants = true; 10231 } 10232 userId = mUserController.handleIncomingUser(callingPid, callingUid, userId, false, 10233 ALLOW_NON_FULL, "checkContentProviderPermissionLocked " + cpi.authority, null); 10234 if (userId != tmpTargetUserId) { 10235 // When we actually went to determine the final targer user ID, this ended 10236 // up different than our initial check for the authority. This is because 10237 // they had asked for USER_CURRENT_OR_SELF and we ended up switching to 10238 // SELF. So we need to re-check the grants again. 10239 checkedGrants = false; 10240 } 10241 } 10242 if (checkComponentPermission(cpi.readPermission, callingPid, callingUid, 10243 cpi.applicationInfo.uid, cpi.exported) 10244 == PackageManager.PERMISSION_GRANTED) { 10245 return null; 10246 } 10247 if (checkComponentPermission(cpi.writePermission, callingPid, callingUid, 10248 cpi.applicationInfo.uid, cpi.exported) 10249 == PackageManager.PERMISSION_GRANTED) { 10250 return null; 10251 } 10252 10253 PathPermission[] pps = cpi.pathPermissions; 10254 if (pps != null) { 10255 int i = pps.length; 10256 while (i > 0) { 10257 i--; 10258 PathPermission pp = pps[i]; 10259 String pprperm = pp.getReadPermission(); 10260 if (pprperm != null && checkComponentPermission(pprperm, callingPid, callingUid, 10261 cpi.applicationInfo.uid, cpi.exported) 10262 == PackageManager.PERMISSION_GRANTED) { 10263 return null; 10264 } 10265 String ppwperm = pp.getWritePermission(); 10266 if (ppwperm != null && checkComponentPermission(ppwperm, callingPid, callingUid, 10267 cpi.applicationInfo.uid, cpi.exported) 10268 == PackageManager.PERMISSION_GRANTED) { 10269 return null; 10270 } 10271 } 10272 } 10273 if (!checkedGrants && checkAuthorityGrants(callingUid, cpi, userId, checkUser)) { 10274 return null; 10275 } 10276 10277 String msg; 10278 if (!cpi.exported) { 10279 msg = "Permission Denial: opening provider " + cpi.name 10280 + " from " + (r != null ? r : "(null)") + " (pid=" + callingPid 10281 + ", uid=" + callingUid + ") that is not exported from uid " 10282 + cpi.applicationInfo.uid; 10283 } else { 10284 msg = "Permission Denial: opening provider " + cpi.name 10285 + " from " + (r != null ? r : "(null)") + " (pid=" + callingPid 10286 + ", uid=" + callingUid + ") requires " 10287 + cpi.readPermission + " or " + cpi.writePermission; 10288 } 10289 Slog.w(TAG, msg); 10290 return msg; 10291 } 10292 10293 /** 10294 * Returns if the ContentProvider has granted a uri to callingUid 10295 */ 10296 boolean checkAuthorityGrants(int callingUid, ProviderInfo cpi, int userId, boolean checkUser) { 10297 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get(callingUid); 10298 if (perms != null) { 10299 for (int i=perms.size()-1; i>=0; i--) { 10300 GrantUri grantUri = perms.keyAt(i); 10301 if (grantUri.sourceUserId == userId || !checkUser) { 10302 if (matchesProvider(grantUri.uri, cpi)) { 10303 return true; 10304 } 10305 } 10306 } 10307 } 10308 return false; 10309 } 10310 10311 /** 10312 * Returns true if the uri authority is one of the authorities specified in the provider. 10313 */ 10314 boolean matchesProvider(Uri uri, ProviderInfo cpi) { 10315 String uriAuth = uri.getAuthority(); 10316 String cpiAuth = cpi.authority; 10317 if (cpiAuth.indexOf(';') == -1) { 10318 return cpiAuth.equals(uriAuth); 10319 } 10320 String[] cpiAuths = cpiAuth.split(";"); 10321 int length = cpiAuths.length; 10322 for (int i = 0; i < length; i++) { 10323 if (cpiAuths[i].equals(uriAuth)) return true; 10324 } 10325 return false; 10326 } 10327 10328 ContentProviderConnection incProviderCountLocked(ProcessRecord r, 10329 final ContentProviderRecord cpr, IBinder externalProcessToken, boolean stable) { 10330 if (r != null) { 10331 for (int i=0; i<r.conProviders.size(); i++) { 10332 ContentProviderConnection conn = r.conProviders.get(i); 10333 if (conn.provider == cpr) { 10334 if (DEBUG_PROVIDER) Slog.v(TAG_PROVIDER, 10335 "Adding provider requested by " 10336 + r.processName + " from process " 10337 + cpr.info.processName + ": " + cpr.name.flattenToShortString() 10338 + " scnt=" + conn.stableCount + " uscnt=" + conn.unstableCount); 10339 if (stable) { 10340 conn.stableCount++; 10341 conn.numStableIncs++; 10342 } else { 10343 conn.unstableCount++; 10344 conn.numUnstableIncs++; 10345 } 10346 return conn; 10347 } 10348 } 10349 ContentProviderConnection conn = new ContentProviderConnection(cpr, r); 10350 if (stable) { 10351 conn.stableCount = 1; 10352 conn.numStableIncs = 1; 10353 } else { 10354 conn.unstableCount = 1; 10355 conn.numUnstableIncs = 1; 10356 } 10357 cpr.connections.add(conn); 10358 r.conProviders.add(conn); 10359 startAssociationLocked(r.uid, r.processName, r.curProcState, 10360 cpr.uid, cpr.name, cpr.info.processName); 10361 return conn; 10362 } 10363 cpr.addExternalProcessHandleLocked(externalProcessToken); 10364 return null; 10365 } 10366 10367 boolean decProviderCountLocked(ContentProviderConnection conn, 10368 ContentProviderRecord cpr, IBinder externalProcessToken, boolean stable) { 10369 if (conn != null) { 10370 cpr = conn.provider; 10371 if (DEBUG_PROVIDER) Slog.v(TAG_PROVIDER, 10372 "Removing provider requested by " 10373 + conn.client.processName + " from process " 10374 + cpr.info.processName + ": " + cpr.name.flattenToShortString() 10375 + " scnt=" + conn.stableCount + " uscnt=" + conn.unstableCount); 10376 if (stable) { 10377 conn.stableCount--; 10378 } else { 10379 conn.unstableCount--; 10380 } 10381 if (conn.stableCount == 0 && conn.unstableCount == 0) { 10382 cpr.connections.remove(conn); 10383 conn.client.conProviders.remove(conn); 10384 if (conn.client.setProcState < ActivityManager.PROCESS_STATE_LAST_ACTIVITY) { 10385 // The client is more important than last activity -- note the time this 10386 // is happening, so we keep the old provider process around a bit as last 10387 // activity to avoid thrashing it. 10388 if (cpr.proc != null) { 10389 cpr.proc.lastProviderTime = SystemClock.uptimeMillis(); 10390 } 10391 } 10392 stopAssociationLocked(conn.client.uid, conn.client.processName, cpr.uid, cpr.name); 10393 return true; 10394 } 10395 return false; 10396 } 10397 cpr.removeExternalProcessHandleLocked(externalProcessToken); 10398 return false; 10399 } 10400 10401 private void checkTime(long startTime, String where) { 10402 long now = SystemClock.uptimeMillis(); 10403 if ((now-startTime) > 50) { 10404 // If we are taking more than 50ms, log about it. 10405 Slog.w(TAG, "Slow operation: " + (now-startTime) + "ms so far, now at " + where); 10406 } 10407 } 10408 10409 private ContentProviderHolder getContentProviderImpl(IApplicationThread caller, 10410 String name, IBinder token, boolean stable, int userId) { 10411 ContentProviderRecord cpr; 10412 ContentProviderConnection conn = null; 10413 ProviderInfo cpi = null; 10414 10415 synchronized(this) { 10416 long startTime = SystemClock.uptimeMillis(); 10417 10418 ProcessRecord r = null; 10419 if (caller != null) { 10420 r = getRecordForAppLocked(caller); 10421 if (r == null) { 10422 throw new SecurityException( 10423 "Unable to find app for caller " + caller 10424 + " (pid=" + Binder.getCallingPid() 10425 + ") when getting content provider " + name); 10426 } 10427 } 10428 10429 boolean checkCrossUser = true; 10430 10431 checkTime(startTime, "getContentProviderImpl: getProviderByName"); 10432 10433 // First check if this content provider has been published... 10434 cpr = mProviderMap.getProviderByName(name, userId); 10435 // If that didn't work, check if it exists for user 0 and then 10436 // verify that it's a singleton provider before using it. 10437 if (cpr == null && userId != UserHandle.USER_SYSTEM) { 10438 cpr = mProviderMap.getProviderByName(name, UserHandle.USER_SYSTEM); 10439 if (cpr != null) { 10440 cpi = cpr.info; 10441 if (isSingleton(cpi.processName, cpi.applicationInfo, 10442 cpi.name, cpi.flags) 10443 && isValidSingletonCall(r.uid, cpi.applicationInfo.uid)) { 10444 userId = UserHandle.USER_SYSTEM; 10445 checkCrossUser = false; 10446 } else { 10447 cpr = null; 10448 cpi = null; 10449 } 10450 } 10451 } 10452 10453 boolean providerRunning = cpr != null; 10454 if (providerRunning) { 10455 cpi = cpr.info; 10456 String msg; 10457 checkTime(startTime, "getContentProviderImpl: before checkContentProviderPermission"); 10458 if ((msg = checkContentProviderPermissionLocked(cpi, r, userId, checkCrossUser)) 10459 != null) { 10460 throw new SecurityException(msg); 10461 } 10462 checkTime(startTime, "getContentProviderImpl: after checkContentProviderPermission"); 10463 10464 if (r != null && cpr.canRunHere(r)) { 10465 // This provider has been published or is in the process 10466 // of being published... but it is also allowed to run 10467 // in the caller's process, so don't make a connection 10468 // and just let the caller instantiate its own instance. 10469 ContentProviderHolder holder = cpr.newHolder(null); 10470 // don't give caller the provider object, it needs 10471 // to make its own. 10472 holder.provider = null; 10473 return holder; 10474 } 10475 10476 final long origId = Binder.clearCallingIdentity(); 10477 10478 checkTime(startTime, "getContentProviderImpl: incProviderCountLocked"); 10479 10480 // In this case the provider instance already exists, so we can 10481 // return it right away. 10482 conn = incProviderCountLocked(r, cpr, token, stable); 10483 if (conn != null && (conn.stableCount+conn.unstableCount) == 1) { 10484 if (cpr.proc != null && r.setAdj <= ProcessList.PERCEPTIBLE_APP_ADJ) { 10485 // If this is a perceptible app accessing the provider, 10486 // make sure to count it as being accessed and thus 10487 // back up on the LRU list. This is good because 10488 // content providers are often expensive to start. 10489 checkTime(startTime, "getContentProviderImpl: before updateLruProcess"); 10490 updateLruProcessLocked(cpr.proc, false, null); 10491 checkTime(startTime, "getContentProviderImpl: after updateLruProcess"); 10492 } 10493 } 10494 10495 if (cpr.proc != null) { 10496 checkTime(startTime, "getContentProviderImpl: before updateOomAdj"); 10497 boolean success = updateOomAdjLocked(cpr.proc); 10498 maybeUpdateProviderUsageStatsLocked(r, cpr.info.packageName, name); 10499 checkTime(startTime, "getContentProviderImpl: after updateOomAdj"); 10500 if (DEBUG_PROVIDER) Slog.i(TAG_PROVIDER, "Adjust success: " + success); 10501 // NOTE: there is still a race here where a signal could be 10502 // pending on the process even though we managed to update its 10503 // adj level. Not sure what to do about this, but at least 10504 // the race is now smaller. 10505 if (!success) { 10506 // Uh oh... it looks like the provider's process 10507 // has been killed on us. We need to wait for a new 10508 // process to be started, and make sure its death 10509 // doesn't kill our process. 10510 Slog.i(TAG, "Existing provider " + cpr.name.flattenToShortString() 10511 + " is crashing; detaching " + r); 10512 boolean lastRef = decProviderCountLocked(conn, cpr, token, stable); 10513 checkTime(startTime, "getContentProviderImpl: before appDied"); 10514 appDiedLocked(cpr.proc); 10515 checkTime(startTime, "getContentProviderImpl: after appDied"); 10516 if (!lastRef) { 10517 // This wasn't the last ref our process had on 10518 // the provider... we have now been killed, bail. 10519 return null; 10520 } 10521 providerRunning = false; 10522 conn = null; 10523 } 10524 } 10525 10526 Binder.restoreCallingIdentity(origId); 10527 } 10528 10529 if (!providerRunning) { 10530 try { 10531 checkTime(startTime, "getContentProviderImpl: before resolveContentProvider"); 10532 cpi = AppGlobals.getPackageManager(). 10533 resolveContentProvider(name, 10534 STOCK_PM_FLAGS | PackageManager.GET_URI_PERMISSION_PATTERNS, userId); 10535 checkTime(startTime, "getContentProviderImpl: after resolveContentProvider"); 10536 } catch (RemoteException ex) { 10537 } 10538 if (cpi == null) { 10539 return null; 10540 } 10541 // If the provider is a singleton AND 10542 // (it's a call within the same user || the provider is a 10543 // privileged app) 10544 // Then allow connecting to the singleton provider 10545 boolean singleton = isSingleton(cpi.processName, cpi.applicationInfo, 10546 cpi.name, cpi.flags) 10547 && isValidSingletonCall(r.uid, cpi.applicationInfo.uid); 10548 if (singleton) { 10549 userId = UserHandle.USER_SYSTEM; 10550 } 10551 cpi.applicationInfo = getAppInfoForUser(cpi.applicationInfo, userId); 10552 checkTime(startTime, "getContentProviderImpl: got app info for user"); 10553 10554 String msg; 10555 checkTime(startTime, "getContentProviderImpl: before checkContentProviderPermission"); 10556 if ((msg = checkContentProviderPermissionLocked(cpi, r, userId, !singleton)) 10557 != null) { 10558 throw new SecurityException(msg); 10559 } 10560 checkTime(startTime, "getContentProviderImpl: after checkContentProviderPermission"); 10561 10562 if (!mProcessesReady 10563 && !cpi.processName.equals("system")) { 10564 // If this content provider does not run in the system 10565 // process, and the system is not yet ready to run other 10566 // processes, then fail fast instead of hanging. 10567 throw new IllegalArgumentException( 10568 "Attempt to launch content provider before system ready"); 10569 } 10570 10571 // Make sure that the user who owns this provider is running. If not, 10572 // we don't want to allow it to run. 10573 if (!mUserController.isUserRunningLocked(userId, 0)) { 10574 Slog.w(TAG, "Unable to launch app " 10575 + cpi.applicationInfo.packageName + "/" 10576 + cpi.applicationInfo.uid + " for provider " 10577 + name + ": user " + userId + " is stopped"); 10578 return null; 10579 } 10580 10581 ComponentName comp = new ComponentName(cpi.packageName, cpi.name); 10582 checkTime(startTime, "getContentProviderImpl: before getProviderByClass"); 10583 cpr = mProviderMap.getProviderByClass(comp, userId); 10584 checkTime(startTime, "getContentProviderImpl: after getProviderByClass"); 10585 final boolean firstClass = cpr == null; 10586 if (firstClass) { 10587 final long ident = Binder.clearCallingIdentity(); 10588 10589 // If permissions need a review before any of the app components can run, 10590 // we return no provider and launch a review activity if the calling app 10591 // is in the foreground. 10592 if (Build.PERMISSIONS_REVIEW_REQUIRED) { 10593 if (!requestTargetProviderPermissionsReviewIfNeededLocked(cpi, r, userId)) { 10594 return null; 10595 } 10596 } 10597 10598 try { 10599 checkTime(startTime, "getContentProviderImpl: before getApplicationInfo"); 10600 ApplicationInfo ai = 10601 AppGlobals.getPackageManager(). 10602 getApplicationInfo( 10603 cpi.applicationInfo.packageName, 10604 STOCK_PM_FLAGS, userId); 10605 checkTime(startTime, "getContentProviderImpl: after getApplicationInfo"); 10606 if (ai == null) { 10607 Slog.w(TAG, "No package info for content provider " 10608 + cpi.name); 10609 return null; 10610 } 10611 ai = getAppInfoForUser(ai, userId); 10612 cpr = new ContentProviderRecord(this, cpi, ai, comp, singleton); 10613 } catch (RemoteException ex) { 10614 // pm is in same process, this will never happen. 10615 } finally { 10616 Binder.restoreCallingIdentity(ident); 10617 } 10618 } 10619 10620 checkTime(startTime, "getContentProviderImpl: now have ContentProviderRecord"); 10621 10622 if (r != null && cpr.canRunHere(r)) { 10623 // If this is a multiprocess provider, then just return its 10624 // info and allow the caller to instantiate it. Only do 10625 // this if the provider is the same user as the caller's 10626 // process, or can run as root (so can be in any process). 10627 return cpr.newHolder(null); 10628 } 10629 10630 if (DEBUG_PROVIDER) Slog.w(TAG_PROVIDER, "LAUNCHING REMOTE PROVIDER (myuid " 10631 + (r != null ? r.uid : null) + " pruid " + cpr.appInfo.uid + "): " 10632 + cpr.info.name + " callers=" + Debug.getCallers(6)); 10633 10634 // This is single process, and our app is now connecting to it. 10635 // See if we are already in the process of launching this 10636 // provider. 10637 final int N = mLaunchingProviders.size(); 10638 int i; 10639 for (i = 0; i < N; i++) { 10640 if (mLaunchingProviders.get(i) == cpr) { 10641 break; 10642 } 10643 } 10644 10645 // If the provider is not already being launched, then get it 10646 // started. 10647 if (i >= N) { 10648 final long origId = Binder.clearCallingIdentity(); 10649 10650 try { 10651 // Content provider is now in use, its package can't be stopped. 10652 try { 10653 checkTime(startTime, "getContentProviderImpl: before set stopped state"); 10654 AppGlobals.getPackageManager().setPackageStoppedState( 10655 cpr.appInfo.packageName, false, userId); 10656 checkTime(startTime, "getContentProviderImpl: after set stopped state"); 10657 } catch (RemoteException e) { 10658 } catch (IllegalArgumentException e) { 10659 Slog.w(TAG, "Failed trying to unstop package " 10660 + cpr.appInfo.packageName + ": " + e); 10661 } 10662 10663 // Use existing process if already started 10664 checkTime(startTime, "getContentProviderImpl: looking for process record"); 10665 ProcessRecord proc = getProcessRecordLocked( 10666 cpi.processName, cpr.appInfo.uid, false); 10667 if (proc != null && proc.thread != null) { 10668 if (DEBUG_PROVIDER) Slog.d(TAG_PROVIDER, 10669 "Installing in existing process " + proc); 10670 if (!proc.pubProviders.containsKey(cpi.name)) { 10671 checkTime(startTime, "getContentProviderImpl: scheduling install"); 10672 proc.pubProviders.put(cpi.name, cpr); 10673 try { 10674 proc.thread.scheduleInstallProvider(cpi); 10675 } catch (RemoteException e) { 10676 } 10677 } 10678 } else { 10679 checkTime(startTime, "getContentProviderImpl: before start process"); 10680 proc = startProcessLocked(cpi.processName, 10681 cpr.appInfo, false, 0, "content provider", 10682 new ComponentName(cpi.applicationInfo.packageName, 10683 cpi.name), false, false, false); 10684 checkTime(startTime, "getContentProviderImpl: after start process"); 10685 if (proc == null) { 10686 Slog.w(TAG, "Unable to launch app " 10687 + cpi.applicationInfo.packageName + "/" 10688 + cpi.applicationInfo.uid + " for provider " 10689 + name + ": process is bad"); 10690 return null; 10691 } 10692 } 10693 cpr.launchingApp = proc; 10694 mLaunchingProviders.add(cpr); 10695 } finally { 10696 Binder.restoreCallingIdentity(origId); 10697 } 10698 } 10699 10700 checkTime(startTime, "getContentProviderImpl: updating data structures"); 10701 10702 // Make sure the provider is published (the same provider class 10703 // may be published under multiple names). 10704 if (firstClass) { 10705 mProviderMap.putProviderByClass(comp, cpr); 10706 } 10707 10708 mProviderMap.putProviderByName(name, cpr); 10709 conn = incProviderCountLocked(r, cpr, token, stable); 10710 if (conn != null) { 10711 conn.waiting = true; 10712 } 10713 } 10714 checkTime(startTime, "getContentProviderImpl: done!"); 10715 } 10716 10717 // Wait for the provider to be published... 10718 synchronized (cpr) { 10719 while (cpr.provider == null) { 10720 if (cpr.launchingApp == null) { 10721 Slog.w(TAG, "Unable to launch app " 10722 + cpi.applicationInfo.packageName + "/" 10723 + cpi.applicationInfo.uid + " for provider " 10724 + name + ": launching app became null"); 10725 EventLog.writeEvent(EventLogTags.AM_PROVIDER_LOST_PROCESS, 10726 UserHandle.getUserId(cpi.applicationInfo.uid), 10727 cpi.applicationInfo.packageName, 10728 cpi.applicationInfo.uid, name); 10729 return null; 10730 } 10731 try { 10732 if (DEBUG_MU) Slog.v(TAG_MU, 10733 "Waiting to start provider " + cpr 10734 + " launchingApp=" + cpr.launchingApp); 10735 if (conn != null) { 10736 conn.waiting = true; 10737 } 10738 cpr.wait(); 10739 } catch (InterruptedException ex) { 10740 } finally { 10741 if (conn != null) { 10742 conn.waiting = false; 10743 } 10744 } 10745 } 10746 } 10747 return cpr != null ? cpr.newHolder(conn) : null; 10748 } 10749 10750 private boolean requestTargetProviderPermissionsReviewIfNeededLocked(ProviderInfo cpi, 10751 ProcessRecord r, final int userId) { 10752 if (getPackageManagerInternalLocked().isPermissionsReviewRequired( 10753 cpi.packageName, userId)) { 10754 10755 final boolean callerForeground = r == null || r.setSchedGroup 10756 != ProcessList.SCHED_GROUP_BACKGROUND; 10757 10758 // Show a permission review UI only for starting from a foreground app 10759 if (!callerForeground) { 10760 Slog.w(TAG, "u" + userId + " Instantiating a provider in package" 10761 + cpi.packageName + " requires a permissions review"); 10762 return false; 10763 } 10764 10765 final Intent intent = new Intent(Intent.ACTION_REVIEW_PERMISSIONS); 10766 intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK 10767 | Intent.FLAG_ACTIVITY_EXCLUDE_FROM_RECENTS); 10768 intent.putExtra(Intent.EXTRA_PACKAGE_NAME, cpi.packageName); 10769 10770 if (DEBUG_PERMISSIONS_REVIEW) { 10771 Slog.i(TAG, "u" + userId + " Launching permission review " 10772 + "for package " + cpi.packageName); 10773 } 10774 10775 final UserHandle userHandle = new UserHandle(userId); 10776 mHandler.post(new Runnable() { 10777 @Override 10778 public void run() { 10779 mContext.startActivityAsUser(intent, userHandle); 10780 } 10781 }); 10782 10783 return false; 10784 } 10785 10786 return true; 10787 } 10788 10789 PackageManagerInternal getPackageManagerInternalLocked() { 10790 if (mPackageManagerInt == null) { 10791 mPackageManagerInt = LocalServices.getService(PackageManagerInternal.class); 10792 } 10793 return mPackageManagerInt; 10794 } 10795 10796 @Override 10797 public final ContentProviderHolder getContentProvider( 10798 IApplicationThread caller, String name, int userId, boolean stable) { 10799 enforceNotIsolatedCaller("getContentProvider"); 10800 if (caller == null) { 10801 String msg = "null IApplicationThread when getting content provider " 10802 + name; 10803 Slog.w(TAG, msg); 10804 throw new SecurityException(msg); 10805 } 10806 // The incoming user check is now handled in checkContentProviderPermissionLocked() to deal 10807 // with cross-user grant. 10808 return getContentProviderImpl(caller, name, null, stable, userId); 10809 } 10810 10811 public ContentProviderHolder getContentProviderExternal( 10812 String name, int userId, IBinder token) { 10813 enforceCallingPermission(android.Manifest.permission.ACCESS_CONTENT_PROVIDERS_EXTERNALLY, 10814 "Do not have permission in call getContentProviderExternal()"); 10815 userId = mUserController.handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 10816 userId, false, ALLOW_FULL_ONLY, "getContentProvider", null); 10817 return getContentProviderExternalUnchecked(name, token, userId); 10818 } 10819 10820 private ContentProviderHolder getContentProviderExternalUnchecked(String name, 10821 IBinder token, int userId) { 10822 return getContentProviderImpl(null, name, token, true, userId); 10823 } 10824 10825 /** 10826 * Drop a content provider from a ProcessRecord's bookkeeping 10827 */ 10828 public void removeContentProvider(IBinder connection, boolean stable) { 10829 enforceNotIsolatedCaller("removeContentProvider"); 10830 long ident = Binder.clearCallingIdentity(); 10831 try { 10832 synchronized (this) { 10833 ContentProviderConnection conn; 10834 try { 10835 conn = (ContentProviderConnection)connection; 10836 } catch (ClassCastException e) { 10837 String msg ="removeContentProvider: " + connection 10838 + " not a ContentProviderConnection"; 10839 Slog.w(TAG, msg); 10840 throw new IllegalArgumentException(msg); 10841 } 10842 if (conn == null) { 10843 throw new NullPointerException("connection is null"); 10844 } 10845 if (decProviderCountLocked(conn, null, null, stable)) { 10846 updateOomAdjLocked(); 10847 } 10848 } 10849 } finally { 10850 Binder.restoreCallingIdentity(ident); 10851 } 10852 } 10853 10854 public void removeContentProviderExternal(String name, IBinder token) { 10855 enforceCallingPermission(android.Manifest.permission.ACCESS_CONTENT_PROVIDERS_EXTERNALLY, 10856 "Do not have permission in call removeContentProviderExternal()"); 10857 int userId = UserHandle.getCallingUserId(); 10858 long ident = Binder.clearCallingIdentity(); 10859 try { 10860 removeContentProviderExternalUnchecked(name, token, userId); 10861 } finally { 10862 Binder.restoreCallingIdentity(ident); 10863 } 10864 } 10865 10866 private void removeContentProviderExternalUnchecked(String name, IBinder token, int userId) { 10867 synchronized (this) { 10868 ContentProviderRecord cpr = mProviderMap.getProviderByName(name, userId); 10869 if(cpr == null) { 10870 //remove from mProvidersByClass 10871 if(DEBUG_ALL) Slog.v(TAG, name+" content provider not found in providers list"); 10872 return; 10873 } 10874 10875 //update content provider record entry info 10876 ComponentName comp = new ComponentName(cpr.info.packageName, cpr.info.name); 10877 ContentProviderRecord localCpr = mProviderMap.getProviderByClass(comp, userId); 10878 if (localCpr.hasExternalProcessHandles()) { 10879 if (localCpr.removeExternalProcessHandleLocked(token)) { 10880 updateOomAdjLocked(); 10881 } else { 10882 Slog.e(TAG, "Attmpt to remove content provider " + localCpr 10883 + " with no external reference for token: " 10884 + token + "."); 10885 } 10886 } else { 10887 Slog.e(TAG, "Attmpt to remove content provider: " + localCpr 10888 + " with no external references."); 10889 } 10890 } 10891 } 10892 10893 public final void publishContentProviders(IApplicationThread caller, 10894 List<ContentProviderHolder> providers) { 10895 if (providers == null) { 10896 return; 10897 } 10898 10899 enforceNotIsolatedCaller("publishContentProviders"); 10900 synchronized (this) { 10901 final ProcessRecord r = getRecordForAppLocked(caller); 10902 if (DEBUG_MU) Slog.v(TAG_MU, "ProcessRecord uid = " + r.uid); 10903 if (r == null) { 10904 throw new SecurityException( 10905 "Unable to find app for caller " + caller 10906 + " (pid=" + Binder.getCallingPid() 10907 + ") when publishing content providers"); 10908 } 10909 10910 final long origId = Binder.clearCallingIdentity(); 10911 10912 final int N = providers.size(); 10913 for (int i = 0; i < N; i++) { 10914 ContentProviderHolder src = providers.get(i); 10915 if (src == null || src.info == null || src.provider == null) { 10916 continue; 10917 } 10918 ContentProviderRecord dst = r.pubProviders.get(src.info.name); 10919 if (DEBUG_MU) Slog.v(TAG_MU, "ContentProviderRecord uid = " + dst.uid); 10920 if (dst != null) { 10921 ComponentName comp = new ComponentName(dst.info.packageName, dst.info.name); 10922 mProviderMap.putProviderByClass(comp, dst); 10923 String names[] = dst.info.authority.split(";"); 10924 for (int j = 0; j < names.length; j++) { 10925 mProviderMap.putProviderByName(names[j], dst); 10926 } 10927 10928 int launchingCount = mLaunchingProviders.size(); 10929 int j; 10930 boolean wasInLaunchingProviders = false; 10931 for (j = 0; j < launchingCount; j++) { 10932 if (mLaunchingProviders.get(j) == dst) { 10933 mLaunchingProviders.remove(j); 10934 wasInLaunchingProviders = true; 10935 j--; 10936 launchingCount--; 10937 } 10938 } 10939 if (wasInLaunchingProviders) { 10940 mHandler.removeMessages(CONTENT_PROVIDER_PUBLISH_TIMEOUT_MSG, r); 10941 } 10942 synchronized (dst) { 10943 dst.provider = src.provider; 10944 dst.proc = r; 10945 dst.notifyAll(); 10946 } 10947 updateOomAdjLocked(r); 10948 maybeUpdateProviderUsageStatsLocked(r, src.info.packageName, 10949 src.info.authority); 10950 } 10951 } 10952 10953 Binder.restoreCallingIdentity(origId); 10954 } 10955 } 10956 10957 public boolean refContentProvider(IBinder connection, int stable, int unstable) { 10958 ContentProviderConnection conn; 10959 try { 10960 conn = (ContentProviderConnection)connection; 10961 } catch (ClassCastException e) { 10962 String msg ="refContentProvider: " + connection 10963 + " not a ContentProviderConnection"; 10964 Slog.w(TAG, msg); 10965 throw new IllegalArgumentException(msg); 10966 } 10967 if (conn == null) { 10968 throw new NullPointerException("connection is null"); 10969 } 10970 10971 synchronized (this) { 10972 if (stable > 0) { 10973 conn.numStableIncs += stable; 10974 } 10975 stable = conn.stableCount + stable; 10976 if (stable < 0) { 10977 throw new IllegalStateException("stableCount < 0: " + stable); 10978 } 10979 10980 if (unstable > 0) { 10981 conn.numUnstableIncs += unstable; 10982 } 10983 unstable = conn.unstableCount + unstable; 10984 if (unstable < 0) { 10985 throw new IllegalStateException("unstableCount < 0: " + unstable); 10986 } 10987 10988 if ((stable+unstable) <= 0) { 10989 throw new IllegalStateException("ref counts can't go to zero here: stable=" 10990 + stable + " unstable=" + unstable); 10991 } 10992 conn.stableCount = stable; 10993 conn.unstableCount = unstable; 10994 return !conn.dead; 10995 } 10996 } 10997 10998 public void unstableProviderDied(IBinder connection) { 10999 ContentProviderConnection conn; 11000 try { 11001 conn = (ContentProviderConnection)connection; 11002 } catch (ClassCastException e) { 11003 String msg ="refContentProvider: " + connection 11004 + " not a ContentProviderConnection"; 11005 Slog.w(TAG, msg); 11006 throw new IllegalArgumentException(msg); 11007 } 11008 if (conn == null) { 11009 throw new NullPointerException("connection is null"); 11010 } 11011 11012 // Safely retrieve the content provider associated with the connection. 11013 IContentProvider provider; 11014 synchronized (this) { 11015 provider = conn.provider.provider; 11016 } 11017 11018 if (provider == null) { 11019 // Um, yeah, we're way ahead of you. 11020 return; 11021 } 11022 11023 // Make sure the caller is being honest with us. 11024 if (provider.asBinder().pingBinder()) { 11025 // Er, no, still looks good to us. 11026 synchronized (this) { 11027 Slog.w(TAG, "unstableProviderDied: caller " + Binder.getCallingUid() 11028 + " says " + conn + " died, but we don't agree"); 11029 return; 11030 } 11031 } 11032 11033 // Well look at that! It's dead! 11034 synchronized (this) { 11035 if (conn.provider.provider != provider) { 11036 // But something changed... good enough. 11037 return; 11038 } 11039 11040 ProcessRecord proc = conn.provider.proc; 11041 if (proc == null || proc.thread == null) { 11042 // Seems like the process is already cleaned up. 11043 return; 11044 } 11045 11046 // As far as we're concerned, this is just like receiving a 11047 // death notification... just a bit prematurely. 11048 Slog.i(TAG, "Process " + proc.processName + " (pid " + proc.pid 11049 + ") early provider death"); 11050 final long ident = Binder.clearCallingIdentity(); 11051 try { 11052 appDiedLocked(proc); 11053 } finally { 11054 Binder.restoreCallingIdentity(ident); 11055 } 11056 } 11057 } 11058 11059 @Override 11060 public void appNotRespondingViaProvider(IBinder connection) { 11061 enforceCallingPermission( 11062 android.Manifest.permission.REMOVE_TASKS, "appNotRespondingViaProvider()"); 11063 11064 final ContentProviderConnection conn = (ContentProviderConnection) connection; 11065 if (conn == null) { 11066 Slog.w(TAG, "ContentProviderConnection is null"); 11067 return; 11068 } 11069 11070 final ProcessRecord host = conn.provider.proc; 11071 if (host == null) { 11072 Slog.w(TAG, "Failed to find hosting ProcessRecord"); 11073 return; 11074 } 11075 11076 mHandler.post(new Runnable() { 11077 @Override 11078 public void run() { 11079 mAppErrors.appNotResponding(host, null, null, false, 11080 "ContentProvider not responding"); 11081 } 11082 }); 11083 } 11084 11085 public final void installSystemProviders() { 11086 List<ProviderInfo> providers; 11087 synchronized (this) { 11088 ProcessRecord app = mProcessNames.get("system", Process.SYSTEM_UID); 11089 providers = generateApplicationProvidersLocked(app); 11090 if (providers != null) { 11091 for (int i=providers.size()-1; i>=0; i--) { 11092 ProviderInfo pi = (ProviderInfo)providers.get(i); 11093 if ((pi.applicationInfo.flags&ApplicationInfo.FLAG_SYSTEM) == 0) { 11094 Slog.w(TAG, "Not installing system proc provider " + pi.name 11095 + ": not system .apk"); 11096 providers.remove(i); 11097 } 11098 } 11099 } 11100 } 11101 if (providers != null) { 11102 mSystemThread.installSystemProviders(providers); 11103 } 11104 11105 mCoreSettingsObserver = new CoreSettingsObserver(this); 11106 mFontScaleSettingObserver = new FontScaleSettingObserver(); 11107 11108 //mUsageStatsService.monitorPackages(); 11109 } 11110 11111 private void startPersistentApps(int matchFlags) { 11112 if (mFactoryTest == FactoryTest.FACTORY_TEST_LOW_LEVEL) return; 11113 11114 synchronized (this) { 11115 try { 11116 final List<ApplicationInfo> apps = AppGlobals.getPackageManager() 11117 .getPersistentApplications(STOCK_PM_FLAGS | matchFlags).getList(); 11118 for (ApplicationInfo app : apps) { 11119 if (!"android".equals(app.packageName)) { 11120 addAppLocked(app, false, null /* ABI override */); 11121 } 11122 } 11123 } catch (RemoteException ex) { 11124 } 11125 } 11126 } 11127 11128 /** 11129 * When a user is unlocked, we need to install encryption-unaware providers 11130 * belonging to any running apps. 11131 */ 11132 private void installEncryptionUnawareProviders(int userId) { 11133 // We're only interested in providers that are encryption unaware, and 11134 // we don't care about uninstalled apps, since there's no way they're 11135 // running at this point. 11136 final int matchFlags = GET_PROVIDERS | MATCH_DIRECT_BOOT_UNAWARE; 11137 11138 synchronized (this) { 11139 final int NP = mProcessNames.getMap().size(); 11140 for (int ip = 0; ip < NP; ip++) { 11141 final SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 11142 final int NA = apps.size(); 11143 for (int ia = 0; ia < NA; ia++) { 11144 final ProcessRecord app = apps.valueAt(ia); 11145 if (app.userId != userId || app.thread == null || app.unlocked) continue; 11146 11147 final int NG = app.pkgList.size(); 11148 for (int ig = 0; ig < NG; ig++) { 11149 try { 11150 final String pkgName = app.pkgList.keyAt(ig); 11151 final PackageInfo pkgInfo = AppGlobals.getPackageManager() 11152 .getPackageInfo(pkgName, matchFlags, userId); 11153 if (pkgInfo != null && !ArrayUtils.isEmpty(pkgInfo.providers)) { 11154 for (ProviderInfo pi : pkgInfo.providers) { 11155 // TODO: keep in sync with generateApplicationProvidersLocked 11156 final boolean processMatch = Objects.equals(pi.processName, 11157 app.processName) || pi.multiprocess; 11158 final boolean userMatch = isSingleton(pi.processName, 11159 pi.applicationInfo, pi.name, pi.flags) 11160 ? (app.userId == UserHandle.USER_SYSTEM) : true; 11161 if (processMatch && userMatch) { 11162 Log.v(TAG, "Installing " + pi); 11163 app.thread.scheduleInstallProvider(pi); 11164 } else { 11165 Log.v(TAG, "Skipping " + pi); 11166 } 11167 } 11168 } 11169 } catch (RemoteException ignored) { 11170 } 11171 } 11172 } 11173 } 11174 } 11175 } 11176 11177 /** 11178 * Allows apps to retrieve the MIME type of a URI. 11179 * If an app is in the same user as the ContentProvider, or if it is allowed to interact across 11180 * users, then it does not need permission to access the ContentProvider. 11181 * Either, it needs cross-user uri grants. 11182 * 11183 * CTS tests for this functionality can be run with "runtest cts-appsecurity". 11184 * 11185 * Test cases are at cts/tests/appsecurity-tests/test-apps/UsePermissionDiffCert/ 11186 * src/com/android/cts/usespermissiondiffcertapp/AccessPermissionWithDiffSigTest.java 11187 */ 11188 public String getProviderMimeType(Uri uri, int userId) { 11189 enforceNotIsolatedCaller("getProviderMimeType"); 11190 final String name = uri.getAuthority(); 11191 int callingUid = Binder.getCallingUid(); 11192 int callingPid = Binder.getCallingPid(); 11193 long ident = 0; 11194 boolean clearedIdentity = false; 11195 synchronized (this) { 11196 userId = mUserController.unsafeConvertIncomingUserLocked(userId); 11197 } 11198 if (canClearIdentity(callingPid, callingUid, userId)) { 11199 clearedIdentity = true; 11200 ident = Binder.clearCallingIdentity(); 11201 } 11202 ContentProviderHolder holder = null; 11203 try { 11204 holder = getContentProviderExternalUnchecked(name, null, userId); 11205 if (holder != null) { 11206 return holder.provider.getType(uri); 11207 } 11208 } catch (RemoteException e) { 11209 Log.w(TAG, "Content provider dead retrieving " + uri, e); 11210 return null; 11211 } finally { 11212 // We need to clear the identity to call removeContentProviderExternalUnchecked 11213 if (!clearedIdentity) { 11214 ident = Binder.clearCallingIdentity(); 11215 } 11216 try { 11217 if (holder != null) { 11218 removeContentProviderExternalUnchecked(name, null, userId); 11219 } 11220 } finally { 11221 Binder.restoreCallingIdentity(ident); 11222 } 11223 } 11224 11225 return null; 11226 } 11227 11228 private boolean canClearIdentity(int callingPid, int callingUid, int userId) { 11229 if (UserHandle.getUserId(callingUid) == userId) { 11230 return true; 11231 } 11232 if (checkComponentPermission(INTERACT_ACROSS_USERS, callingPid, 11233 callingUid, -1, true) == PackageManager.PERMISSION_GRANTED 11234 || checkComponentPermission(INTERACT_ACROSS_USERS_FULL, callingPid, 11235 callingUid, -1, true) == PackageManager.PERMISSION_GRANTED) { 11236 return true; 11237 } 11238 return false; 11239 } 11240 11241 // ========================================================= 11242 // GLOBAL MANAGEMENT 11243 // ========================================================= 11244 11245 final ProcessRecord newProcessRecordLocked(ApplicationInfo info, String customProcess, 11246 boolean isolated, int isolatedUid) { 11247 String proc = customProcess != null ? customProcess : info.processName; 11248 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 11249 final int userId = UserHandle.getUserId(info.uid); 11250 int uid = info.uid; 11251 if (isolated) { 11252 if (isolatedUid == 0) { 11253 int stepsLeft = Process.LAST_ISOLATED_UID - Process.FIRST_ISOLATED_UID + 1; 11254 while (true) { 11255 if (mNextIsolatedProcessUid < Process.FIRST_ISOLATED_UID 11256 || mNextIsolatedProcessUid > Process.LAST_ISOLATED_UID) { 11257 mNextIsolatedProcessUid = Process.FIRST_ISOLATED_UID; 11258 } 11259 uid = UserHandle.getUid(userId, mNextIsolatedProcessUid); 11260 mNextIsolatedProcessUid++; 11261 if (mIsolatedProcesses.indexOfKey(uid) < 0) { 11262 // No process for this uid, use it. 11263 break; 11264 } 11265 stepsLeft--; 11266 if (stepsLeft <= 0) { 11267 return null; 11268 } 11269 } 11270 } else { 11271 // Special case for startIsolatedProcess (internal only), where 11272 // the uid of the isolated process is specified by the caller. 11273 uid = isolatedUid; 11274 } 11275 } 11276 final ProcessRecord r = new ProcessRecord(stats, info, proc, uid); 11277 if (!mBooted && !mBooting 11278 && userId == UserHandle.USER_SYSTEM 11279 && (info.flags & PERSISTENT_MASK) == PERSISTENT_MASK) { 11280 r.persistent = true; 11281 } 11282 addProcessNameLocked(r); 11283 return r; 11284 } 11285 11286 final ProcessRecord addAppLocked(ApplicationInfo info, boolean isolated, 11287 String abiOverride) { 11288 ProcessRecord app; 11289 if (!isolated) { 11290 app = getProcessRecordLocked(info.processName, info.uid, true); 11291 } else { 11292 app = null; 11293 } 11294 11295 if (app == null) { 11296 app = newProcessRecordLocked(info, null, isolated, 0); 11297 updateLruProcessLocked(app, false, null); 11298 updateOomAdjLocked(); 11299 } 11300 11301 // This package really, really can not be stopped. 11302 try { 11303 AppGlobals.getPackageManager().setPackageStoppedState( 11304 info.packageName, false, UserHandle.getUserId(app.uid)); 11305 } catch (RemoteException e) { 11306 } catch (IllegalArgumentException e) { 11307 Slog.w(TAG, "Failed trying to unstop package " 11308 + info.packageName + ": " + e); 11309 } 11310 11311 if ((info.flags & PERSISTENT_MASK) == PERSISTENT_MASK) { 11312 app.persistent = true; 11313 app.maxAdj = ProcessList.PERSISTENT_PROC_ADJ; 11314 } 11315 if (app.thread == null && mPersistentStartingProcesses.indexOf(app) < 0) { 11316 mPersistentStartingProcesses.add(app); 11317 startProcessLocked(app, "added application", app.processName, abiOverride, 11318 null /* entryPoint */, null /* entryPointArgs */); 11319 } 11320 11321 return app; 11322 } 11323 11324 public void unhandledBack() { 11325 enforceCallingPermission(android.Manifest.permission.FORCE_BACK, 11326 "unhandledBack()"); 11327 11328 synchronized(this) { 11329 final long origId = Binder.clearCallingIdentity(); 11330 try { 11331 getFocusedStack().unhandledBackLocked(); 11332 } finally { 11333 Binder.restoreCallingIdentity(origId); 11334 } 11335 } 11336 } 11337 11338 public ParcelFileDescriptor openContentUri(Uri uri) throws RemoteException { 11339 enforceNotIsolatedCaller("openContentUri"); 11340 final int userId = UserHandle.getCallingUserId(); 11341 String name = uri.getAuthority(); 11342 ContentProviderHolder cph = getContentProviderExternalUnchecked(name, null, userId); 11343 ParcelFileDescriptor pfd = null; 11344 if (cph != null) { 11345 // We record the binder invoker's uid in thread-local storage before 11346 // going to the content provider to open the file. Later, in the code 11347 // that handles all permissions checks, we look for this uid and use 11348 // that rather than the Activity Manager's own uid. The effect is that 11349 // we do the check against the caller's permissions even though it looks 11350 // to the content provider like the Activity Manager itself is making 11351 // the request. 11352 Binder token = new Binder(); 11353 sCallerIdentity.set(new Identity( 11354 token, Binder.getCallingPid(), Binder.getCallingUid())); 11355 try { 11356 pfd = cph.provider.openFile(null, uri, "r", null, token); 11357 } catch (FileNotFoundException e) { 11358 // do nothing; pfd will be returned null 11359 } finally { 11360 // Ensure that whatever happens, we clean up the identity state 11361 sCallerIdentity.remove(); 11362 // Ensure we're done with the provider. 11363 removeContentProviderExternalUnchecked(name, null, userId); 11364 } 11365 } else { 11366 Slog.d(TAG, "Failed to get provider for authority '" + name + "'"); 11367 } 11368 return pfd; 11369 } 11370 11371 // Actually is sleeping or shutting down or whatever else in the future 11372 // is an inactive state. 11373 public boolean isSleepingOrShuttingDown() { 11374 return isSleeping() || mShuttingDown; 11375 } 11376 11377 public boolean isSleeping() { 11378 return mSleeping; 11379 } 11380 11381 void onWakefulnessChanged(int wakefulness) { 11382 synchronized(this) { 11383 mWakefulness = wakefulness; 11384 updateSleepIfNeededLocked(); 11385 } 11386 } 11387 11388 void finishRunningVoiceLocked() { 11389 if (mRunningVoice != null) { 11390 mRunningVoice = null; 11391 mVoiceWakeLock.release(); 11392 updateSleepIfNeededLocked(); 11393 } 11394 } 11395 11396 void startTimeTrackingFocusedActivityLocked() { 11397 if (!mSleeping && mCurAppTimeTracker != null && mFocusedActivity != null) { 11398 mCurAppTimeTracker.start(mFocusedActivity.packageName); 11399 } 11400 } 11401 11402 void updateSleepIfNeededLocked() { 11403 if (mSleeping && !shouldSleepLocked()) { 11404 mSleeping = false; 11405 startTimeTrackingFocusedActivityLocked(); 11406 mTopProcessState = ActivityManager.PROCESS_STATE_TOP; 11407 mStackSupervisor.comeOutOfSleepIfNeededLocked(); 11408 updateOomAdjLocked(); 11409 } else if (!mSleeping && shouldSleepLocked()) { 11410 mSleeping = true; 11411 if (mCurAppTimeTracker != null) { 11412 mCurAppTimeTracker.stop(); 11413 } 11414 mTopProcessState = ActivityManager.PROCESS_STATE_TOP_SLEEPING; 11415 mStackSupervisor.goingToSleepLocked(); 11416 updateOomAdjLocked(); 11417 11418 // Initialize the wake times of all processes. 11419 checkExcessivePowerUsageLocked(false); 11420 mHandler.removeMessages(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 11421 Message nmsg = mHandler.obtainMessage(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 11422 mHandler.sendMessageDelayed(nmsg, POWER_CHECK_DELAY); 11423 } 11424 } 11425 11426 private boolean shouldSleepLocked() { 11427 // Resume applications while running a voice interactor. 11428 if (mRunningVoice != null) { 11429 return false; 11430 } 11431 11432 // TODO: Transform the lock screen state into a sleep token instead. 11433 switch (mWakefulness) { 11434 case PowerManagerInternal.WAKEFULNESS_AWAKE: 11435 case PowerManagerInternal.WAKEFULNESS_DREAMING: 11436 case PowerManagerInternal.WAKEFULNESS_DOZING: 11437 // Pause applications whenever the lock screen is shown or any sleep 11438 // tokens have been acquired. 11439 return (mLockScreenShown != LOCK_SCREEN_HIDDEN || !mSleepTokens.isEmpty()); 11440 case PowerManagerInternal.WAKEFULNESS_ASLEEP: 11441 default: 11442 // If we're asleep then pause applications unconditionally. 11443 return true; 11444 } 11445 } 11446 11447 /** Pokes the task persister. */ 11448 void notifyTaskPersisterLocked(TaskRecord task, boolean flush) { 11449 mRecentTasks.notifyTaskPersisterLocked(task, flush); 11450 } 11451 11452 /** Notifies all listeners when the task stack has changed. */ 11453 void notifyTaskStackChangedLocked() { 11454 mHandler.sendEmptyMessage(LOG_STACK_STATE); 11455 mHandler.removeMessages(NOTIFY_TASK_STACK_CHANGE_LISTENERS_MSG); 11456 Message nmsg = mHandler.obtainMessage(NOTIFY_TASK_STACK_CHANGE_LISTENERS_MSG); 11457 mHandler.sendMessageDelayed(nmsg, NOTIFY_TASK_STACK_CHANGE_LISTENERS_DELAY); 11458 } 11459 11460 /** Notifies all listeners when an Activity is pinned. */ 11461 void notifyActivityPinnedLocked() { 11462 mHandler.removeMessages(NOTIFY_ACTIVITY_PINNED_LISTENERS_MSG); 11463 mHandler.obtainMessage(NOTIFY_ACTIVITY_PINNED_LISTENERS_MSG).sendToTarget(); 11464 } 11465 11466 /** 11467 * Notifies all listeners when an attempt was made to start an an activity that is already 11468 * running in the pinned stack and the activity was not actually started, but the task is 11469 * either brought to the front or a new Intent is delivered to it. 11470 */ 11471 void notifyPinnedActivityRestartAttemptLocked() { 11472 mHandler.removeMessages(NOTIFY_PINNED_ACTIVITY_RESTART_ATTEMPT_LISTENERS_MSG); 11473 mHandler.obtainMessage(NOTIFY_PINNED_ACTIVITY_RESTART_ATTEMPT_LISTENERS_MSG).sendToTarget(); 11474 } 11475 11476 /** Notifies all listeners when the pinned stack animation ends. */ 11477 @Override 11478 public void notifyPinnedStackAnimationEnded() { 11479 synchronized (this) { 11480 mHandler.removeMessages(NOTIFY_PINNED_STACK_ANIMATION_ENDED_LISTENERS_MSG); 11481 mHandler.obtainMessage( 11482 NOTIFY_PINNED_STACK_ANIMATION_ENDED_LISTENERS_MSG).sendToTarget(); 11483 } 11484 } 11485 11486 @Override 11487 public void notifyCleartextNetwork(int uid, byte[] firstPacket) { 11488 mHandler.obtainMessage(NOTIFY_CLEARTEXT_NETWORK_MSG, uid, 0, firstPacket).sendToTarget(); 11489 } 11490 11491 @Override 11492 public boolean shutdown(int timeout) { 11493 if (checkCallingPermission(android.Manifest.permission.SHUTDOWN) 11494 != PackageManager.PERMISSION_GRANTED) { 11495 throw new SecurityException("Requires permission " 11496 + android.Manifest.permission.SHUTDOWN); 11497 } 11498 11499 boolean timedout = false; 11500 11501 synchronized(this) { 11502 mShuttingDown = true; 11503 updateEventDispatchingLocked(); 11504 timedout = mStackSupervisor.shutdownLocked(timeout); 11505 } 11506 11507 mAppOpsService.shutdown(); 11508 if (mUsageStatsService != null) { 11509 mUsageStatsService.prepareShutdown(); 11510 } 11511 mBatteryStatsService.shutdown(); 11512 synchronized (this) { 11513 mProcessStats.shutdownLocked(); 11514 notifyTaskPersisterLocked(null, true); 11515 } 11516 11517 return timedout; 11518 } 11519 11520 public final void activitySlept(IBinder token) { 11521 if (DEBUG_ALL) Slog.v(TAG, "Activity slept: token=" + token); 11522 11523 final long origId = Binder.clearCallingIdentity(); 11524 11525 synchronized (this) { 11526 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 11527 if (r != null) { 11528 mStackSupervisor.activitySleptLocked(r); 11529 } 11530 } 11531 11532 Binder.restoreCallingIdentity(origId); 11533 } 11534 11535 private String lockScreenShownToString() { 11536 switch (mLockScreenShown) { 11537 case LOCK_SCREEN_HIDDEN: return "LOCK_SCREEN_HIDDEN"; 11538 case LOCK_SCREEN_LEAVING: return "LOCK_SCREEN_LEAVING"; 11539 case LOCK_SCREEN_SHOWN: return "LOCK_SCREEN_SHOWN"; 11540 default: return "Unknown=" + mLockScreenShown; 11541 } 11542 } 11543 11544 void logLockScreen(String msg) { 11545 if (DEBUG_LOCKSCREEN) Slog.d(TAG_LOCKSCREEN, Debug.getCallers(2) + ":" + msg 11546 + " mLockScreenShown=" + lockScreenShownToString() + " mWakefulness=" 11547 + PowerManagerInternal.wakefulnessToString(mWakefulness) 11548 + " mSleeping=" + mSleeping); 11549 } 11550 11551 void startRunningVoiceLocked(IVoiceInteractionSession session, int targetUid) { 11552 Slog.d(TAG, "<<< startRunningVoiceLocked()"); 11553 mVoiceWakeLock.setWorkSource(new WorkSource(targetUid)); 11554 if (mRunningVoice == null || mRunningVoice.asBinder() != session.asBinder()) { 11555 boolean wasRunningVoice = mRunningVoice != null; 11556 mRunningVoice = session; 11557 if (!wasRunningVoice) { 11558 mVoiceWakeLock.acquire(); 11559 updateSleepIfNeededLocked(); 11560 } 11561 } 11562 } 11563 11564 private void updateEventDispatchingLocked() { 11565 mWindowManager.setEventDispatching(mBooted && !mShuttingDown); 11566 } 11567 11568 public void setLockScreenShown(boolean showing, boolean occluded) { 11569 if (checkCallingPermission(android.Manifest.permission.DEVICE_POWER) 11570 != PackageManager.PERMISSION_GRANTED) { 11571 throw new SecurityException("Requires permission " 11572 + android.Manifest.permission.DEVICE_POWER); 11573 } 11574 11575 synchronized(this) { 11576 long ident = Binder.clearCallingIdentity(); 11577 try { 11578 if (DEBUG_LOCKSCREEN) logLockScreen(" showing=" + showing + " occluded=" + occluded); 11579 mLockScreenShown = (showing && !occluded) ? LOCK_SCREEN_SHOWN : LOCK_SCREEN_HIDDEN; 11580 if (showing && occluded) { 11581 // The lock screen is currently showing, but is occluded by a window that can 11582 // show on top of the lock screen. In this can we want to dismiss the docked 11583 // stack since it will be complicated/risky to try to put the activity on top 11584 // of the lock screen in the right fullscreen configuration. 11585 mStackSupervisor.moveTasksToFullscreenStackLocked(DOCKED_STACK_ID, 11586 mStackSupervisor.mFocusedStack.getStackId() == DOCKED_STACK_ID); 11587 } 11588 11589 updateSleepIfNeededLocked(); 11590 } finally { 11591 Binder.restoreCallingIdentity(ident); 11592 } 11593 } 11594 } 11595 11596 @Override 11597 public void notifyLockedProfile(@UserIdInt int userId) { 11598 try { 11599 if (!AppGlobals.getPackageManager().isUidPrivileged(Binder.getCallingUid())) { 11600 throw new SecurityException("Only privileged app can call notifyLockedProfile"); 11601 } 11602 } catch (RemoteException ex) { 11603 throw new SecurityException("Fail to check is caller a privileged app", ex); 11604 } 11605 11606 synchronized (this) { 11607 if (mStackSupervisor.isUserLockedProfile(userId)) { 11608 final long ident = Binder.clearCallingIdentity(); 11609 try { 11610 final int currentUserId = mUserController.getCurrentUserIdLocked(); 11611 if (mUserController.isLockScreenDisabled(currentUserId)) { 11612 // If there is no device lock, we will show the profile's credential page. 11613 mActivityStarter.showConfirmDeviceCredential(userId); 11614 } else { 11615 // Showing launcher to avoid user entering credential twice. 11616 startHomeActivityLocked(currentUserId, "notifyLockedProfile"); 11617 } 11618 } finally { 11619 Binder.restoreCallingIdentity(ident); 11620 } 11621 } 11622 } 11623 } 11624 11625 @Override 11626 public void startConfirmDeviceCredentialIntent(Intent intent) { 11627 enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "startConfirmDeviceCredentialIntent"); 11628 synchronized (this) { 11629 final long ident = Binder.clearCallingIdentity(); 11630 try { 11631 mActivityStarter.startConfirmCredentialIntent(intent); 11632 } finally { 11633 Binder.restoreCallingIdentity(ident); 11634 } 11635 } 11636 } 11637 11638 @Override 11639 public void stopAppSwitches() { 11640 if (checkCallingPermission(android.Manifest.permission.STOP_APP_SWITCHES) 11641 != PackageManager.PERMISSION_GRANTED) { 11642 throw new SecurityException("viewquires permission " 11643 + android.Manifest.permission.STOP_APP_SWITCHES); 11644 } 11645 11646 synchronized(this) { 11647 mAppSwitchesAllowedTime = SystemClock.uptimeMillis() 11648 + APP_SWITCH_DELAY_TIME; 11649 mDidAppSwitch = false; 11650 mHandler.removeMessages(DO_PENDING_ACTIVITY_LAUNCHES_MSG); 11651 Message msg = mHandler.obtainMessage(DO_PENDING_ACTIVITY_LAUNCHES_MSG); 11652 mHandler.sendMessageDelayed(msg, APP_SWITCH_DELAY_TIME); 11653 } 11654 } 11655 11656 public void resumeAppSwitches() { 11657 if (checkCallingPermission(android.Manifest.permission.STOP_APP_SWITCHES) 11658 != PackageManager.PERMISSION_GRANTED) { 11659 throw new SecurityException("Requires permission " 11660 + android.Manifest.permission.STOP_APP_SWITCHES); 11661 } 11662 11663 synchronized(this) { 11664 // Note that we don't execute any pending app switches... we will 11665 // let those wait until either the timeout, or the next start 11666 // activity request. 11667 mAppSwitchesAllowedTime = 0; 11668 } 11669 } 11670 11671 boolean checkAppSwitchAllowedLocked(int sourcePid, int sourceUid, 11672 int callingPid, int callingUid, String name) { 11673 if (mAppSwitchesAllowedTime < SystemClock.uptimeMillis()) { 11674 return true; 11675 } 11676 11677 int perm = checkComponentPermission( 11678 android.Manifest.permission.STOP_APP_SWITCHES, sourcePid, 11679 sourceUid, -1, true); 11680 if (perm == PackageManager.PERMISSION_GRANTED) { 11681 return true; 11682 } 11683 11684 // If the actual IPC caller is different from the logical source, then 11685 // also see if they are allowed to control app switches. 11686 if (callingUid != -1 && callingUid != sourceUid) { 11687 perm = checkComponentPermission( 11688 android.Manifest.permission.STOP_APP_SWITCHES, callingPid, 11689 callingUid, -1, true); 11690 if (perm == PackageManager.PERMISSION_GRANTED) { 11691 return true; 11692 } 11693 } 11694 11695 Slog.w(TAG, name + " request from " + sourceUid + " stopped"); 11696 return false; 11697 } 11698 11699 public void setDebugApp(String packageName, boolean waitForDebugger, 11700 boolean persistent) { 11701 enforceCallingPermission(android.Manifest.permission.SET_DEBUG_APP, 11702 "setDebugApp()"); 11703 11704 long ident = Binder.clearCallingIdentity(); 11705 try { 11706 // Note that this is not really thread safe if there are multiple 11707 // callers into it at the same time, but that's not a situation we 11708 // care about. 11709 if (persistent) { 11710 final ContentResolver resolver = mContext.getContentResolver(); 11711 Settings.Global.putString( 11712 resolver, Settings.Global.DEBUG_APP, 11713 packageName); 11714 Settings.Global.putInt( 11715 resolver, Settings.Global.WAIT_FOR_DEBUGGER, 11716 waitForDebugger ? 1 : 0); 11717 } 11718 11719 synchronized (this) { 11720 if (!persistent) { 11721 mOrigDebugApp = mDebugApp; 11722 mOrigWaitForDebugger = mWaitForDebugger; 11723 } 11724 mDebugApp = packageName; 11725 mWaitForDebugger = waitForDebugger; 11726 mDebugTransient = !persistent; 11727 if (packageName != null) { 11728 forceStopPackageLocked(packageName, -1, false, false, true, true, 11729 false, UserHandle.USER_ALL, "set debug app"); 11730 } 11731 } 11732 } finally { 11733 Binder.restoreCallingIdentity(ident); 11734 } 11735 } 11736 11737 void setTrackAllocationApp(ApplicationInfo app, String processName) { 11738 synchronized (this) { 11739 boolean isDebuggable = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 11740 if (!isDebuggable) { 11741 if ((app.flags & ApplicationInfo.FLAG_DEBUGGABLE) == 0) { 11742 throw new SecurityException("Process not debuggable: " + app.packageName); 11743 } 11744 } 11745 11746 mTrackAllocationApp = processName; 11747 } 11748 } 11749 11750 void setProfileApp(ApplicationInfo app, String processName, ProfilerInfo profilerInfo) { 11751 synchronized (this) { 11752 boolean isDebuggable = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 11753 if (!isDebuggable) { 11754 if ((app.flags & ApplicationInfo.FLAG_DEBUGGABLE) == 0) { 11755 throw new SecurityException("Process not debuggable: " + app.packageName); 11756 } 11757 } 11758 mProfileApp = processName; 11759 mProfileFile = profilerInfo.profileFile; 11760 if (mProfileFd != null) { 11761 try { 11762 mProfileFd.close(); 11763 } catch (IOException e) { 11764 } 11765 mProfileFd = null; 11766 } 11767 mProfileFd = profilerInfo.profileFd; 11768 mSamplingInterval = profilerInfo.samplingInterval; 11769 mAutoStopProfiler = profilerInfo.autoStopProfiler; 11770 mProfileType = 0; 11771 } 11772 } 11773 11774 void setNativeDebuggingAppLocked(ApplicationInfo app, String processName) { 11775 boolean isDebuggable = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 11776 if (!isDebuggable) { 11777 if ((app.flags & ApplicationInfo.FLAG_DEBUGGABLE) == 0) { 11778 throw new SecurityException("Process not debuggable: " + app.packageName); 11779 } 11780 } 11781 mNativeDebuggingApp = processName; 11782 } 11783 11784 @Override 11785 public void setAlwaysFinish(boolean enabled) { 11786 enforceCallingPermission(android.Manifest.permission.SET_ALWAYS_FINISH, 11787 "setAlwaysFinish()"); 11788 11789 long ident = Binder.clearCallingIdentity(); 11790 try { 11791 Settings.Global.putInt( 11792 mContext.getContentResolver(), 11793 Settings.Global.ALWAYS_FINISH_ACTIVITIES, enabled ? 1 : 0); 11794 11795 synchronized (this) { 11796 mAlwaysFinishActivities = enabled; 11797 } 11798 } finally { 11799 Binder.restoreCallingIdentity(ident); 11800 } 11801 } 11802 11803 @Override 11804 public void setLenientBackgroundCheck(boolean enabled) { 11805 enforceCallingPermission(android.Manifest.permission.SET_PROCESS_LIMIT, 11806 "setLenientBackgroundCheck()"); 11807 11808 long ident = Binder.clearCallingIdentity(); 11809 try { 11810 Settings.Global.putInt( 11811 mContext.getContentResolver(), 11812 Settings.Global.LENIENT_BACKGROUND_CHECK, enabled ? 1 : 0); 11813 11814 synchronized (this) { 11815 mLenientBackgroundCheck = enabled; 11816 } 11817 } finally { 11818 Binder.restoreCallingIdentity(ident); 11819 } 11820 } 11821 11822 @Override 11823 public void setActivityController(IActivityController controller, boolean imAMonkey) { 11824 enforceCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER, 11825 "setActivityController()"); 11826 synchronized (this) { 11827 mController = controller; 11828 mControllerIsAMonkey = imAMonkey; 11829 Watchdog.getInstance().setActivityController(controller); 11830 } 11831 } 11832 11833 @Override 11834 public void setUserIsMonkey(boolean userIsMonkey) { 11835 synchronized (this) { 11836 synchronized (mPidsSelfLocked) { 11837 final int callingPid = Binder.getCallingPid(); 11838 ProcessRecord precessRecord = mPidsSelfLocked.get(callingPid); 11839 if (precessRecord == null) { 11840 throw new SecurityException("Unknown process: " + callingPid); 11841 } 11842 if (precessRecord.instrumentationUiAutomationConnection == null) { 11843 throw new SecurityException("Only an instrumentation process " 11844 + "with a UiAutomation can call setUserIsMonkey"); 11845 } 11846 } 11847 mUserIsMonkey = userIsMonkey; 11848 } 11849 } 11850 11851 @Override 11852 public boolean isUserAMonkey() { 11853 synchronized (this) { 11854 // If there is a controller also implies the user is a monkey. 11855 return (mUserIsMonkey || (mController != null && mControllerIsAMonkey)); 11856 } 11857 } 11858 11859 public void requestBugReport(int bugreportType) { 11860 String service = null; 11861 switch (bugreportType) { 11862 case ActivityManager.BUGREPORT_OPTION_FULL: 11863 service = "bugreport"; 11864 break; 11865 case ActivityManager.BUGREPORT_OPTION_INTERACTIVE: 11866 service = "bugreportplus"; 11867 break; 11868 case ActivityManager.BUGREPORT_OPTION_REMOTE: 11869 service = "bugreportremote"; 11870 break; 11871 } 11872 if (service == null) { 11873 throw new IllegalArgumentException("Provided bugreport type is not correct, value: " 11874 + bugreportType); 11875 } 11876 enforceCallingPermission(android.Manifest.permission.DUMP, "requestBugReport"); 11877 SystemProperties.set("ctl.start", service); 11878 } 11879 11880 public static long getInputDispatchingTimeoutLocked(ActivityRecord r) { 11881 return r != null ? getInputDispatchingTimeoutLocked(r.app) : KEY_DISPATCHING_TIMEOUT; 11882 } 11883 11884 public static long getInputDispatchingTimeoutLocked(ProcessRecord r) { 11885 if (r != null && (r.instrumentationClass != null || r.usingWrapper)) { 11886 return INSTRUMENTATION_KEY_DISPATCHING_TIMEOUT; 11887 } 11888 return KEY_DISPATCHING_TIMEOUT; 11889 } 11890 11891 @Override 11892 public long inputDispatchingTimedOut(int pid, final boolean aboveSystem, String reason) { 11893 if (checkCallingPermission(android.Manifest.permission.FILTER_EVENTS) 11894 != PackageManager.PERMISSION_GRANTED) { 11895 throw new SecurityException("Requires permission " 11896 + android.Manifest.permission.FILTER_EVENTS); 11897 } 11898 ProcessRecord proc; 11899 long timeout; 11900 synchronized (this) { 11901 synchronized (mPidsSelfLocked) { 11902 proc = mPidsSelfLocked.get(pid); 11903 } 11904 timeout = getInputDispatchingTimeoutLocked(proc); 11905 } 11906 11907 if (!inputDispatchingTimedOut(proc, null, null, aboveSystem, reason)) { 11908 return -1; 11909 } 11910 11911 return timeout; 11912 } 11913 11914 /** 11915 * Handle input dispatching timeouts. 11916 * Returns whether input dispatching should be aborted or not. 11917 */ 11918 public boolean inputDispatchingTimedOut(final ProcessRecord proc, 11919 final ActivityRecord activity, final ActivityRecord parent, 11920 final boolean aboveSystem, String reason) { 11921 if (checkCallingPermission(android.Manifest.permission.FILTER_EVENTS) 11922 != PackageManager.PERMISSION_GRANTED) { 11923 throw new SecurityException("Requires permission " 11924 + android.Manifest.permission.FILTER_EVENTS); 11925 } 11926 11927 final String annotation; 11928 if (reason == null) { 11929 annotation = "Input dispatching timed out"; 11930 } else { 11931 annotation = "Input dispatching timed out (" + reason + ")"; 11932 } 11933 11934 if (proc != null) { 11935 synchronized (this) { 11936 if (proc.debugging) { 11937 return false; 11938 } 11939 11940 if (mDidDexOpt) { 11941 // Give more time since we were dexopting. 11942 mDidDexOpt = false; 11943 return false; 11944 } 11945 11946 if (proc.instrumentationClass != null) { 11947 Bundle info = new Bundle(); 11948 info.putString("shortMsg", "keyDispatchingTimedOut"); 11949 info.putString("longMsg", annotation); 11950 finishInstrumentationLocked(proc, Activity.RESULT_CANCELED, info); 11951 return true; 11952 } 11953 } 11954 mHandler.post(new Runnable() { 11955 @Override 11956 public void run() { 11957 mAppErrors.appNotResponding(proc, activity, parent, aboveSystem, annotation); 11958 } 11959 }); 11960 } 11961 11962 return true; 11963 } 11964 11965 @Override 11966 public Bundle getAssistContextExtras(int requestType) { 11967 PendingAssistExtras pae = enqueueAssistContext(requestType, null, null, null, 11968 null, null, true /* focused */, true /* newSessionId */, 11969 UserHandle.getCallingUserId(), null, PENDING_ASSIST_EXTRAS_TIMEOUT); 11970 if (pae == null) { 11971 return null; 11972 } 11973 synchronized (pae) { 11974 while (!pae.haveResult) { 11975 try { 11976 pae.wait(); 11977 } catch (InterruptedException e) { 11978 } 11979 } 11980 } 11981 synchronized (this) { 11982 buildAssistBundleLocked(pae, pae.result); 11983 mPendingAssistExtras.remove(pae); 11984 mUiHandler.removeCallbacks(pae); 11985 } 11986 return pae.extras; 11987 } 11988 11989 @Override 11990 public boolean isAssistDataAllowedOnCurrentActivity() { 11991 int userId; 11992 synchronized (this) { 11993 userId = mUserController.getCurrentUserIdLocked(); 11994 ActivityRecord activity = getFocusedStack().topActivity(); 11995 if (activity == null) { 11996 return false; 11997 } 11998 userId = activity.userId; 11999 } 12000 DevicePolicyManager dpm = (DevicePolicyManager) mContext.getSystemService( 12001 Context.DEVICE_POLICY_SERVICE); 12002 return (dpm == null) || (!dpm.getScreenCaptureDisabled(null, userId)); 12003 } 12004 12005 @Override 12006 public boolean showAssistFromActivity(IBinder token, Bundle args) { 12007 long ident = Binder.clearCallingIdentity(); 12008 try { 12009 synchronized (this) { 12010 ActivityRecord caller = ActivityRecord.forTokenLocked(token); 12011 ActivityRecord top = getFocusedStack().topActivity(); 12012 if (top != caller) { 12013 Slog.w(TAG, "showAssistFromActivity failed: caller " + caller 12014 + " is not current top " + top); 12015 return false; 12016 } 12017 if (!top.nowVisible) { 12018 Slog.w(TAG, "showAssistFromActivity failed: caller " + caller 12019 + " is not visible"); 12020 return false; 12021 } 12022 } 12023 AssistUtils utils = new AssistUtils(mContext); 12024 return utils.showSessionForActiveService(args, 12025 VoiceInteractionSession.SHOW_SOURCE_APPLICATION, null, token); 12026 } finally { 12027 Binder.restoreCallingIdentity(ident); 12028 } 12029 } 12030 12031 @Override 12032 public boolean requestAssistContextExtras(int requestType, IResultReceiver receiver, 12033 Bundle receiverExtras, 12034 IBinder activityToken, boolean focused, boolean newSessionId) { 12035 return enqueueAssistContext(requestType, null, null, receiver, receiverExtras, 12036 activityToken, focused, newSessionId, 12037 UserHandle.getCallingUserId(), null, PENDING_ASSIST_EXTRAS_LONG_TIMEOUT) 12038 != null; 12039 } 12040 12041 private PendingAssistExtras enqueueAssistContext(int requestType, Intent intent, String hint, 12042 IResultReceiver receiver, Bundle receiverExtras, IBinder activityToken, 12043 boolean focused, boolean newSessionId, int userHandle, Bundle args, long timeout) { 12044 enforceCallingPermission(android.Manifest.permission.GET_TOP_ACTIVITY_INFO, 12045 "enqueueAssistContext()"); 12046 synchronized (this) { 12047 ActivityRecord activity = getFocusedStack().topActivity(); 12048 if (activity == null) { 12049 Slog.w(TAG, "getAssistContextExtras failed: no top activity"); 12050 return null; 12051 } 12052 if (activity.app == null || activity.app.thread == null) { 12053 Slog.w(TAG, "getAssistContextExtras failed: no process for " + activity); 12054 return null; 12055 } 12056 if (focused) { 12057 if (activityToken != null) { 12058 ActivityRecord caller = ActivityRecord.forTokenLocked(activityToken); 12059 if (activity != caller) { 12060 Slog.w(TAG, "enqueueAssistContext failed: caller " + caller 12061 + " is not current top " + activity); 12062 return null; 12063 } 12064 } 12065 } else { 12066 activity = ActivityRecord.forTokenLocked(activityToken); 12067 if (activity == null) { 12068 Slog.w(TAG, "enqueueAssistContext failed: activity for token=" + activityToken 12069 + " couldn't be found"); 12070 return null; 12071 } 12072 } 12073 12074 PendingAssistExtras pae; 12075 Bundle extras = new Bundle(); 12076 if (args != null) { 12077 extras.putAll(args); 12078 } 12079 extras.putString(Intent.EXTRA_ASSIST_PACKAGE, activity.packageName); 12080 extras.putInt(Intent.EXTRA_ASSIST_UID, activity.app.uid); 12081 pae = new PendingAssistExtras(activity, extras, intent, hint, receiver, receiverExtras, 12082 userHandle); 12083 // Increment the sessionId if necessary 12084 if (newSessionId) { 12085 mViSessionId++; 12086 } 12087 try { 12088 activity.app.thread.requestAssistContextExtras(activity.appToken, pae, 12089 requestType, mViSessionId); 12090 mPendingAssistExtras.add(pae); 12091 mUiHandler.postDelayed(pae, timeout); 12092 } catch (RemoteException e) { 12093 Slog.w(TAG, "getAssistContextExtras failed: crash calling " + activity); 12094 return null; 12095 } 12096 return pae; 12097 } 12098 } 12099 12100 void pendingAssistExtrasTimedOut(PendingAssistExtras pae) { 12101 IResultReceiver receiver; 12102 synchronized (this) { 12103 mPendingAssistExtras.remove(pae); 12104 receiver = pae.receiver; 12105 } 12106 if (receiver != null) { 12107 // Caller wants result sent back to them. 12108 Bundle sendBundle = new Bundle(); 12109 // At least return the receiver extras 12110 sendBundle.putBundle(VoiceInteractionSession.KEY_RECEIVER_EXTRAS, 12111 pae.receiverExtras); 12112 try { 12113 pae.receiver.send(0, sendBundle); 12114 } catch (RemoteException e) { 12115 } 12116 } 12117 } 12118 12119 private void buildAssistBundleLocked(PendingAssistExtras pae, Bundle result) { 12120 if (result != null) { 12121 pae.extras.putBundle(Intent.EXTRA_ASSIST_CONTEXT, result); 12122 } 12123 if (pae.hint != null) { 12124 pae.extras.putBoolean(pae.hint, true); 12125 } 12126 } 12127 12128 public void reportAssistContextExtras(IBinder token, Bundle extras, AssistStructure structure, 12129 AssistContent content, Uri referrer) { 12130 PendingAssistExtras pae = (PendingAssistExtras)token; 12131 synchronized (pae) { 12132 pae.result = extras; 12133 pae.structure = structure; 12134 pae.content = content; 12135 if (referrer != null) { 12136 pae.extras.putParcelable(Intent.EXTRA_REFERRER, referrer); 12137 } 12138 pae.haveResult = true; 12139 pae.notifyAll(); 12140 if (pae.intent == null && pae.receiver == null) { 12141 // Caller is just waiting for the result. 12142 return; 12143 } 12144 } 12145 12146 // We are now ready to launch the assist activity. 12147 IResultReceiver sendReceiver = null; 12148 Bundle sendBundle = null; 12149 synchronized (this) { 12150 buildAssistBundleLocked(pae, extras); 12151 boolean exists = mPendingAssistExtras.remove(pae); 12152 mUiHandler.removeCallbacks(pae); 12153 if (!exists) { 12154 // Timed out. 12155 return; 12156 } 12157 if ((sendReceiver=pae.receiver) != null) { 12158 // Caller wants result sent back to them. 12159 sendBundle = new Bundle(); 12160 sendBundle.putBundle(VoiceInteractionSession.KEY_DATA, pae.extras); 12161 sendBundle.putParcelable(VoiceInteractionSession.KEY_STRUCTURE, pae.structure); 12162 sendBundle.putParcelable(VoiceInteractionSession.KEY_CONTENT, pae.content); 12163 sendBundle.putBundle(VoiceInteractionSession.KEY_RECEIVER_EXTRAS, 12164 pae.receiverExtras); 12165 } 12166 } 12167 if (sendReceiver != null) { 12168 try { 12169 sendReceiver.send(0, sendBundle); 12170 } catch (RemoteException e) { 12171 } 12172 return; 12173 } 12174 12175 long ident = Binder.clearCallingIdentity(); 12176 try { 12177 pae.intent.replaceExtras(pae.extras); 12178 pae.intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK 12179 | Intent.FLAG_ACTIVITY_SINGLE_TOP 12180 | Intent.FLAG_ACTIVITY_CLEAR_TOP); 12181 closeSystemDialogs("assist"); 12182 try { 12183 mContext.startActivityAsUser(pae.intent, new UserHandle(pae.userHandle)); 12184 } catch (ActivityNotFoundException e) { 12185 Slog.w(TAG, "No activity to handle assist action.", e); 12186 } 12187 } finally { 12188 Binder.restoreCallingIdentity(ident); 12189 } 12190 } 12191 12192 public boolean launchAssistIntent(Intent intent, int requestType, String hint, int userHandle, 12193 Bundle args) { 12194 return enqueueAssistContext(requestType, intent, hint, null, null, null, 12195 true /* focused */, true /* newSessionId */, 12196 userHandle, args, PENDING_ASSIST_EXTRAS_TIMEOUT) != null; 12197 } 12198 12199 public void registerProcessObserver(IProcessObserver observer) { 12200 enforceCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER, 12201 "registerProcessObserver()"); 12202 synchronized (this) { 12203 mProcessObservers.register(observer); 12204 } 12205 } 12206 12207 @Override 12208 public void unregisterProcessObserver(IProcessObserver observer) { 12209 synchronized (this) { 12210 mProcessObservers.unregister(observer); 12211 } 12212 } 12213 12214 @Override 12215 public void registerUidObserver(IUidObserver observer, int which) { 12216 enforceCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER, 12217 "registerUidObserver()"); 12218 synchronized (this) { 12219 mUidObservers.register(observer, which); 12220 } 12221 } 12222 12223 @Override 12224 public void unregisterUidObserver(IUidObserver observer) { 12225 synchronized (this) { 12226 mUidObservers.unregister(observer); 12227 } 12228 } 12229 12230 @Override 12231 public boolean convertFromTranslucent(IBinder token) { 12232 final long origId = Binder.clearCallingIdentity(); 12233 try { 12234 synchronized (this) { 12235 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 12236 if (r == null) { 12237 return false; 12238 } 12239 final boolean translucentChanged = r.changeWindowTranslucency(true); 12240 if (translucentChanged) { 12241 r.task.stack.releaseBackgroundResources(r); 12242 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0, !PRESERVE_WINDOWS); 12243 } 12244 mWindowManager.setAppFullscreen(token, true); 12245 return translucentChanged; 12246 } 12247 } finally { 12248 Binder.restoreCallingIdentity(origId); 12249 } 12250 } 12251 12252 @Override 12253 public boolean convertToTranslucent(IBinder token, ActivityOptions options) { 12254 final long origId = Binder.clearCallingIdentity(); 12255 try { 12256 synchronized (this) { 12257 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 12258 if (r == null) { 12259 return false; 12260 } 12261 int index = r.task.mActivities.lastIndexOf(r); 12262 if (index > 0) { 12263 ActivityRecord under = r.task.mActivities.get(index - 1); 12264 under.returningOptions = options; 12265 } 12266 final boolean translucentChanged = r.changeWindowTranslucency(false); 12267 if (translucentChanged) { 12268 r.task.stack.convertActivityToTranslucent(r); 12269 } 12270 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0, !PRESERVE_WINDOWS); 12271 mWindowManager.setAppFullscreen(token, false); 12272 return translucentChanged; 12273 } 12274 } finally { 12275 Binder.restoreCallingIdentity(origId); 12276 } 12277 } 12278 12279 @Override 12280 public boolean requestVisibleBehind(IBinder token, boolean visible) { 12281 final long origId = Binder.clearCallingIdentity(); 12282 try { 12283 synchronized (this) { 12284 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 12285 if (r != null) { 12286 return mStackSupervisor.requestVisibleBehindLocked(r, visible); 12287 } 12288 } 12289 return false; 12290 } finally { 12291 Binder.restoreCallingIdentity(origId); 12292 } 12293 } 12294 12295 @Override 12296 public boolean isBackgroundVisibleBehind(IBinder token) { 12297 final long origId = Binder.clearCallingIdentity(); 12298 try { 12299 synchronized (this) { 12300 final ActivityStack stack = ActivityRecord.getStackLocked(token); 12301 final boolean visible = stack == null ? false : stack.hasVisibleBehindActivity(); 12302 if (DEBUG_VISIBLE_BEHIND) Slog.d(TAG_VISIBLE_BEHIND, 12303 "isBackgroundVisibleBehind: stack=" + stack + " visible=" + visible); 12304 return visible; 12305 } 12306 } finally { 12307 Binder.restoreCallingIdentity(origId); 12308 } 12309 } 12310 12311 @Override 12312 public ActivityOptions getActivityOptions(IBinder token) { 12313 final long origId = Binder.clearCallingIdentity(); 12314 try { 12315 synchronized (this) { 12316 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 12317 if (r != null) { 12318 final ActivityOptions activityOptions = r.pendingOptions; 12319 r.pendingOptions = null; 12320 return activityOptions; 12321 } 12322 return null; 12323 } 12324 } finally { 12325 Binder.restoreCallingIdentity(origId); 12326 } 12327 } 12328 12329 @Override 12330 public void setImmersive(IBinder token, boolean immersive) { 12331 synchronized(this) { 12332 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 12333 if (r == null) { 12334 throw new IllegalArgumentException(); 12335 } 12336 r.immersive = immersive; 12337 12338 // update associated state if we're frontmost 12339 if (r == mFocusedActivity) { 12340 if (DEBUG_IMMERSIVE) Slog.d(TAG_IMMERSIVE, "Frontmost changed immersion: "+ r); 12341 applyUpdateLockStateLocked(r); 12342 } 12343 } 12344 } 12345 12346 @Override 12347 public boolean isImmersive(IBinder token) { 12348 synchronized (this) { 12349 ActivityRecord r = ActivityRecord.isInStackLocked(token); 12350 if (r == null) { 12351 throw new IllegalArgumentException(); 12352 } 12353 return r.immersive; 12354 } 12355 } 12356 12357 @Override 12358 public int setVrMode(IBinder token, boolean enabled, ComponentName packageName) { 12359 if (!mContext.getPackageManager().hasSystemFeature(PackageManager.FEATURE_VR_MODE)) { 12360 throw new UnsupportedOperationException("VR mode not supported on this device!"); 12361 } 12362 12363 final VrManagerInternal vrService = LocalServices.getService(VrManagerInternal.class); 12364 12365 ActivityRecord r; 12366 synchronized (this) { 12367 r = ActivityRecord.isInStackLocked(token); 12368 } 12369 12370 if (r == null) { 12371 throw new IllegalArgumentException(); 12372 } 12373 12374 int err; 12375 if ((err = vrService.hasVrPackage(packageName, r.userId)) != 12376 VrManagerInternal.NO_ERROR) { 12377 return err; 12378 } 12379 12380 synchronized(this) { 12381 r.requestedVrComponent = (enabled) ? packageName : null; 12382 12383 // Update associated state if this activity is currently focused 12384 if (r == mFocusedActivity) { 12385 applyUpdateVrModeLocked(r); 12386 } 12387 return 0; 12388 } 12389 } 12390 12391 @Override 12392 public boolean isVrModePackageEnabled(ComponentName packageName) { 12393 if (!mContext.getPackageManager().hasSystemFeature(PackageManager.FEATURE_VR_MODE)) { 12394 throw new UnsupportedOperationException("VR mode not supported on this device!"); 12395 } 12396 12397 final VrManagerInternal vrService = LocalServices.getService(VrManagerInternal.class); 12398 12399 return vrService.hasVrPackage(packageName, UserHandle.getCallingUserId()) == 12400 VrManagerInternal.NO_ERROR; 12401 } 12402 12403 public boolean isTopActivityImmersive() { 12404 enforceNotIsolatedCaller("startActivity"); 12405 synchronized (this) { 12406 ActivityRecord r = getFocusedStack().topRunningActivityLocked(); 12407 return (r != null) ? r.immersive : false; 12408 } 12409 } 12410 12411 @Override 12412 public boolean isTopOfTask(IBinder token) { 12413 synchronized (this) { 12414 ActivityRecord r = ActivityRecord.isInStackLocked(token); 12415 if (r == null) { 12416 throw new IllegalArgumentException(); 12417 } 12418 return r.task.getTopActivity() == r; 12419 } 12420 } 12421 12422 public final void enterSafeMode() { 12423 synchronized(this) { 12424 // It only makes sense to do this before the system is ready 12425 // and started launching other packages. 12426 if (!mSystemReady) { 12427 try { 12428 AppGlobals.getPackageManager().enterSafeMode(); 12429 } catch (RemoteException e) { 12430 } 12431 } 12432 12433 mSafeMode = true; 12434 } 12435 } 12436 12437 public final void showSafeModeOverlay() { 12438 View v = LayoutInflater.from(mContext).inflate( 12439 com.android.internal.R.layout.safe_mode, null); 12440 WindowManager.LayoutParams lp = new WindowManager.LayoutParams(); 12441 lp.type = WindowManager.LayoutParams.TYPE_SECURE_SYSTEM_OVERLAY; 12442 lp.width = WindowManager.LayoutParams.WRAP_CONTENT; 12443 lp.height = WindowManager.LayoutParams.WRAP_CONTENT; 12444 lp.gravity = Gravity.BOTTOM | Gravity.START; 12445 lp.format = v.getBackground().getOpacity(); 12446 lp.flags = WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE 12447 | WindowManager.LayoutParams.FLAG_NOT_TOUCHABLE; 12448 lp.privateFlags |= WindowManager.LayoutParams.PRIVATE_FLAG_SHOW_FOR_ALL_USERS; 12449 ((WindowManager)mContext.getSystemService( 12450 Context.WINDOW_SERVICE)).addView(v, lp); 12451 } 12452 12453 public void noteWakeupAlarm(IIntentSender sender, int sourceUid, String sourcePkg, String tag) { 12454 if (sender != null && !(sender instanceof PendingIntentRecord)) { 12455 return; 12456 } 12457 final PendingIntentRecord rec = (PendingIntentRecord)sender; 12458 final BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 12459 synchronized (stats) { 12460 if (mBatteryStatsService.isOnBattery()) { 12461 mBatteryStatsService.enforceCallingPermission(); 12462 int MY_UID = Binder.getCallingUid(); 12463 final int uid; 12464 if (sender == null) { 12465 uid = sourceUid; 12466 } else { 12467 uid = rec.uid == MY_UID ? Process.SYSTEM_UID : rec.uid; 12468 } 12469 BatteryStatsImpl.Uid.Pkg pkg = 12470 stats.getPackageStatsLocked(sourceUid >= 0 ? sourceUid : uid, 12471 sourcePkg != null ? sourcePkg : rec.key.packageName); 12472 pkg.noteWakeupAlarmLocked(tag); 12473 } 12474 } 12475 } 12476 12477 public void noteAlarmStart(IIntentSender sender, int sourceUid, String tag) { 12478 if (sender != null && !(sender instanceof PendingIntentRecord)) { 12479 return; 12480 } 12481 final PendingIntentRecord rec = (PendingIntentRecord)sender; 12482 final BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 12483 synchronized (stats) { 12484 mBatteryStatsService.enforceCallingPermission(); 12485 int MY_UID = Binder.getCallingUid(); 12486 final int uid; 12487 if (sender == null) { 12488 uid = sourceUid; 12489 } else { 12490 uid = rec.uid == MY_UID ? Process.SYSTEM_UID : rec.uid; 12491 } 12492 mBatteryStatsService.noteAlarmStart(tag, sourceUid >= 0 ? sourceUid : uid); 12493 } 12494 } 12495 12496 public void noteAlarmFinish(IIntentSender sender, int sourceUid, String tag) { 12497 if (sender != null && !(sender instanceof PendingIntentRecord)) { 12498 return; 12499 } 12500 final PendingIntentRecord rec = (PendingIntentRecord)sender; 12501 final BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 12502 synchronized (stats) { 12503 mBatteryStatsService.enforceCallingPermission(); 12504 int MY_UID = Binder.getCallingUid(); 12505 final int uid; 12506 if (sender == null) { 12507 uid = sourceUid; 12508 } else { 12509 uid = rec.uid == MY_UID ? Process.SYSTEM_UID : rec.uid; 12510 } 12511 mBatteryStatsService.noteAlarmFinish(tag, sourceUid >= 0 ? sourceUid : uid); 12512 } 12513 } 12514 12515 public boolean killPids(int[] pids, String pReason, boolean secure) { 12516 if (Binder.getCallingUid() != Process.SYSTEM_UID) { 12517 throw new SecurityException("killPids only available to the system"); 12518 } 12519 String reason = (pReason == null) ? "Unknown" : pReason; 12520 // XXX Note: don't acquire main activity lock here, because the window 12521 // manager calls in with its locks held. 12522 12523 boolean killed = false; 12524 synchronized (mPidsSelfLocked) { 12525 int worstType = 0; 12526 for (int i=0; i<pids.length; i++) { 12527 ProcessRecord proc = mPidsSelfLocked.get(pids[i]); 12528 if (proc != null) { 12529 int type = proc.setAdj; 12530 if (type > worstType) { 12531 worstType = type; 12532 } 12533 } 12534 } 12535 12536 // If the worst oom_adj is somewhere in the cached proc LRU range, 12537 // then constrain it so we will kill all cached procs. 12538 if (worstType < ProcessList.CACHED_APP_MAX_ADJ 12539 && worstType > ProcessList.CACHED_APP_MIN_ADJ) { 12540 worstType = ProcessList.CACHED_APP_MIN_ADJ; 12541 } 12542 12543 // If this is not a secure call, don't let it kill processes that 12544 // are important. 12545 if (!secure && worstType < ProcessList.SERVICE_ADJ) { 12546 worstType = ProcessList.SERVICE_ADJ; 12547 } 12548 12549 Slog.w(TAG, "Killing processes " + reason + " at adjustment " + worstType); 12550 for (int i=0; i<pids.length; i++) { 12551 ProcessRecord proc = mPidsSelfLocked.get(pids[i]); 12552 if (proc == null) { 12553 continue; 12554 } 12555 int adj = proc.setAdj; 12556 if (adj >= worstType && !proc.killedByAm) { 12557 proc.kill(reason, true); 12558 killed = true; 12559 } 12560 } 12561 } 12562 return killed; 12563 } 12564 12565 @Override 12566 public void killUid(int appId, int userId, String reason) { 12567 enforceCallingPermission(Manifest.permission.KILL_UID, "killUid"); 12568 synchronized (this) { 12569 final long identity = Binder.clearCallingIdentity(); 12570 try { 12571 killPackageProcessesLocked(null, appId, userId, 12572 ProcessList.PERSISTENT_PROC_ADJ, false, true, true, true, 12573 reason != null ? reason : "kill uid"); 12574 } finally { 12575 Binder.restoreCallingIdentity(identity); 12576 } 12577 } 12578 } 12579 12580 @Override 12581 public boolean killProcessesBelowForeground(String reason) { 12582 if (Binder.getCallingUid() != Process.SYSTEM_UID) { 12583 throw new SecurityException("killProcessesBelowForeground() only available to system"); 12584 } 12585 12586 return killProcessesBelowAdj(ProcessList.FOREGROUND_APP_ADJ, reason); 12587 } 12588 12589 private boolean killProcessesBelowAdj(int belowAdj, String reason) { 12590 if (Binder.getCallingUid() != Process.SYSTEM_UID) { 12591 throw new SecurityException("killProcessesBelowAdj() only available to system"); 12592 } 12593 12594 boolean killed = false; 12595 synchronized (mPidsSelfLocked) { 12596 final int size = mPidsSelfLocked.size(); 12597 for (int i = 0; i < size; i++) { 12598 final int pid = mPidsSelfLocked.keyAt(i); 12599 final ProcessRecord proc = mPidsSelfLocked.valueAt(i); 12600 if (proc == null) continue; 12601 12602 final int adj = proc.setAdj; 12603 if (adj > belowAdj && !proc.killedByAm) { 12604 proc.kill(reason, true); 12605 killed = true; 12606 } 12607 } 12608 } 12609 return killed; 12610 } 12611 12612 @Override 12613 public void hang(final IBinder who, boolean allowRestart) { 12614 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 12615 != PackageManager.PERMISSION_GRANTED) { 12616 throw new SecurityException("Requires permission " 12617 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 12618 } 12619 12620 final IBinder.DeathRecipient death = new DeathRecipient() { 12621 @Override 12622 public void binderDied() { 12623 synchronized (this) { 12624 notifyAll(); 12625 } 12626 } 12627 }; 12628 12629 try { 12630 who.linkToDeath(death, 0); 12631 } catch (RemoteException e) { 12632 Slog.w(TAG, "hang: given caller IBinder is already dead."); 12633 return; 12634 } 12635 12636 synchronized (this) { 12637 Watchdog.getInstance().setAllowRestart(allowRestart); 12638 Slog.i(TAG, "Hanging system process at request of pid " + Binder.getCallingPid()); 12639 synchronized (death) { 12640 while (who.isBinderAlive()) { 12641 try { 12642 death.wait(); 12643 } catch (InterruptedException e) { 12644 } 12645 } 12646 } 12647 Watchdog.getInstance().setAllowRestart(true); 12648 } 12649 } 12650 12651 @Override 12652 public void restart() { 12653 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 12654 != PackageManager.PERMISSION_GRANTED) { 12655 throw new SecurityException("Requires permission " 12656 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 12657 } 12658 12659 Log.i(TAG, "Sending shutdown broadcast..."); 12660 12661 BroadcastReceiver br = new BroadcastReceiver() { 12662 @Override public void onReceive(Context context, Intent intent) { 12663 // Now the broadcast is done, finish up the low-level shutdown. 12664 Log.i(TAG, "Shutting down activity manager..."); 12665 shutdown(10000); 12666 Log.i(TAG, "Shutdown complete, restarting!"); 12667 Process.killProcess(Process.myPid()); 12668 System.exit(10); 12669 } 12670 }; 12671 12672 // First send the high-level shut down broadcast. 12673 Intent intent = new Intent(Intent.ACTION_SHUTDOWN); 12674 intent.addFlags(Intent.FLAG_RECEIVER_FOREGROUND); 12675 intent.putExtra(Intent.EXTRA_SHUTDOWN_USERSPACE_ONLY, true); 12676 /* For now we are not doing a clean shutdown, because things seem to get unhappy. 12677 mContext.sendOrderedBroadcastAsUser(intent, 12678 UserHandle.ALL, null, br, mHandler, 0, null, null); 12679 */ 12680 br.onReceive(mContext, intent); 12681 } 12682 12683 private long getLowRamTimeSinceIdle(long now) { 12684 return mLowRamTimeSinceLastIdle + (mLowRamStartTime > 0 ? (now-mLowRamStartTime) : 0); 12685 } 12686 12687 @Override 12688 public void performIdleMaintenance() { 12689 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 12690 != PackageManager.PERMISSION_GRANTED) { 12691 throw new SecurityException("Requires permission " 12692 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 12693 } 12694 12695 synchronized (this) { 12696 final long now = SystemClock.uptimeMillis(); 12697 final long timeSinceLastIdle = now - mLastIdleTime; 12698 final long lowRamSinceLastIdle = getLowRamTimeSinceIdle(now); 12699 mLastIdleTime = now; 12700 mLowRamTimeSinceLastIdle = 0; 12701 if (mLowRamStartTime != 0) { 12702 mLowRamStartTime = now; 12703 } 12704 12705 StringBuilder sb = new StringBuilder(128); 12706 sb.append("Idle maintenance over "); 12707 TimeUtils.formatDuration(timeSinceLastIdle, sb); 12708 sb.append(" low RAM for "); 12709 TimeUtils.formatDuration(lowRamSinceLastIdle, sb); 12710 Slog.i(TAG, sb.toString()); 12711 12712 // If at least 1/3 of our time since the last idle period has been spent 12713 // with RAM low, then we want to kill processes. 12714 boolean doKilling = lowRamSinceLastIdle > (timeSinceLastIdle/3); 12715 12716 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 12717 ProcessRecord proc = mLruProcesses.get(i); 12718 if (proc.notCachedSinceIdle) { 12719 if (proc.setProcState != ActivityManager.PROCESS_STATE_TOP_SLEEPING 12720 && proc.setProcState >= ActivityManager.PROCESS_STATE_FOREGROUND_SERVICE 12721 && proc.setProcState <= ActivityManager.PROCESS_STATE_SERVICE) { 12722 if (doKilling && proc.initialIdlePss != 0 12723 && proc.lastPss > ((proc.initialIdlePss*3)/2)) { 12724 sb = new StringBuilder(128); 12725 sb.append("Kill"); 12726 sb.append(proc.processName); 12727 sb.append(" in idle maint: pss="); 12728 sb.append(proc.lastPss); 12729 sb.append(", swapPss="); 12730 sb.append(proc.lastSwapPss); 12731 sb.append(", initialPss="); 12732 sb.append(proc.initialIdlePss); 12733 sb.append(", period="); 12734 TimeUtils.formatDuration(timeSinceLastIdle, sb); 12735 sb.append(", lowRamPeriod="); 12736 TimeUtils.formatDuration(lowRamSinceLastIdle, sb); 12737 Slog.wtfQuiet(TAG, sb.toString()); 12738 proc.kill("idle maint (pss " + proc.lastPss 12739 + " from " + proc.initialIdlePss + ")", true); 12740 } 12741 } 12742 } else if (proc.setProcState < ActivityManager.PROCESS_STATE_HOME 12743 && proc.setProcState > ActivityManager.PROCESS_STATE_NONEXISTENT) { 12744 proc.notCachedSinceIdle = true; 12745 proc.initialIdlePss = 0; 12746 proc.nextPssTime = ProcessList.computeNextPssTime(proc.setProcState, true, 12747 mTestPssMode, isSleeping(), now); 12748 } 12749 } 12750 12751 mHandler.removeMessages(REQUEST_ALL_PSS_MSG); 12752 mHandler.sendEmptyMessageDelayed(REQUEST_ALL_PSS_MSG, 2*60*1000); 12753 } 12754 } 12755 12756 @Override 12757 public void sendIdleJobTrigger() { 12758 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 12759 != PackageManager.PERMISSION_GRANTED) { 12760 throw new SecurityException("Requires permission " 12761 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 12762 } 12763 12764 final long ident = Binder.clearCallingIdentity(); 12765 try { 12766 Intent intent = new Intent(ACTION_TRIGGER_IDLE) 12767 .setPackage("android") 12768 .addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 12769 broadcastIntent(null, intent, null, null, 0, null, null, null, 12770 android.app.AppOpsManager.OP_NONE, null, true, false, UserHandle.USER_ALL); 12771 } finally { 12772 Binder.restoreCallingIdentity(ident); 12773 } 12774 } 12775 12776 private void retrieveSettings() { 12777 final ContentResolver resolver = mContext.getContentResolver(); 12778 final boolean freeformWindowManagement = 12779 mContext.getPackageManager().hasSystemFeature(FEATURE_FREEFORM_WINDOW_MANAGEMENT) 12780 || Settings.Global.getInt( 12781 resolver, DEVELOPMENT_ENABLE_FREEFORM_WINDOWS_SUPPORT, 0) != 0; 12782 final boolean supportsPictureInPicture = 12783 mContext.getPackageManager().hasSystemFeature(FEATURE_PICTURE_IN_PICTURE); 12784 12785 final boolean supportsMultiWindow = ActivityManager.supportsMultiWindow(); 12786 final String debugApp = Settings.Global.getString(resolver, DEBUG_APP); 12787 final boolean waitForDebugger = Settings.Global.getInt(resolver, WAIT_FOR_DEBUGGER, 0) != 0; 12788 final boolean alwaysFinishActivities = 12789 Settings.Global.getInt(resolver, ALWAYS_FINISH_ACTIVITIES, 0) != 0; 12790 final boolean lenientBackgroundCheck = 12791 Settings.Global.getInt(resolver, LENIENT_BACKGROUND_CHECK, 0) != 0; 12792 final boolean forceRtl = Settings.Global.getInt(resolver, DEVELOPMENT_FORCE_RTL, 0) != 0; 12793 final boolean forceResizable = Settings.Global.getInt( 12794 resolver, DEVELOPMENT_FORCE_RESIZABLE_ACTIVITIES, 0) != 0; 12795 // Transfer any global setting for forcing RTL layout, into a System Property 12796 SystemProperties.set(DEVELOPMENT_FORCE_RTL, forceRtl ? "1":"0"); 12797 12798 final Configuration configuration = new Configuration(); 12799 Settings.System.getConfiguration(resolver, configuration); 12800 if (forceRtl) { 12801 // This will take care of setting the correct layout direction flags 12802 configuration.setLayoutDirection(configuration.locale); 12803 } 12804 12805 synchronized (this) { 12806 mDebugApp = mOrigDebugApp = debugApp; 12807 mWaitForDebugger = mOrigWaitForDebugger = waitForDebugger; 12808 mAlwaysFinishActivities = alwaysFinishActivities; 12809 mLenientBackgroundCheck = lenientBackgroundCheck; 12810 mForceResizableActivities = forceResizable; 12811 mWindowManager.setForceResizableTasks(mForceResizableActivities); 12812 if (supportsMultiWindow || forceResizable) { 12813 mSupportsMultiWindow = true; 12814 mSupportsFreeformWindowManagement = freeformWindowManagement || forceResizable; 12815 mSupportsPictureInPicture = supportsPictureInPicture || forceResizable; 12816 } else { 12817 mSupportsMultiWindow = false; 12818 mSupportsFreeformWindowManagement = false; 12819 mSupportsPictureInPicture = false; 12820 } 12821 // This happens before any activities are started, so we can 12822 // change mConfiguration in-place. 12823 updateConfigurationLocked(configuration, null, true); 12824 if (DEBUG_CONFIGURATION) Slog.v(TAG_CONFIGURATION, 12825 "Initial config: " + mConfiguration); 12826 12827 // Load resources only after the current configuration has been set. 12828 final Resources res = mContext.getResources(); 12829 mHasRecents = res.getBoolean(com.android.internal.R.bool.config_hasRecents); 12830 mThumbnailWidth = res.getDimensionPixelSize( 12831 com.android.internal.R.dimen.thumbnail_width); 12832 mThumbnailHeight = res.getDimensionPixelSize( 12833 com.android.internal.R.dimen.thumbnail_height); 12834 mDefaultPinnedStackBounds = Rect.unflattenFromString(res.getString( 12835 com.android.internal.R.string.config_defaultPictureInPictureBounds)); 12836 mAppErrors.loadAppsNotReportingCrashesFromConfigLocked(res.getString( 12837 com.android.internal.R.string.config_appsNotReportingCrashes)); 12838 if ((mConfiguration.uiMode & UI_MODE_TYPE_TELEVISION) == UI_MODE_TYPE_TELEVISION) { 12839 mFullscreenThumbnailScale = (float) res 12840 .getInteger(com.android.internal.R.integer.thumbnail_width_tv) / 12841 (float) mConfiguration.screenWidthDp; 12842 } else { 12843 mFullscreenThumbnailScale = res.getFraction( 12844 com.android.internal.R.fraction.thumbnail_fullscreen_scale, 1, 1); 12845 } 12846 } 12847 } 12848 12849 public boolean testIsSystemReady() { 12850 // no need to synchronize(this) just to read & return the value 12851 return mSystemReady; 12852 } 12853 12854 public void systemReady(final Runnable goingCallback) { 12855 synchronized(this) { 12856 if (mSystemReady) { 12857 // If we're done calling all the receivers, run the next "boot phase" passed in 12858 // by the SystemServer 12859 if (goingCallback != null) { 12860 goingCallback.run(); 12861 } 12862 return; 12863 } 12864 12865 mLocalDeviceIdleController 12866 = LocalServices.getService(DeviceIdleController.LocalService.class); 12867 12868 // Make sure we have the current profile info, since it is needed for security checks. 12869 mUserController.onSystemReady(); 12870 mRecentTasks.onSystemReadyLocked(); 12871 mAppOpsService.systemReady(); 12872 mSystemReady = true; 12873 } 12874 12875 ArrayList<ProcessRecord> procsToKill = null; 12876 synchronized(mPidsSelfLocked) { 12877 for (int i=mPidsSelfLocked.size()-1; i>=0; i--) { 12878 ProcessRecord proc = mPidsSelfLocked.valueAt(i); 12879 if (!isAllowedWhileBooting(proc.info)){ 12880 if (procsToKill == null) { 12881 procsToKill = new ArrayList<ProcessRecord>(); 12882 } 12883 procsToKill.add(proc); 12884 } 12885 } 12886 } 12887 12888 synchronized(this) { 12889 if (procsToKill != null) { 12890 for (int i=procsToKill.size()-1; i>=0; i--) { 12891 ProcessRecord proc = procsToKill.get(i); 12892 Slog.i(TAG, "Removing system update proc: " + proc); 12893 removeProcessLocked(proc, true, false, "system update done"); 12894 } 12895 } 12896 12897 // Now that we have cleaned up any update processes, we 12898 // are ready to start launching real processes and know that 12899 // we won't trample on them any more. 12900 mProcessesReady = true; 12901 } 12902 12903 Slog.i(TAG, "System now ready"); 12904 EventLog.writeEvent(EventLogTags.BOOT_PROGRESS_AMS_READY, 12905 SystemClock.uptimeMillis()); 12906 12907 synchronized(this) { 12908 // Make sure we have no pre-ready processes sitting around. 12909 12910 if (mFactoryTest == FactoryTest.FACTORY_TEST_LOW_LEVEL) { 12911 ResolveInfo ri = mContext.getPackageManager() 12912 .resolveActivity(new Intent(Intent.ACTION_FACTORY_TEST), 12913 STOCK_PM_FLAGS); 12914 CharSequence errorMsg = null; 12915 if (ri != null) { 12916 ActivityInfo ai = ri.activityInfo; 12917 ApplicationInfo app = ai.applicationInfo; 12918 if ((app.flags&ApplicationInfo.FLAG_SYSTEM) != 0) { 12919 mTopAction = Intent.ACTION_FACTORY_TEST; 12920 mTopData = null; 12921 mTopComponent = new ComponentName(app.packageName, 12922 ai.name); 12923 } else { 12924 errorMsg = mContext.getResources().getText( 12925 com.android.internal.R.string.factorytest_not_system); 12926 } 12927 } else { 12928 errorMsg = mContext.getResources().getText( 12929 com.android.internal.R.string.factorytest_no_action); 12930 } 12931 if (errorMsg != null) { 12932 mTopAction = null; 12933 mTopData = null; 12934 mTopComponent = null; 12935 Message msg = Message.obtain(); 12936 msg.what = SHOW_FACTORY_ERROR_UI_MSG; 12937 msg.getData().putCharSequence("msg", errorMsg); 12938 mUiHandler.sendMessage(msg); 12939 } 12940 } 12941 } 12942 12943 retrieveSettings(); 12944 final int currentUserId; 12945 synchronized (this) { 12946 currentUserId = mUserController.getCurrentUserIdLocked(); 12947 readGrantedUriPermissionsLocked(); 12948 } 12949 12950 if (goingCallback != null) goingCallback.run(); 12951 12952 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_USER_RUNNING_START, 12953 Integer.toString(currentUserId), currentUserId); 12954 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_USER_FOREGROUND_START, 12955 Integer.toString(currentUserId), currentUserId); 12956 mSystemServiceManager.startUser(currentUserId); 12957 12958 synchronized (this) { 12959 // Only start up encryption-aware persistent apps; once user is 12960 // unlocked we'll come back around and start unaware apps 12961 startPersistentApps(PackageManager.MATCH_DIRECT_BOOT_AWARE); 12962 12963 // Start up initial activity. 12964 mBooting = true; 12965 // Enable home activity for system user, so that the system can always boot 12966 if (UserManager.isSplitSystemUser()) { 12967 ComponentName cName = new ComponentName(mContext, SystemUserHomeActivity.class); 12968 try { 12969 AppGlobals.getPackageManager().setComponentEnabledSetting(cName, 12970 PackageManager.COMPONENT_ENABLED_STATE_ENABLED, 0, 12971 UserHandle.USER_SYSTEM); 12972 } catch (RemoteException e) { 12973 throw e.rethrowAsRuntimeException(); 12974 } 12975 } 12976 startHomeActivityLocked(currentUserId, "systemReady"); 12977 12978 try { 12979 if (AppGlobals.getPackageManager().hasSystemUidErrors()) { 12980 Slog.e(TAG, "UIDs on the system are inconsistent, you need to wipe your" 12981 + " data partition or your device will be unstable."); 12982 mUiHandler.obtainMessage(SHOW_UID_ERROR_UI_MSG).sendToTarget(); 12983 } 12984 } catch (RemoteException e) { 12985 } 12986 12987 if (!Build.isBuildConsistent()) { 12988 Slog.e(TAG, "Build fingerprint is not consistent, warning user"); 12989 mUiHandler.obtainMessage(SHOW_FINGERPRINT_ERROR_UI_MSG).sendToTarget(); 12990 } 12991 12992 long ident = Binder.clearCallingIdentity(); 12993 try { 12994 Intent intent = new Intent(Intent.ACTION_USER_STARTED); 12995 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 12996 | Intent.FLAG_RECEIVER_FOREGROUND); 12997 intent.putExtra(Intent.EXTRA_USER_HANDLE, currentUserId); 12998 broadcastIntentLocked(null, null, intent, 12999 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 13000 null, false, false, MY_PID, Process.SYSTEM_UID, 13001 currentUserId); 13002 intent = new Intent(Intent.ACTION_USER_STARTING); 13003 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 13004 intent.putExtra(Intent.EXTRA_USER_HANDLE, currentUserId); 13005 broadcastIntentLocked(null, null, intent, 13006 null, new IIntentReceiver.Stub() { 13007 @Override 13008 public void performReceive(Intent intent, int resultCode, String data, 13009 Bundle extras, boolean ordered, boolean sticky, int sendingUser) 13010 throws RemoteException { 13011 } 13012 }, 0, null, null, 13013 new String[] {INTERACT_ACROSS_USERS}, AppOpsManager.OP_NONE, 13014 null, true, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 13015 } catch (Throwable t) { 13016 Slog.wtf(TAG, "Failed sending first user broadcasts", t); 13017 } finally { 13018 Binder.restoreCallingIdentity(ident); 13019 } 13020 mStackSupervisor.resumeFocusedStackTopActivityLocked(); 13021 mUserController.sendUserSwitchBroadcastsLocked(-1, currentUserId); 13022 } 13023 } 13024 13025 void killAppAtUsersRequest(ProcessRecord app, Dialog fromDialog) { 13026 synchronized (this) { 13027 mAppErrors.killAppAtUserRequestLocked(app, fromDialog); 13028 } 13029 } 13030 13031 void skipCurrentReceiverLocked(ProcessRecord app) { 13032 for (BroadcastQueue queue : mBroadcastQueues) { 13033 queue.skipCurrentReceiverLocked(app); 13034 } 13035 } 13036 13037 /** 13038 * Used by {@link com.android.internal.os.RuntimeInit} to report when an application crashes. 13039 * The application process will exit immediately after this call returns. 13040 * @param app object of the crashing app, null for the system server 13041 * @param crashInfo describing the exception 13042 */ 13043 public void handleApplicationCrash(IBinder app, ApplicationErrorReport.CrashInfo crashInfo) { 13044 ProcessRecord r = findAppProcess(app, "Crash"); 13045 final String processName = app == null ? "system_server" 13046 : (r == null ? "unknown" : r.processName); 13047 13048 handleApplicationCrashInner("crash", r, processName, crashInfo); 13049 } 13050 13051 /* Native crash reporting uses this inner version because it needs to be somewhat 13052 * decoupled from the AM-managed cleanup lifecycle 13053 */ 13054 void handleApplicationCrashInner(String eventType, ProcessRecord r, String processName, 13055 ApplicationErrorReport.CrashInfo crashInfo) { 13056 EventLog.writeEvent(EventLogTags.AM_CRASH, Binder.getCallingPid(), 13057 UserHandle.getUserId(Binder.getCallingUid()), processName, 13058 r == null ? -1 : r.info.flags, 13059 crashInfo.exceptionClassName, 13060 crashInfo.exceptionMessage, 13061 crashInfo.throwFileName, 13062 crashInfo.throwLineNumber); 13063 13064 addErrorToDropBox(eventType, r, processName, null, null, null, null, null, crashInfo); 13065 13066 mAppErrors.crashApplication(r, crashInfo); 13067 } 13068 13069 public void handleApplicationStrictModeViolation( 13070 IBinder app, 13071 int violationMask, 13072 StrictMode.ViolationInfo info) { 13073 ProcessRecord r = findAppProcess(app, "StrictMode"); 13074 if (r == null) { 13075 return; 13076 } 13077 13078 if ((violationMask & StrictMode.PENALTY_DROPBOX) != 0) { 13079 Integer stackFingerprint = info.hashCode(); 13080 boolean logIt = true; 13081 synchronized (mAlreadyLoggedViolatedStacks) { 13082 if (mAlreadyLoggedViolatedStacks.contains(stackFingerprint)) { 13083 logIt = false; 13084 // TODO: sub-sample into EventLog for these, with 13085 // the info.durationMillis? Then we'd get 13086 // the relative pain numbers, without logging all 13087 // the stack traces repeatedly. We'd want to do 13088 // likewise in the client code, which also does 13089 // dup suppression, before the Binder call. 13090 } else { 13091 if (mAlreadyLoggedViolatedStacks.size() >= MAX_DUP_SUPPRESSED_STACKS) { 13092 mAlreadyLoggedViolatedStacks.clear(); 13093 } 13094 mAlreadyLoggedViolatedStacks.add(stackFingerprint); 13095 } 13096 } 13097 if (logIt) { 13098 logStrictModeViolationToDropBox(r, info); 13099 } 13100 } 13101 13102 if ((violationMask & StrictMode.PENALTY_DIALOG) != 0) { 13103 AppErrorResult result = new AppErrorResult(); 13104 synchronized (this) { 13105 final long origId = Binder.clearCallingIdentity(); 13106 13107 Message msg = Message.obtain(); 13108 msg.what = SHOW_STRICT_MODE_VIOLATION_UI_MSG; 13109 HashMap<String, Object> data = new HashMap<String, Object>(); 13110 data.put("result", result); 13111 data.put("app", r); 13112 data.put("violationMask", violationMask); 13113 data.put("info", info); 13114 msg.obj = data; 13115 mUiHandler.sendMessage(msg); 13116 13117 Binder.restoreCallingIdentity(origId); 13118 } 13119 int res = result.get(); 13120 Slog.w(TAG, "handleApplicationStrictModeViolation; res=" + res); 13121 } 13122 } 13123 13124 // Depending on the policy in effect, there could be a bunch of 13125 // these in quick succession so we try to batch these together to 13126 // minimize disk writes, number of dropbox entries, and maximize 13127 // compression, by having more fewer, larger records. 13128 private void logStrictModeViolationToDropBox( 13129 ProcessRecord process, 13130 StrictMode.ViolationInfo info) { 13131 if (info == null) { 13132 return; 13133 } 13134 final boolean isSystemApp = process == null || 13135 (process.info.flags & (ApplicationInfo.FLAG_SYSTEM | 13136 ApplicationInfo.FLAG_UPDATED_SYSTEM_APP)) != 0; 13137 final String processName = process == null ? "unknown" : process.processName; 13138 final String dropboxTag = isSystemApp ? "system_app_strictmode" : "data_app_strictmode"; 13139 final DropBoxManager dbox = (DropBoxManager) 13140 mContext.getSystemService(Context.DROPBOX_SERVICE); 13141 13142 // Exit early if the dropbox isn't configured to accept this report type. 13143 if (dbox == null || !dbox.isTagEnabled(dropboxTag)) return; 13144 13145 boolean bufferWasEmpty; 13146 boolean needsFlush; 13147 final StringBuilder sb = isSystemApp ? mStrictModeBuffer : new StringBuilder(1024); 13148 synchronized (sb) { 13149 bufferWasEmpty = sb.length() == 0; 13150 appendDropBoxProcessHeaders(process, processName, sb); 13151 sb.append("Build: ").append(Build.FINGERPRINT).append("\n"); 13152 sb.append("System-App: ").append(isSystemApp).append("\n"); 13153 sb.append("Uptime-Millis: ").append(info.violationUptimeMillis).append("\n"); 13154 if (info.violationNumThisLoop != 0) { 13155 sb.append("Loop-Violation-Number: ").append(info.violationNumThisLoop).append("\n"); 13156 } 13157 if (info.numAnimationsRunning != 0) { 13158 sb.append("Animations-Running: ").append(info.numAnimationsRunning).append("\n"); 13159 } 13160 if (info.broadcastIntentAction != null) { 13161 sb.append("Broadcast-Intent-Action: ").append(info.broadcastIntentAction).append("\n"); 13162 } 13163 if (info.durationMillis != -1) { 13164 sb.append("Duration-Millis: ").append(info.durationMillis).append("\n"); 13165 } 13166 if (info.numInstances != -1) { 13167 sb.append("Instance-Count: ").append(info.numInstances).append("\n"); 13168 } 13169 if (info.tags != null) { 13170 for (String tag : info.tags) { 13171 sb.append("Span-Tag: ").append(tag).append("\n"); 13172 } 13173 } 13174 sb.append("\n"); 13175 if (info.crashInfo != null && info.crashInfo.stackTrace != null) { 13176 sb.append(info.crashInfo.stackTrace); 13177 sb.append("\n"); 13178 } 13179 if (info.message != null) { 13180 sb.append(info.message); 13181 sb.append("\n"); 13182 } 13183 13184 // Only buffer up to ~64k. Various logging bits truncate 13185 // things at 128k. 13186 needsFlush = (sb.length() > 64 * 1024); 13187 } 13188 13189 // Flush immediately if the buffer's grown too large, or this 13190 // is a non-system app. Non-system apps are isolated with a 13191 // different tag & policy and not batched. 13192 // 13193 // Batching is useful during internal testing with 13194 // StrictMode settings turned up high. Without batching, 13195 // thousands of separate files could be created on boot. 13196 if (!isSystemApp || needsFlush) { 13197 new Thread("Error dump: " + dropboxTag) { 13198 @Override 13199 public void run() { 13200 String report; 13201 synchronized (sb) { 13202 report = sb.toString(); 13203 sb.delete(0, sb.length()); 13204 sb.trimToSize(); 13205 } 13206 if (report.length() != 0) { 13207 dbox.addText(dropboxTag, report); 13208 } 13209 } 13210 }.start(); 13211 return; 13212 } 13213 13214 // System app batching: 13215 if (!bufferWasEmpty) { 13216 // An existing dropbox-writing thread is outstanding, so 13217 // we don't need to start it up. The existing thread will 13218 // catch the buffer appends we just did. 13219 return; 13220 } 13221 13222 // Worker thread to both batch writes and to avoid blocking the caller on I/O. 13223 // (After this point, we shouldn't access AMS internal data structures.) 13224 new Thread("Error dump: " + dropboxTag) { 13225 @Override 13226 public void run() { 13227 // 5 second sleep to let stacks arrive and be batched together 13228 try { 13229 Thread.sleep(5000); // 5 seconds 13230 } catch (InterruptedException e) {} 13231 13232 String errorReport; 13233 synchronized (mStrictModeBuffer) { 13234 errorReport = mStrictModeBuffer.toString(); 13235 if (errorReport.length() == 0) { 13236 return; 13237 } 13238 mStrictModeBuffer.delete(0, mStrictModeBuffer.length()); 13239 mStrictModeBuffer.trimToSize(); 13240 } 13241 dbox.addText(dropboxTag, errorReport); 13242 } 13243 }.start(); 13244 } 13245 13246 /** 13247 * Used by {@link Log} via {@link com.android.internal.os.RuntimeInit} to report serious errors. 13248 * @param app object of the crashing app, null for the system server 13249 * @param tag reported by the caller 13250 * @param system whether this wtf is coming from the system 13251 * @param crashInfo describing the context of the error 13252 * @return true if the process should exit immediately (WTF is fatal) 13253 */ 13254 public boolean handleApplicationWtf(final IBinder app, final String tag, boolean system, 13255 final ApplicationErrorReport.CrashInfo crashInfo) { 13256 final int callingUid = Binder.getCallingUid(); 13257 final int callingPid = Binder.getCallingPid(); 13258 13259 if (system) { 13260 // If this is coming from the system, we could very well have low-level 13261 // system locks held, so we want to do this all asynchronously. And we 13262 // never want this to become fatal, so there is that too. 13263 mHandler.post(new Runnable() { 13264 @Override public void run() { 13265 handleApplicationWtfInner(callingUid, callingPid, app, tag, crashInfo); 13266 } 13267 }); 13268 return false; 13269 } 13270 13271 final ProcessRecord r = handleApplicationWtfInner(callingUid, callingPid, app, tag, 13272 crashInfo); 13273 13274 if (r != null && r.pid != Process.myPid() && 13275 Settings.Global.getInt(mContext.getContentResolver(), 13276 Settings.Global.WTF_IS_FATAL, 0) != 0) { 13277 mAppErrors.crashApplication(r, crashInfo); 13278 return true; 13279 } else { 13280 return false; 13281 } 13282 } 13283 13284 ProcessRecord handleApplicationWtfInner(int callingUid, int callingPid, IBinder app, String tag, 13285 final ApplicationErrorReport.CrashInfo crashInfo) { 13286 final ProcessRecord r = findAppProcess(app, "WTF"); 13287 final String processName = app == null ? "system_server" 13288 : (r == null ? "unknown" : r.processName); 13289 13290 EventLog.writeEvent(EventLogTags.AM_WTF, UserHandle.getUserId(callingUid), callingPid, 13291 processName, r == null ? -1 : r.info.flags, tag, crashInfo.exceptionMessage); 13292 13293 addErrorToDropBox("wtf", r, processName, null, null, tag, null, null, crashInfo); 13294 13295 return r; 13296 } 13297 13298 /** 13299 * @param app object of some object (as stored in {@link com.android.internal.os.RuntimeInit}) 13300 * @return the corresponding {@link ProcessRecord} object, or null if none could be found 13301 */ 13302 private ProcessRecord findAppProcess(IBinder app, String reason) { 13303 if (app == null) { 13304 return null; 13305 } 13306 13307 synchronized (this) { 13308 final int NP = mProcessNames.getMap().size(); 13309 for (int ip=0; ip<NP; ip++) { 13310 SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 13311 final int NA = apps.size(); 13312 for (int ia=0; ia<NA; ia++) { 13313 ProcessRecord p = apps.valueAt(ia); 13314 if (p.thread != null && p.thread.asBinder() == app) { 13315 return p; 13316 } 13317 } 13318 } 13319 13320 Slog.w(TAG, "Can't find mystery application for " + reason 13321 + " from pid=" + Binder.getCallingPid() 13322 + " uid=" + Binder.getCallingUid() + ": " + app); 13323 return null; 13324 } 13325 } 13326 13327 /** 13328 * Utility function for addErrorToDropBox and handleStrictModeViolation's logging 13329 * to append various headers to the dropbox log text. 13330 */ 13331 private void appendDropBoxProcessHeaders(ProcessRecord process, String processName, 13332 StringBuilder sb) { 13333 // Watchdog thread ends up invoking this function (with 13334 // a null ProcessRecord) to add the stack file to dropbox. 13335 // Do not acquire a lock on this (am) in such cases, as it 13336 // could cause a potential deadlock, if and when watchdog 13337 // is invoked due to unavailability of lock on am and it 13338 // would prevent watchdog from killing system_server. 13339 if (process == null) { 13340 sb.append("Process: ").append(processName).append("\n"); 13341 return; 13342 } 13343 // Note: ProcessRecord 'process' is guarded by the service 13344 // instance. (notably process.pkgList, which could otherwise change 13345 // concurrently during execution of this method) 13346 synchronized (this) { 13347 sb.append("Process: ").append(processName).append("\n"); 13348 int flags = process.info.flags; 13349 IPackageManager pm = AppGlobals.getPackageManager(); 13350 sb.append("Flags: 0x").append(Integer.toString(flags, 16)).append("\n"); 13351 for (int ip=0; ip<process.pkgList.size(); ip++) { 13352 String pkg = process.pkgList.keyAt(ip); 13353 sb.append("Package: ").append(pkg); 13354 try { 13355 PackageInfo pi = pm.getPackageInfo(pkg, 0, UserHandle.getCallingUserId()); 13356 if (pi != null) { 13357 sb.append(" v").append(pi.versionCode); 13358 if (pi.versionName != null) { 13359 sb.append(" (").append(pi.versionName).append(")"); 13360 } 13361 } 13362 } catch (RemoteException e) { 13363 Slog.e(TAG, "Error getting package info: " + pkg, e); 13364 } 13365 sb.append("\n"); 13366 } 13367 } 13368 } 13369 13370 private static String processClass(ProcessRecord process) { 13371 if (process == null || process.pid == MY_PID) { 13372 return "system_server"; 13373 } else if ((process.info.flags & ApplicationInfo.FLAG_SYSTEM) != 0) { 13374 return "system_app"; 13375 } else { 13376 return "data_app"; 13377 } 13378 } 13379 13380 private volatile long mWtfClusterStart; 13381 private volatile int mWtfClusterCount; 13382 13383 /** 13384 * Write a description of an error (crash, WTF, ANR) to the drop box. 13385 * @param eventType to include in the drop box tag ("crash", "wtf", etc.) 13386 * @param process which caused the error, null means the system server 13387 * @param activity which triggered the error, null if unknown 13388 * @param parent activity related to the error, null if unknown 13389 * @param subject line related to the error, null if absent 13390 * @param report in long form describing the error, null if absent 13391 * @param logFile to include in the report, null if none 13392 * @param crashInfo giving an application stack trace, null if absent 13393 */ 13394 public void addErrorToDropBox(String eventType, 13395 ProcessRecord process, String processName, ActivityRecord activity, 13396 ActivityRecord parent, String subject, 13397 final String report, final File logFile, 13398 final ApplicationErrorReport.CrashInfo crashInfo) { 13399 // NOTE -- this must never acquire the ActivityManagerService lock, 13400 // otherwise the watchdog may be prevented from resetting the system. 13401 13402 final String dropboxTag = processClass(process) + "_" + eventType; 13403 final DropBoxManager dbox = (DropBoxManager) 13404 mContext.getSystemService(Context.DROPBOX_SERVICE); 13405 13406 // Exit early if the dropbox isn't configured to accept this report type. 13407 if (dbox == null || !dbox.isTagEnabled(dropboxTag)) return; 13408 13409 // Rate-limit how often we're willing to do the heavy lifting below to 13410 // collect and record logs; currently 5 logs per 10 second period. 13411 final long now = SystemClock.elapsedRealtime(); 13412 if (now - mWtfClusterStart > 10 * DateUtils.SECOND_IN_MILLIS) { 13413 mWtfClusterStart = now; 13414 mWtfClusterCount = 1; 13415 } else { 13416 if (mWtfClusterCount++ >= 5) return; 13417 } 13418 13419 final StringBuilder sb = new StringBuilder(1024); 13420 appendDropBoxProcessHeaders(process, processName, sb); 13421 if (process != null) { 13422 sb.append("Foreground: ") 13423 .append(process.isInterestingToUserLocked() ? "Yes" : "No") 13424 .append("\n"); 13425 } 13426 if (activity != null) { 13427 sb.append("Activity: ").append(activity.shortComponentName).append("\n"); 13428 } 13429 if (parent != null && parent.app != null && parent.app.pid != process.pid) { 13430 sb.append("Parent-Process: ").append(parent.app.processName).append("\n"); 13431 } 13432 if (parent != null && parent != activity) { 13433 sb.append("Parent-Activity: ").append(parent.shortComponentName).append("\n"); 13434 } 13435 if (subject != null) { 13436 sb.append("Subject: ").append(subject).append("\n"); 13437 } 13438 sb.append("Build: ").append(Build.FINGERPRINT).append("\n"); 13439 if (Debug.isDebuggerConnected()) { 13440 sb.append("Debugger: Connected\n"); 13441 } 13442 sb.append("\n"); 13443 13444 // Do the rest in a worker thread to avoid blocking the caller on I/O 13445 // (After this point, we shouldn't access AMS internal data structures.) 13446 Thread worker = new Thread("Error dump: " + dropboxTag) { 13447 @Override 13448 public void run() { 13449 if (report != null) { 13450 sb.append(report); 13451 } 13452 if (logFile != null) { 13453 try { 13454 sb.append(FileUtils.readTextFile(logFile, DROPBOX_MAX_SIZE, 13455 "\n\n[[TRUNCATED]]")); 13456 } catch (IOException e) { 13457 Slog.e(TAG, "Error reading " + logFile, e); 13458 } 13459 } 13460 if (crashInfo != null && crashInfo.stackTrace != null) { 13461 sb.append(crashInfo.stackTrace); 13462 } 13463 13464 String setting = Settings.Global.ERROR_LOGCAT_PREFIX + dropboxTag; 13465 int lines = Settings.Global.getInt(mContext.getContentResolver(), setting, 0); 13466 if (lines > 0) { 13467 sb.append("\n"); 13468 13469 // Merge several logcat streams, and take the last N lines 13470 InputStreamReader input = null; 13471 try { 13472 java.lang.Process logcat = new ProcessBuilder( 13473 "/system/bin/timeout", "-k", "15s", "10s", 13474 "/system/bin/logcat", "-v", "time", "-b", "events", "-b", "system", 13475 "-b", "main", "-b", "crash", "-t", String.valueOf(lines)) 13476 .redirectErrorStream(true).start(); 13477 13478 try { logcat.getOutputStream().close(); } catch (IOException e) {} 13479 try { logcat.getErrorStream().close(); } catch (IOException e) {} 13480 input = new InputStreamReader(logcat.getInputStream()); 13481 13482 int num; 13483 char[] buf = new char[8192]; 13484 while ((num = input.read(buf)) > 0) sb.append(buf, 0, num); 13485 } catch (IOException e) { 13486 Slog.e(TAG, "Error running logcat", e); 13487 } finally { 13488 if (input != null) try { input.close(); } catch (IOException e) {} 13489 } 13490 } 13491 13492 dbox.addText(dropboxTag, sb.toString()); 13493 } 13494 }; 13495 13496 if (process == null) { 13497 // If process is null, we are being called from some internal code 13498 // and may be about to die -- run this synchronously. 13499 worker.run(); 13500 } else { 13501 worker.start(); 13502 } 13503 } 13504 13505 @Override 13506 public List<ActivityManager.ProcessErrorStateInfo> getProcessesInErrorState() { 13507 enforceNotIsolatedCaller("getProcessesInErrorState"); 13508 // assume our apps are happy - lazy create the list 13509 List<ActivityManager.ProcessErrorStateInfo> errList = null; 13510 13511 final boolean allUsers = ActivityManager.checkUidPermission(INTERACT_ACROSS_USERS_FULL, 13512 Binder.getCallingUid()) == PackageManager.PERMISSION_GRANTED; 13513 int userId = UserHandle.getUserId(Binder.getCallingUid()); 13514 13515 synchronized (this) { 13516 13517 // iterate across all processes 13518 for (int i=mLruProcesses.size()-1; i>=0; i--) { 13519 ProcessRecord app = mLruProcesses.get(i); 13520 if (!allUsers && app.userId != userId) { 13521 continue; 13522 } 13523 if ((app.thread != null) && (app.crashing || app.notResponding)) { 13524 // This one's in trouble, so we'll generate a report for it 13525 // crashes are higher priority (in case there's a crash *and* an anr) 13526 ActivityManager.ProcessErrorStateInfo report = null; 13527 if (app.crashing) { 13528 report = app.crashingReport; 13529 } else if (app.notResponding) { 13530 report = app.notRespondingReport; 13531 } 13532 13533 if (report != null) { 13534 if (errList == null) { 13535 errList = new ArrayList<ActivityManager.ProcessErrorStateInfo>(1); 13536 } 13537 errList.add(report); 13538 } else { 13539 Slog.w(TAG, "Missing app error report, app = " + app.processName + 13540 " crashing = " + app.crashing + 13541 " notResponding = " + app.notResponding); 13542 } 13543 } 13544 } 13545 } 13546 13547 return errList; 13548 } 13549 13550 static int procStateToImportance(int procState, int memAdj, 13551 ActivityManager.RunningAppProcessInfo currApp) { 13552 int imp = ActivityManager.RunningAppProcessInfo.procStateToImportance(procState); 13553 if (imp == ActivityManager.RunningAppProcessInfo.IMPORTANCE_BACKGROUND) { 13554 currApp.lru = memAdj; 13555 } else { 13556 currApp.lru = 0; 13557 } 13558 return imp; 13559 } 13560 13561 private void fillInProcMemInfo(ProcessRecord app, 13562 ActivityManager.RunningAppProcessInfo outInfo) { 13563 outInfo.pid = app.pid; 13564 outInfo.uid = app.info.uid; 13565 if (mHeavyWeightProcess == app) { 13566 outInfo.flags |= ActivityManager.RunningAppProcessInfo.FLAG_CANT_SAVE_STATE; 13567 } 13568 if (app.persistent) { 13569 outInfo.flags |= ActivityManager.RunningAppProcessInfo.FLAG_PERSISTENT; 13570 } 13571 if (app.activities.size() > 0) { 13572 outInfo.flags |= ActivityManager.RunningAppProcessInfo.FLAG_HAS_ACTIVITIES; 13573 } 13574 outInfo.lastTrimLevel = app.trimMemoryLevel; 13575 int adj = app.curAdj; 13576 int procState = app.curProcState; 13577 outInfo.importance = procStateToImportance(procState, adj, outInfo); 13578 outInfo.importanceReasonCode = app.adjTypeCode; 13579 outInfo.processState = app.curProcState; 13580 } 13581 13582 @Override 13583 public List<ActivityManager.RunningAppProcessInfo> getRunningAppProcesses() { 13584 enforceNotIsolatedCaller("getRunningAppProcesses"); 13585 13586 final int callingUid = Binder.getCallingUid(); 13587 13588 // Lazy instantiation of list 13589 List<ActivityManager.RunningAppProcessInfo> runList = null; 13590 final boolean allUsers = ActivityManager.checkUidPermission(INTERACT_ACROSS_USERS_FULL, 13591 callingUid) == PackageManager.PERMISSION_GRANTED; 13592 final int userId = UserHandle.getUserId(callingUid); 13593 final boolean allUids = isGetTasksAllowed( 13594 "getRunningAppProcesses", Binder.getCallingPid(), callingUid); 13595 13596 synchronized (this) { 13597 // Iterate across all processes 13598 for (int i = mLruProcesses.size() - 1; i >= 0; i--) { 13599 ProcessRecord app = mLruProcesses.get(i); 13600 if ((!allUsers && app.userId != userId) 13601 || (!allUids && app.uid != callingUid)) { 13602 continue; 13603 } 13604 if ((app.thread != null) && (!app.crashing && !app.notResponding)) { 13605 // Generate process state info for running application 13606 ActivityManager.RunningAppProcessInfo currApp = 13607 new ActivityManager.RunningAppProcessInfo(app.processName, 13608 app.pid, app.getPackageList()); 13609 fillInProcMemInfo(app, currApp); 13610 if (app.adjSource instanceof ProcessRecord) { 13611 currApp.importanceReasonPid = ((ProcessRecord)app.adjSource).pid; 13612 currApp.importanceReasonImportance = 13613 ActivityManager.RunningAppProcessInfo.procStateToImportance( 13614 app.adjSourceProcState); 13615 } else if (app.adjSource instanceof ActivityRecord) { 13616 ActivityRecord r = (ActivityRecord)app.adjSource; 13617 if (r.app != null) currApp.importanceReasonPid = r.app.pid; 13618 } 13619 if (app.adjTarget instanceof ComponentName) { 13620 currApp.importanceReasonComponent = (ComponentName)app.adjTarget; 13621 } 13622 //Slog.v(TAG, "Proc " + app.processName + ": imp=" + currApp.importance 13623 // + " lru=" + currApp.lru); 13624 if (runList == null) { 13625 runList = new ArrayList<>(); 13626 } 13627 runList.add(currApp); 13628 } 13629 } 13630 } 13631 return runList; 13632 } 13633 13634 @Override 13635 public List<ApplicationInfo> getRunningExternalApplications() { 13636 enforceNotIsolatedCaller("getRunningExternalApplications"); 13637 List<ActivityManager.RunningAppProcessInfo> runningApps = getRunningAppProcesses(); 13638 List<ApplicationInfo> retList = new ArrayList<ApplicationInfo>(); 13639 if (runningApps != null && runningApps.size() > 0) { 13640 Set<String> extList = new HashSet<String>(); 13641 for (ActivityManager.RunningAppProcessInfo app : runningApps) { 13642 if (app.pkgList != null) { 13643 for (String pkg : app.pkgList) { 13644 extList.add(pkg); 13645 } 13646 } 13647 } 13648 IPackageManager pm = AppGlobals.getPackageManager(); 13649 for (String pkg : extList) { 13650 try { 13651 ApplicationInfo info = pm.getApplicationInfo(pkg, 0, UserHandle.getCallingUserId()); 13652 if ((info.flags & ApplicationInfo.FLAG_EXTERNAL_STORAGE) != 0) { 13653 retList.add(info); 13654 } 13655 } catch (RemoteException e) { 13656 } 13657 } 13658 } 13659 return retList; 13660 } 13661 13662 @Override 13663 public void getMyMemoryState(ActivityManager.RunningAppProcessInfo outInfo) { 13664 enforceNotIsolatedCaller("getMyMemoryState"); 13665 synchronized (this) { 13666 ProcessRecord proc; 13667 synchronized (mPidsSelfLocked) { 13668 proc = mPidsSelfLocked.get(Binder.getCallingPid()); 13669 } 13670 fillInProcMemInfo(proc, outInfo); 13671 } 13672 } 13673 13674 @Override 13675 public int getMemoryTrimLevel() { 13676 enforceNotIsolatedCaller("getMyMemoryState"); 13677 synchronized (this) { 13678 return mLastMemoryLevel; 13679 } 13680 } 13681 13682 @Override 13683 public void onShellCommand(FileDescriptor in, FileDescriptor out, 13684 FileDescriptor err, String[] args, ResultReceiver resultReceiver) { 13685 (new ActivityManagerShellCommand(this, false)).exec( 13686 this, in, out, err, args, resultReceiver); 13687 } 13688 13689 @Override 13690 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 13691 if (checkCallingPermission(android.Manifest.permission.DUMP) 13692 != PackageManager.PERMISSION_GRANTED) { 13693 pw.println("Permission Denial: can't dump ActivityManager from from pid=" 13694 + Binder.getCallingPid() 13695 + ", uid=" + Binder.getCallingUid() 13696 + " without permission " 13697 + android.Manifest.permission.DUMP); 13698 return; 13699 } 13700 13701 boolean dumpAll = false; 13702 boolean dumpClient = false; 13703 String dumpPackage = null; 13704 13705 int opti = 0; 13706 while (opti < args.length) { 13707 String opt = args[opti]; 13708 if (opt == null || opt.length() <= 0 || opt.charAt(0) != '-') { 13709 break; 13710 } 13711 opti++; 13712 if ("-a".equals(opt)) { 13713 dumpAll = true; 13714 } else if ("-c".equals(opt)) { 13715 dumpClient = true; 13716 } else if ("-p".equals(opt)) { 13717 if (opti < args.length) { 13718 dumpPackage = args[opti]; 13719 opti++; 13720 } else { 13721 pw.println("Error: -p option requires package argument"); 13722 return; 13723 } 13724 dumpClient = true; 13725 } else if ("-h".equals(opt)) { 13726 ActivityManagerShellCommand.dumpHelp(pw, true); 13727 return; 13728 } else { 13729 pw.println("Unknown argument: " + opt + "; use -h for help"); 13730 } 13731 } 13732 13733 long origId = Binder.clearCallingIdentity(); 13734 boolean more = false; 13735 // Is the caller requesting to dump a particular piece of data? 13736 if (opti < args.length) { 13737 String cmd = args[opti]; 13738 opti++; 13739 if ("activities".equals(cmd) || "a".equals(cmd)) { 13740 synchronized (this) { 13741 dumpActivitiesLocked(fd, pw, args, opti, true, dumpClient, dumpPackage); 13742 } 13743 } else if ("recents".equals(cmd) || "r".equals(cmd)) { 13744 synchronized (this) { 13745 dumpRecentsLocked(fd, pw, args, opti, true, dumpPackage); 13746 } 13747 } else if ("broadcasts".equals(cmd) || "b".equals(cmd)) { 13748 String[] newArgs; 13749 String name; 13750 if (opti >= args.length) { 13751 name = null; 13752 newArgs = EMPTY_STRING_ARRAY; 13753 } else { 13754 dumpPackage = args[opti]; 13755 opti++; 13756 newArgs = new String[args.length - opti]; 13757 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 13758 args.length - opti); 13759 } 13760 synchronized (this) { 13761 dumpBroadcastsLocked(fd, pw, args, opti, true, dumpPackage); 13762 } 13763 } else if ("intents".equals(cmd) || "i".equals(cmd)) { 13764 String[] newArgs; 13765 String name; 13766 if (opti >= args.length) { 13767 name = null; 13768 newArgs = EMPTY_STRING_ARRAY; 13769 } else { 13770 dumpPackage = args[opti]; 13771 opti++; 13772 newArgs = new String[args.length - opti]; 13773 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 13774 args.length - opti); 13775 } 13776 synchronized (this) { 13777 dumpPendingIntentsLocked(fd, pw, args, opti, true, dumpPackage); 13778 } 13779 } else if ("processes".equals(cmd) || "p".equals(cmd)) { 13780 String[] newArgs; 13781 String name; 13782 if (opti >= args.length) { 13783 name = null; 13784 newArgs = EMPTY_STRING_ARRAY; 13785 } else { 13786 dumpPackage = args[opti]; 13787 opti++; 13788 newArgs = new String[args.length - opti]; 13789 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 13790 args.length - opti); 13791 } 13792 synchronized (this) { 13793 dumpProcessesLocked(fd, pw, args, opti, true, dumpPackage); 13794 } 13795 } else if ("oom".equals(cmd) || "o".equals(cmd)) { 13796 synchronized (this) { 13797 dumpOomLocked(fd, pw, args, opti, true); 13798 } 13799 } else if ("permissions".equals(cmd) || "perm".equals(cmd)) { 13800 synchronized (this) { 13801 dumpPermissionsLocked(fd, pw, args, opti, true, null); 13802 } 13803 } else if ("provider".equals(cmd)) { 13804 String[] newArgs; 13805 String name; 13806 if (opti >= args.length) { 13807 name = null; 13808 newArgs = EMPTY_STRING_ARRAY; 13809 } else { 13810 name = args[opti]; 13811 opti++; 13812 newArgs = new String[args.length - opti]; 13813 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, args.length - opti); 13814 } 13815 if (!dumpProvider(fd, pw, name, newArgs, 0, dumpAll)) { 13816 pw.println("No providers match: " + name); 13817 pw.println("Use -h for help."); 13818 } 13819 } else if ("providers".equals(cmd) || "prov".equals(cmd)) { 13820 synchronized (this) { 13821 dumpProvidersLocked(fd, pw, args, opti, true, null); 13822 } 13823 } else if ("service".equals(cmd)) { 13824 String[] newArgs; 13825 String name; 13826 if (opti >= args.length) { 13827 name = null; 13828 newArgs = EMPTY_STRING_ARRAY; 13829 } else { 13830 name = args[opti]; 13831 opti++; 13832 newArgs = new String[args.length - opti]; 13833 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 13834 args.length - opti); 13835 } 13836 if (!mServices.dumpService(fd, pw, name, newArgs, 0, dumpAll)) { 13837 pw.println("No services match: " + name); 13838 pw.println("Use -h for help."); 13839 } 13840 } else if ("package".equals(cmd)) { 13841 String[] newArgs; 13842 if (opti >= args.length) { 13843 pw.println("package: no package name specified"); 13844 pw.println("Use -h for help."); 13845 } else { 13846 dumpPackage = args[opti]; 13847 opti++; 13848 newArgs = new String[args.length - opti]; 13849 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 13850 args.length - opti); 13851 args = newArgs; 13852 opti = 0; 13853 more = true; 13854 } 13855 } else if ("associations".equals(cmd) || "as".equals(cmd)) { 13856 synchronized (this) { 13857 dumpAssociationsLocked(fd, pw, args, opti, true, dumpClient, dumpPackage); 13858 } 13859 } else if ("services".equals(cmd) || "s".equals(cmd)) { 13860 if (dumpClient) { 13861 ActiveServices.ServiceDumper dumper; 13862 synchronized (this) { 13863 dumper = mServices.newServiceDumperLocked(fd, pw, args, opti, true, 13864 dumpPackage); 13865 } 13866 dumper.dumpWithClient(); 13867 } else { 13868 synchronized (this) { 13869 mServices.newServiceDumperLocked(fd, pw, args, opti, true, 13870 dumpPackage).dumpLocked(); 13871 } 13872 } 13873 } else if ("locks".equals(cmd)) { 13874 LockGuard.dump(fd, pw, args); 13875 } else { 13876 // Dumping a single activity? 13877 if (!dumpActivity(fd, pw, cmd, args, opti, dumpAll)) { 13878 ActivityManagerShellCommand shell = new ActivityManagerShellCommand(this, true); 13879 int res = shell.exec(this, null, fd, null, args, new ResultReceiver(null)); 13880 if (res < 0) { 13881 pw.println("Bad activity command, or no activities match: " + cmd); 13882 pw.println("Use -h for help."); 13883 } 13884 } 13885 } 13886 if (!more) { 13887 Binder.restoreCallingIdentity(origId); 13888 return; 13889 } 13890 } 13891 13892 // No piece of data specified, dump everything. 13893 if (dumpClient) { 13894 ActiveServices.ServiceDumper sdumper; 13895 synchronized (this) { 13896 dumpPendingIntentsLocked(fd, pw, args, opti, dumpAll, dumpPackage); 13897 pw.println(); 13898 if (dumpAll) { 13899 pw.println("-------------------------------------------------------------------------------"); 13900 } 13901 dumpBroadcastsLocked(fd, pw, args, opti, dumpAll, dumpPackage); 13902 pw.println(); 13903 if (dumpAll) { 13904 pw.println("-------------------------------------------------------------------------------"); 13905 } 13906 dumpProvidersLocked(fd, pw, args, opti, dumpAll, dumpPackage); 13907 pw.println(); 13908 if (dumpAll) { 13909 pw.println("-------------------------------------------------------------------------------"); 13910 } 13911 dumpPermissionsLocked(fd, pw, args, opti, dumpAll, dumpPackage); 13912 pw.println(); 13913 if (dumpAll) { 13914 pw.println("-------------------------------------------------------------------------------"); 13915 } 13916 sdumper = mServices.newServiceDumperLocked(fd, pw, args, opti, dumpAll, 13917 dumpPackage); 13918 } 13919 sdumper.dumpWithClient(); 13920 pw.println(); 13921 synchronized (this) { 13922 if (dumpAll) { 13923 pw.println("-------------------------------------------------------------------------------"); 13924 } 13925 dumpRecentsLocked(fd, pw, args, opti, dumpAll, dumpPackage); 13926 pw.println(); 13927 if (dumpAll) { 13928 pw.println("-------------------------------------------------------------------------------"); 13929 } 13930 dumpActivitiesLocked(fd, pw, args, opti, dumpAll, dumpClient, dumpPackage); 13931 if (mAssociations.size() > 0) { 13932 pw.println(); 13933 if (dumpAll) { 13934 pw.println("-------------------------------------------------------------------------------"); 13935 } 13936 dumpAssociationsLocked(fd, pw, args, opti, dumpAll, dumpClient, dumpPackage); 13937 } 13938 pw.println(); 13939 if (dumpAll) { 13940 pw.println("-------------------------------------------------------------------------------"); 13941 } 13942 dumpProcessesLocked(fd, pw, args, opti, dumpAll, dumpPackage); 13943 } 13944 13945 } else { 13946 synchronized (this) { 13947 dumpPendingIntentsLocked(fd, pw, args, opti, dumpAll, dumpPackage); 13948 pw.println(); 13949 if (dumpAll) { 13950 pw.println("-------------------------------------------------------------------------------"); 13951 } 13952 dumpBroadcastsLocked(fd, pw, args, opti, dumpAll, dumpPackage); 13953 pw.println(); 13954 if (dumpAll) { 13955 pw.println("-------------------------------------------------------------------------------"); 13956 } 13957 dumpProvidersLocked(fd, pw, args, opti, dumpAll, dumpPackage); 13958 pw.println(); 13959 if (dumpAll) { 13960 pw.println("-------------------------------------------------------------------------------"); 13961 } 13962 dumpPermissionsLocked(fd, pw, args, opti, dumpAll, dumpPackage); 13963 pw.println(); 13964 if (dumpAll) { 13965 pw.println("-------------------------------------------------------------------------------"); 13966 } 13967 mServices.newServiceDumperLocked(fd, pw, args, opti, dumpAll, dumpPackage) 13968 .dumpLocked(); 13969 pw.println(); 13970 if (dumpAll) { 13971 pw.println("-------------------------------------------------------------------------------"); 13972 } 13973 dumpRecentsLocked(fd, pw, args, opti, dumpAll, dumpPackage); 13974 pw.println(); 13975 if (dumpAll) { 13976 pw.println("-------------------------------------------------------------------------------"); 13977 } 13978 dumpActivitiesLocked(fd, pw, args, opti, dumpAll, dumpClient, dumpPackage); 13979 if (mAssociations.size() > 0) { 13980 pw.println(); 13981 if (dumpAll) { 13982 pw.println("-------------------------------------------------------------------------------"); 13983 } 13984 dumpAssociationsLocked(fd, pw, args, opti, dumpAll, dumpClient, dumpPackage); 13985 } 13986 pw.println(); 13987 if (dumpAll) { 13988 pw.println("-------------------------------------------------------------------------------"); 13989 } 13990 dumpProcessesLocked(fd, pw, args, opti, dumpAll, dumpPackage); 13991 } 13992 } 13993 Binder.restoreCallingIdentity(origId); 13994 } 13995 13996 void dumpActivitiesLocked(FileDescriptor fd, PrintWriter pw, String[] args, 13997 int opti, boolean dumpAll, boolean dumpClient, String dumpPackage) { 13998 pw.println("ACTIVITY MANAGER ACTIVITIES (dumpsys activity activities)"); 13999 14000 boolean printedAnything = mStackSupervisor.dumpActivitiesLocked(fd, pw, dumpAll, dumpClient, 14001 dumpPackage); 14002 boolean needSep = printedAnything; 14003 14004 boolean printed = ActivityStackSupervisor.printThisActivity(pw, mFocusedActivity, 14005 dumpPackage, needSep, " mFocusedActivity: "); 14006 if (printed) { 14007 printedAnything = true; 14008 needSep = false; 14009 } 14010 14011 if (dumpPackage == null) { 14012 if (needSep) { 14013 pw.println(); 14014 } 14015 needSep = true; 14016 printedAnything = true; 14017 mStackSupervisor.dump(pw, " "); 14018 } 14019 14020 if (!printedAnything) { 14021 pw.println(" (nothing)"); 14022 } 14023 } 14024 14025 void dumpRecentsLocked(FileDescriptor fd, PrintWriter pw, String[] args, 14026 int opti, boolean dumpAll, String dumpPackage) { 14027 pw.println("ACTIVITY MANAGER RECENT TASKS (dumpsys activity recents)"); 14028 14029 boolean printedAnything = false; 14030 14031 if (mRecentTasks != null && mRecentTasks.size() > 0) { 14032 boolean printedHeader = false; 14033 14034 final int N = mRecentTasks.size(); 14035 for (int i=0; i<N; i++) { 14036 TaskRecord tr = mRecentTasks.get(i); 14037 if (dumpPackage != null) { 14038 if (tr.realActivity == null || 14039 !dumpPackage.equals(tr.realActivity)) { 14040 continue; 14041 } 14042 } 14043 if (!printedHeader) { 14044 pw.println(" Recent tasks:"); 14045 printedHeader = true; 14046 printedAnything = true; 14047 } 14048 pw.print(" * Recent #"); pw.print(i); pw.print(": "); 14049 pw.println(tr); 14050 if (dumpAll) { 14051 mRecentTasks.get(i).dump(pw, " "); 14052 } 14053 } 14054 } 14055 14056 if (!printedAnything) { 14057 pw.println(" (nothing)"); 14058 } 14059 } 14060 14061 void dumpAssociationsLocked(FileDescriptor fd, PrintWriter pw, String[] args, 14062 int opti, boolean dumpAll, boolean dumpClient, String dumpPackage) { 14063 pw.println("ACTIVITY MANAGER ASSOCIATIONS (dumpsys activity associations)"); 14064 14065 int dumpUid = 0; 14066 if (dumpPackage != null) { 14067 IPackageManager pm = AppGlobals.getPackageManager(); 14068 try { 14069 dumpUid = pm.getPackageUid(dumpPackage, MATCH_UNINSTALLED_PACKAGES, 0); 14070 } catch (RemoteException e) { 14071 } 14072 } 14073 14074 boolean printedAnything = false; 14075 14076 final long now = SystemClock.uptimeMillis(); 14077 14078 for (int i1=0, N1=mAssociations.size(); i1<N1; i1++) { 14079 ArrayMap<ComponentName, SparseArray<ArrayMap<String, Association>>> targetComponents 14080 = mAssociations.valueAt(i1); 14081 for (int i2=0, N2=targetComponents.size(); i2<N2; i2++) { 14082 SparseArray<ArrayMap<String, Association>> sourceUids 14083 = targetComponents.valueAt(i2); 14084 for (int i3=0, N3=sourceUids.size(); i3<N3; i3++) { 14085 ArrayMap<String, Association> sourceProcesses = sourceUids.valueAt(i3); 14086 for (int i4=0, N4=sourceProcesses.size(); i4<N4; i4++) { 14087 Association ass = sourceProcesses.valueAt(i4); 14088 if (dumpPackage != null) { 14089 if (!ass.mTargetComponent.getPackageName().equals(dumpPackage) 14090 && UserHandle.getAppId(ass.mSourceUid) != dumpUid) { 14091 continue; 14092 } 14093 } 14094 printedAnything = true; 14095 pw.print(" "); 14096 pw.print(ass.mTargetProcess); 14097 pw.print("/"); 14098 UserHandle.formatUid(pw, ass.mTargetUid); 14099 pw.print(" <- "); 14100 pw.print(ass.mSourceProcess); 14101 pw.print("/"); 14102 UserHandle.formatUid(pw, ass.mSourceUid); 14103 pw.println(); 14104 pw.print(" via "); 14105 pw.print(ass.mTargetComponent.flattenToShortString()); 14106 pw.println(); 14107 pw.print(" "); 14108 long dur = ass.mTime; 14109 if (ass.mNesting > 0) { 14110 dur += now - ass.mStartTime; 14111 } 14112 TimeUtils.formatDuration(dur, pw); 14113 pw.print(" ("); 14114 pw.print(ass.mCount); 14115 pw.print(" times)"); 14116 pw.print(" "); 14117 for (int i=0; i<ass.mStateTimes.length; i++) { 14118 long amt = ass.mStateTimes[i]; 14119 if (ass.mLastState-ActivityManager.MIN_PROCESS_STATE == i) { 14120 amt += now - ass.mLastStateUptime; 14121 } 14122 if (amt != 0) { 14123 pw.print(" "); 14124 pw.print(ProcessList.makeProcStateString( 14125 i + ActivityManager.MIN_PROCESS_STATE)); 14126 pw.print("="); 14127 TimeUtils.formatDuration(amt, pw); 14128 if (ass.mLastState-ActivityManager.MIN_PROCESS_STATE == i) { 14129 pw.print("*"); 14130 } 14131 } 14132 } 14133 pw.println(); 14134 if (ass.mNesting > 0) { 14135 pw.print(" Currently active: "); 14136 TimeUtils.formatDuration(now - ass.mStartTime, pw); 14137 pw.println(); 14138 } 14139 } 14140 } 14141 } 14142 14143 } 14144 14145 if (!printedAnything) { 14146 pw.println(" (nothing)"); 14147 } 14148 } 14149 14150 boolean dumpUids(PrintWriter pw, String dumpPackage, SparseArray<UidRecord> uids, 14151 String header, boolean needSep) { 14152 boolean printed = false; 14153 int whichAppId = -1; 14154 if (dumpPackage != null) { 14155 try { 14156 ApplicationInfo info = mContext.getPackageManager().getApplicationInfo( 14157 dumpPackage, 0); 14158 whichAppId = UserHandle.getAppId(info.uid); 14159 } catch (NameNotFoundException e) { 14160 e.printStackTrace(); 14161 } 14162 } 14163 for (int i=0; i<uids.size(); i++) { 14164 UidRecord uidRec = uids.valueAt(i); 14165 if (dumpPackage != null && UserHandle.getAppId(uidRec.uid) != whichAppId) { 14166 continue; 14167 } 14168 if (!printed) { 14169 printed = true; 14170 if (needSep) { 14171 pw.println(); 14172 } 14173 pw.print(" "); 14174 pw.println(header); 14175 needSep = true; 14176 } 14177 pw.print(" UID "); UserHandle.formatUid(pw, uidRec.uid); 14178 pw.print(": "); pw.println(uidRec); 14179 } 14180 return printed; 14181 } 14182 14183 void dumpProcessesLocked(FileDescriptor fd, PrintWriter pw, String[] args, 14184 int opti, boolean dumpAll, String dumpPackage) { 14185 boolean needSep = false; 14186 boolean printedAnything = false; 14187 int numPers = 0; 14188 14189 pw.println("ACTIVITY MANAGER RUNNING PROCESSES (dumpsys activity processes)"); 14190 14191 if (dumpAll) { 14192 final int NP = mProcessNames.getMap().size(); 14193 for (int ip=0; ip<NP; ip++) { 14194 SparseArray<ProcessRecord> procs = mProcessNames.getMap().valueAt(ip); 14195 final int NA = procs.size(); 14196 for (int ia=0; ia<NA; ia++) { 14197 ProcessRecord r = procs.valueAt(ia); 14198 if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) { 14199 continue; 14200 } 14201 if (!needSep) { 14202 pw.println(" All known processes:"); 14203 needSep = true; 14204 printedAnything = true; 14205 } 14206 pw.print(r.persistent ? " *PERS*" : " *APP*"); 14207 pw.print(" UID "); pw.print(procs.keyAt(ia)); 14208 pw.print(" "); pw.println(r); 14209 r.dump(pw, " "); 14210 if (r.persistent) { 14211 numPers++; 14212 } 14213 } 14214 } 14215 } 14216 14217 if (mIsolatedProcesses.size() > 0) { 14218 boolean printed = false; 14219 for (int i=0; i<mIsolatedProcesses.size(); i++) { 14220 ProcessRecord r = mIsolatedProcesses.valueAt(i); 14221 if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) { 14222 continue; 14223 } 14224 if (!printed) { 14225 if (needSep) { 14226 pw.println(); 14227 } 14228 pw.println(" Isolated process list (sorted by uid):"); 14229 printedAnything = true; 14230 printed = true; 14231 needSep = true; 14232 } 14233 pw.println(String.format("%sIsolated #%2d: %s", 14234 " ", i, r.toString())); 14235 } 14236 } 14237 14238 if (mActiveUids.size() > 0) { 14239 if (dumpUids(pw, dumpPackage, mActiveUids, "UID states:", needSep)) { 14240 printedAnything = needSep = true; 14241 } 14242 } 14243 if (mValidateUids.size() > 0) { 14244 if (dumpUids(pw, dumpPackage, mValidateUids, "UID validation:", needSep)) { 14245 printedAnything = needSep = true; 14246 } 14247 } 14248 14249 if (mLruProcesses.size() > 0) { 14250 if (needSep) { 14251 pw.println(); 14252 } 14253 pw.print(" Process LRU list (sorted by oom_adj, "); pw.print(mLruProcesses.size()); 14254 pw.print(" total, non-act at "); 14255 pw.print(mLruProcesses.size()-mLruProcessActivityStart); 14256 pw.print(", non-svc at "); 14257 pw.print(mLruProcesses.size()-mLruProcessServiceStart); 14258 pw.println("):"); 14259 dumpProcessOomList(pw, this, mLruProcesses, " ", "Proc", "PERS", false, dumpPackage); 14260 needSep = true; 14261 printedAnything = true; 14262 } 14263 14264 if (dumpAll || dumpPackage != null) { 14265 synchronized (mPidsSelfLocked) { 14266 boolean printed = false; 14267 for (int i=0; i<mPidsSelfLocked.size(); i++) { 14268 ProcessRecord r = mPidsSelfLocked.valueAt(i); 14269 if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) { 14270 continue; 14271 } 14272 if (!printed) { 14273 if (needSep) pw.println(); 14274 needSep = true; 14275 pw.println(" PID mappings:"); 14276 printed = true; 14277 printedAnything = true; 14278 } 14279 pw.print(" PID #"); pw.print(mPidsSelfLocked.keyAt(i)); 14280 pw.print(": "); pw.println(mPidsSelfLocked.valueAt(i)); 14281 } 14282 } 14283 } 14284 14285 if (mForegroundProcesses.size() > 0) { 14286 synchronized (mPidsSelfLocked) { 14287 boolean printed = false; 14288 for (int i=0; i<mForegroundProcesses.size(); i++) { 14289 ProcessRecord r = mPidsSelfLocked.get( 14290 mForegroundProcesses.valueAt(i).pid); 14291 if (dumpPackage != null && (r == null 14292 || !r.pkgList.containsKey(dumpPackage))) { 14293 continue; 14294 } 14295 if (!printed) { 14296 if (needSep) pw.println(); 14297 needSep = true; 14298 pw.println(" Foreground Processes:"); 14299 printed = true; 14300 printedAnything = true; 14301 } 14302 pw.print(" PID #"); pw.print(mForegroundProcesses.keyAt(i)); 14303 pw.print(": "); pw.println(mForegroundProcesses.valueAt(i)); 14304 } 14305 } 14306 } 14307 14308 if (mPersistentStartingProcesses.size() > 0) { 14309 if (needSep) pw.println(); 14310 needSep = true; 14311 printedAnything = true; 14312 pw.println(" Persisent processes that are starting:"); 14313 dumpProcessList(pw, this, mPersistentStartingProcesses, " ", 14314 "Starting Norm", "Restarting PERS", dumpPackage); 14315 } 14316 14317 if (mRemovedProcesses.size() > 0) { 14318 if (needSep) pw.println(); 14319 needSep = true; 14320 printedAnything = true; 14321 pw.println(" Processes that are being removed:"); 14322 dumpProcessList(pw, this, mRemovedProcesses, " ", 14323 "Removed Norm", "Removed PERS", dumpPackage); 14324 } 14325 14326 if (mProcessesOnHold.size() > 0) { 14327 if (needSep) pw.println(); 14328 needSep = true; 14329 printedAnything = true; 14330 pw.println(" Processes that are on old until the system is ready:"); 14331 dumpProcessList(pw, this, mProcessesOnHold, " ", 14332 "OnHold Norm", "OnHold PERS", dumpPackage); 14333 } 14334 14335 needSep = dumpProcessesToGc(fd, pw, args, opti, needSep, dumpAll, dumpPackage); 14336 14337 needSep = mAppErrors.dumpLocked(fd, pw, needSep, dumpPackage); 14338 if (needSep) { 14339 printedAnything = true; 14340 } 14341 14342 if (dumpPackage == null) { 14343 pw.println(); 14344 needSep = false; 14345 mUserController.dump(pw, dumpAll); 14346 } 14347 if (mHomeProcess != null && (dumpPackage == null 14348 || mHomeProcess.pkgList.containsKey(dumpPackage))) { 14349 if (needSep) { 14350 pw.println(); 14351 needSep = false; 14352 } 14353 pw.println(" mHomeProcess: " + mHomeProcess); 14354 } 14355 if (mPreviousProcess != null && (dumpPackage == null 14356 || mPreviousProcess.pkgList.containsKey(dumpPackage))) { 14357 if (needSep) { 14358 pw.println(); 14359 needSep = false; 14360 } 14361 pw.println(" mPreviousProcess: " + mPreviousProcess); 14362 } 14363 if (dumpAll) { 14364 StringBuilder sb = new StringBuilder(128); 14365 sb.append(" mPreviousProcessVisibleTime: "); 14366 TimeUtils.formatDuration(mPreviousProcessVisibleTime, sb); 14367 pw.println(sb); 14368 } 14369 if (mHeavyWeightProcess != null && (dumpPackage == null 14370 || mHeavyWeightProcess.pkgList.containsKey(dumpPackage))) { 14371 if (needSep) { 14372 pw.println(); 14373 needSep = false; 14374 } 14375 pw.println(" mHeavyWeightProcess: " + mHeavyWeightProcess); 14376 } 14377 if (dumpPackage == null) { 14378 pw.println(" mConfiguration: " + mConfiguration); 14379 } 14380 if (dumpAll) { 14381 pw.println(" mConfigWillChange: " + getFocusedStack().mConfigWillChange); 14382 if (mCompatModePackages.getPackages().size() > 0) { 14383 boolean printed = false; 14384 for (Map.Entry<String, Integer> entry 14385 : mCompatModePackages.getPackages().entrySet()) { 14386 String pkg = entry.getKey(); 14387 int mode = entry.getValue(); 14388 if (dumpPackage != null && !dumpPackage.equals(pkg)) { 14389 continue; 14390 } 14391 if (!printed) { 14392 pw.println(" mScreenCompatPackages:"); 14393 printed = true; 14394 } 14395 pw.print(" "); pw.print(pkg); pw.print(": "); 14396 pw.print(mode); pw.println(); 14397 } 14398 } 14399 } 14400 if (dumpPackage == null) { 14401 pw.println(" mWakefulness=" 14402 + PowerManagerInternal.wakefulnessToString(mWakefulness)); 14403 pw.println(" mSleepTokens=" + mSleepTokens); 14404 pw.println(" mSleeping=" + mSleeping + " mLockScreenShown=" 14405 + lockScreenShownToString()); 14406 pw.println(" mShuttingDown=" + mShuttingDown + " mTestPssMode=" + mTestPssMode); 14407 if (mRunningVoice != null) { 14408 pw.println(" mRunningVoice=" + mRunningVoice); 14409 pw.println(" mVoiceWakeLock" + mVoiceWakeLock); 14410 } 14411 } 14412 if (mDebugApp != null || mOrigDebugApp != null || mDebugTransient 14413 || mOrigWaitForDebugger) { 14414 if (dumpPackage == null || dumpPackage.equals(mDebugApp) 14415 || dumpPackage.equals(mOrigDebugApp)) { 14416 if (needSep) { 14417 pw.println(); 14418 needSep = false; 14419 } 14420 pw.println(" mDebugApp=" + mDebugApp + "/orig=" + mOrigDebugApp 14421 + " mDebugTransient=" + mDebugTransient 14422 + " mOrigWaitForDebugger=" + mOrigWaitForDebugger); 14423 } 14424 } 14425 if (mCurAppTimeTracker != null) { 14426 mCurAppTimeTracker.dumpWithHeader(pw, " ", true); 14427 } 14428 if (mMemWatchProcesses.getMap().size() > 0) { 14429 pw.println(" Mem watch processes:"); 14430 final ArrayMap<String, SparseArray<Pair<Long, String>>> procs 14431 = mMemWatchProcesses.getMap(); 14432 for (int i=0; i<procs.size(); i++) { 14433 final String proc = procs.keyAt(i); 14434 final SparseArray<Pair<Long, String>> uids = procs.valueAt(i); 14435 for (int j=0; j<uids.size(); j++) { 14436 if (needSep) { 14437 pw.println(); 14438 needSep = false; 14439 } 14440 StringBuilder sb = new StringBuilder(); 14441 sb.append(" ").append(proc).append('/'); 14442 UserHandle.formatUid(sb, uids.keyAt(j)); 14443 Pair<Long, String> val = uids.valueAt(j); 14444 sb.append(": "); DebugUtils.sizeValueToString(val.first, sb); 14445 if (val.second != null) { 14446 sb.append(", report to ").append(val.second); 14447 } 14448 pw.println(sb.toString()); 14449 } 14450 } 14451 pw.print(" mMemWatchDumpProcName="); pw.println(mMemWatchDumpProcName); 14452 pw.print(" mMemWatchDumpFile="); pw.println(mMemWatchDumpFile); 14453 pw.print(" mMemWatchDumpPid="); pw.print(mMemWatchDumpPid); 14454 pw.print(" mMemWatchDumpUid="); pw.println(mMemWatchDumpUid); 14455 } 14456 if (mTrackAllocationApp != null) { 14457 if (dumpPackage == null || dumpPackage.equals(mTrackAllocationApp)) { 14458 if (needSep) { 14459 pw.println(); 14460 needSep = false; 14461 } 14462 pw.println(" mTrackAllocationApp=" + mTrackAllocationApp); 14463 } 14464 } 14465 if (mProfileApp != null || mProfileProc != null || mProfileFile != null 14466 || mProfileFd != null) { 14467 if (dumpPackage == null || dumpPackage.equals(mProfileApp)) { 14468 if (needSep) { 14469 pw.println(); 14470 needSep = false; 14471 } 14472 pw.println(" mProfileApp=" + mProfileApp + " mProfileProc=" + mProfileProc); 14473 pw.println(" mProfileFile=" + mProfileFile + " mProfileFd=" + mProfileFd); 14474 pw.println(" mSamplingInterval=" + mSamplingInterval + " mAutoStopProfiler=" 14475 + mAutoStopProfiler); 14476 pw.println(" mProfileType=" + mProfileType); 14477 } 14478 } 14479 if (mNativeDebuggingApp != null) { 14480 if (dumpPackage == null || dumpPackage.equals(mNativeDebuggingApp)) { 14481 if (needSep) { 14482 pw.println(); 14483 needSep = false; 14484 } 14485 pw.println(" mNativeDebuggingApp=" + mNativeDebuggingApp); 14486 } 14487 } 14488 if (dumpPackage == null) { 14489 if (mAlwaysFinishActivities || mLenientBackgroundCheck) { 14490 pw.println(" mAlwaysFinishActivities=" + mAlwaysFinishActivities 14491 + " mLenientBackgroundCheck=" + mLenientBackgroundCheck); 14492 } 14493 if (mController != null) { 14494 pw.println(" mController=" + mController 14495 + " mControllerIsAMonkey=" + mControllerIsAMonkey); 14496 } 14497 if (dumpAll) { 14498 pw.println(" Total persistent processes: " + numPers); 14499 pw.println(" mProcessesReady=" + mProcessesReady 14500 + " mSystemReady=" + mSystemReady 14501 + " mBooted=" + mBooted 14502 + " mFactoryTest=" + mFactoryTest); 14503 pw.println(" mBooting=" + mBooting 14504 + " mCallFinishBooting=" + mCallFinishBooting 14505 + " mBootAnimationComplete=" + mBootAnimationComplete); 14506 pw.print(" mLastPowerCheckRealtime="); 14507 TimeUtils.formatDuration(mLastPowerCheckRealtime, pw); 14508 pw.println(""); 14509 pw.print(" mLastPowerCheckUptime="); 14510 TimeUtils.formatDuration(mLastPowerCheckUptime, pw); 14511 pw.println(""); 14512 pw.println(" mGoingToSleep=" + mStackSupervisor.mGoingToSleep); 14513 pw.println(" mLaunchingActivity=" + mStackSupervisor.mLaunchingActivity); 14514 pw.println(" mAdjSeq=" + mAdjSeq + " mLruSeq=" + mLruSeq); 14515 pw.println(" mNumNonCachedProcs=" + mNumNonCachedProcs 14516 + " (" + mLruProcesses.size() + " total)" 14517 + " mNumCachedHiddenProcs=" + mNumCachedHiddenProcs 14518 + " mNumServiceProcs=" + mNumServiceProcs 14519 + " mNewNumServiceProcs=" + mNewNumServiceProcs); 14520 pw.println(" mAllowLowerMemLevel=" + mAllowLowerMemLevel 14521 + " mLastMemoryLevel=" + mLastMemoryLevel 14522 + " mLastNumProcesses=" + mLastNumProcesses); 14523 long now = SystemClock.uptimeMillis(); 14524 pw.print(" mLastIdleTime="); 14525 TimeUtils.formatDuration(now, mLastIdleTime, pw); 14526 pw.print(" mLowRamSinceLastIdle="); 14527 TimeUtils.formatDuration(getLowRamTimeSinceIdle(now), pw); 14528 pw.println(); 14529 } 14530 } 14531 14532 if (!printedAnything) { 14533 pw.println(" (nothing)"); 14534 } 14535 } 14536 14537 boolean dumpProcessesToGc(FileDescriptor fd, PrintWriter pw, String[] args, 14538 int opti, boolean needSep, boolean dumpAll, String dumpPackage) { 14539 if (mProcessesToGc.size() > 0) { 14540 boolean printed = false; 14541 long now = SystemClock.uptimeMillis(); 14542 for (int i=0; i<mProcessesToGc.size(); i++) { 14543 ProcessRecord proc = mProcessesToGc.get(i); 14544 if (dumpPackage != null && !dumpPackage.equals(proc.info.packageName)) { 14545 continue; 14546 } 14547 if (!printed) { 14548 if (needSep) pw.println(); 14549 needSep = true; 14550 pw.println(" Processes that are waiting to GC:"); 14551 printed = true; 14552 } 14553 pw.print(" Process "); pw.println(proc); 14554 pw.print(" lowMem="); pw.print(proc.reportLowMemory); 14555 pw.print(", last gced="); 14556 pw.print(now-proc.lastRequestedGc); 14557 pw.print(" ms ago, last lowMem="); 14558 pw.print(now-proc.lastLowMemory); 14559 pw.println(" ms ago"); 14560 14561 } 14562 } 14563 return needSep; 14564 } 14565 14566 void printOomLevel(PrintWriter pw, String name, int adj) { 14567 pw.print(" "); 14568 if (adj >= 0) { 14569 pw.print(' '); 14570 if (adj < 10) pw.print(' '); 14571 } else { 14572 if (adj > -10) pw.print(' '); 14573 } 14574 pw.print(adj); 14575 pw.print(": "); 14576 pw.print(name); 14577 pw.print(" ("); 14578 pw.print(stringifySize(mProcessList.getMemLevel(adj), 1024)); 14579 pw.println(")"); 14580 } 14581 14582 boolean dumpOomLocked(FileDescriptor fd, PrintWriter pw, String[] args, 14583 int opti, boolean dumpAll) { 14584 boolean needSep = false; 14585 14586 if (mLruProcesses.size() > 0) { 14587 if (needSep) pw.println(); 14588 needSep = true; 14589 pw.println(" OOM levels:"); 14590 printOomLevel(pw, "SYSTEM_ADJ", ProcessList.SYSTEM_ADJ); 14591 printOomLevel(pw, "PERSISTENT_PROC_ADJ", ProcessList.PERSISTENT_PROC_ADJ); 14592 printOomLevel(pw, "PERSISTENT_SERVICE_ADJ", ProcessList.PERSISTENT_SERVICE_ADJ); 14593 printOomLevel(pw, "FOREGROUND_APP_ADJ", ProcessList.FOREGROUND_APP_ADJ); 14594 printOomLevel(pw, "VISIBLE_APP_ADJ", ProcessList.VISIBLE_APP_ADJ); 14595 printOomLevel(pw, "PERCEPTIBLE_APP_ADJ", ProcessList.PERCEPTIBLE_APP_ADJ); 14596 printOomLevel(pw, "BACKUP_APP_ADJ", ProcessList.BACKUP_APP_ADJ); 14597 printOomLevel(pw, "HEAVY_WEIGHT_APP_ADJ", ProcessList.HEAVY_WEIGHT_APP_ADJ); 14598 printOomLevel(pw, "SERVICE_ADJ", ProcessList.SERVICE_ADJ); 14599 printOomLevel(pw, "HOME_APP_ADJ", ProcessList.HOME_APP_ADJ); 14600 printOomLevel(pw, "PREVIOUS_APP_ADJ", ProcessList.PREVIOUS_APP_ADJ); 14601 printOomLevel(pw, "SERVICE_B_ADJ", ProcessList.SERVICE_B_ADJ); 14602 printOomLevel(pw, "CACHED_APP_MIN_ADJ", ProcessList.CACHED_APP_MIN_ADJ); 14603 printOomLevel(pw, "CACHED_APP_MAX_ADJ", ProcessList.CACHED_APP_MAX_ADJ); 14604 14605 if (needSep) pw.println(); 14606 pw.print(" Process OOM control ("); pw.print(mLruProcesses.size()); 14607 pw.print(" total, non-act at "); 14608 pw.print(mLruProcesses.size()-mLruProcessActivityStart); 14609 pw.print(", non-svc at "); 14610 pw.print(mLruProcesses.size()-mLruProcessServiceStart); 14611 pw.println("):"); 14612 dumpProcessOomList(pw, this, mLruProcesses, " ", "Proc", "PERS", true, null); 14613 needSep = true; 14614 } 14615 14616 dumpProcessesToGc(fd, pw, args, opti, needSep, dumpAll, null); 14617 14618 pw.println(); 14619 pw.println(" mHomeProcess: " + mHomeProcess); 14620 pw.println(" mPreviousProcess: " + mPreviousProcess); 14621 if (mHeavyWeightProcess != null) { 14622 pw.println(" mHeavyWeightProcess: " + mHeavyWeightProcess); 14623 } 14624 14625 return true; 14626 } 14627 14628 /** 14629 * There are three ways to call this: 14630 * - no provider specified: dump all the providers 14631 * - a flattened component name that matched an existing provider was specified as the 14632 * first arg: dump that one provider 14633 * - the first arg isn't the flattened component name of an existing provider: 14634 * dump all providers whose component contains the first arg as a substring 14635 */ 14636 protected boolean dumpProvider(FileDescriptor fd, PrintWriter pw, String name, String[] args, 14637 int opti, boolean dumpAll) { 14638 return mProviderMap.dumpProvider(fd, pw, name, args, opti, dumpAll); 14639 } 14640 14641 static class ItemMatcher { 14642 ArrayList<ComponentName> components; 14643 ArrayList<String> strings; 14644 ArrayList<Integer> objects; 14645 boolean all; 14646 14647 ItemMatcher() { 14648 all = true; 14649 } 14650 14651 void build(String name) { 14652 ComponentName componentName = ComponentName.unflattenFromString(name); 14653 if (componentName != null) { 14654 if (components == null) { 14655 components = new ArrayList<ComponentName>(); 14656 } 14657 components.add(componentName); 14658 all = false; 14659 } else { 14660 int objectId = 0; 14661 // Not a '/' separated full component name; maybe an object ID? 14662 try { 14663 objectId = Integer.parseInt(name, 16); 14664 if (objects == null) { 14665 objects = new ArrayList<Integer>(); 14666 } 14667 objects.add(objectId); 14668 all = false; 14669 } catch (RuntimeException e) { 14670 // Not an integer; just do string match. 14671 if (strings == null) { 14672 strings = new ArrayList<String>(); 14673 } 14674 strings.add(name); 14675 all = false; 14676 } 14677 } 14678 } 14679 14680 int build(String[] args, int opti) { 14681 for (; opti<args.length; opti++) { 14682 String name = args[opti]; 14683 if ("--".equals(name)) { 14684 return opti+1; 14685 } 14686 build(name); 14687 } 14688 return opti; 14689 } 14690 14691 boolean match(Object object, ComponentName comp) { 14692 if (all) { 14693 return true; 14694 } 14695 if (components != null) { 14696 for (int i=0; i<components.size(); i++) { 14697 if (components.get(i).equals(comp)) { 14698 return true; 14699 } 14700 } 14701 } 14702 if (objects != null) { 14703 for (int i=0; i<objects.size(); i++) { 14704 if (System.identityHashCode(object) == objects.get(i)) { 14705 return true; 14706 } 14707 } 14708 } 14709 if (strings != null) { 14710 String flat = comp.flattenToString(); 14711 for (int i=0; i<strings.size(); i++) { 14712 if (flat.contains(strings.get(i))) { 14713 return true; 14714 } 14715 } 14716 } 14717 return false; 14718 } 14719 } 14720 14721 /** 14722 * There are three things that cmd can be: 14723 * - a flattened component name that matches an existing activity 14724 * - the cmd arg isn't the flattened component name of an existing activity: 14725 * dump all activity whose component contains the cmd as a substring 14726 * - A hex number of the ActivityRecord object instance. 14727 */ 14728 protected boolean dumpActivity(FileDescriptor fd, PrintWriter pw, String name, String[] args, 14729 int opti, boolean dumpAll) { 14730 ArrayList<ActivityRecord> activities; 14731 14732 synchronized (this) { 14733 activities = mStackSupervisor.getDumpActivitiesLocked(name); 14734 } 14735 14736 if (activities.size() <= 0) { 14737 return false; 14738 } 14739 14740 String[] newArgs = new String[args.length - opti]; 14741 System.arraycopy(args, opti, newArgs, 0, args.length - opti); 14742 14743 TaskRecord lastTask = null; 14744 boolean needSep = false; 14745 for (int i=activities.size()-1; i>=0; i--) { 14746 ActivityRecord r = activities.get(i); 14747 if (needSep) { 14748 pw.println(); 14749 } 14750 needSep = true; 14751 synchronized (this) { 14752 if (lastTask != r.task) { 14753 lastTask = r.task; 14754 pw.print("TASK "); pw.print(lastTask.affinity); 14755 pw.print(" id="); pw.println(lastTask.taskId); 14756 if (dumpAll) { 14757 lastTask.dump(pw, " "); 14758 } 14759 } 14760 } 14761 dumpActivity(" ", fd, pw, activities.get(i), newArgs, dumpAll); 14762 } 14763 return true; 14764 } 14765 14766 /** 14767 * Invokes IApplicationThread.dumpActivity() on the thread of the specified activity if 14768 * there is a thread associated with the activity. 14769 */ 14770 private void dumpActivity(String prefix, FileDescriptor fd, PrintWriter pw, 14771 final ActivityRecord r, String[] args, boolean dumpAll) { 14772 String innerPrefix = prefix + " "; 14773 synchronized (this) { 14774 pw.print(prefix); pw.print("ACTIVITY "); pw.print(r.shortComponentName); 14775 pw.print(" "); pw.print(Integer.toHexString(System.identityHashCode(r))); 14776 pw.print(" pid="); 14777 if (r.app != null) pw.println(r.app.pid); 14778 else pw.println("(not running)"); 14779 if (dumpAll) { 14780 r.dump(pw, innerPrefix); 14781 } 14782 } 14783 if (r.app != null && r.app.thread != null) { 14784 // flush anything that is already in the PrintWriter since the thread is going 14785 // to write to the file descriptor directly 14786 pw.flush(); 14787 try { 14788 TransferPipe tp = new TransferPipe(); 14789 try { 14790 r.app.thread.dumpActivity(tp.getWriteFd().getFileDescriptor(), 14791 r.appToken, innerPrefix, args); 14792 tp.go(fd); 14793 } finally { 14794 tp.kill(); 14795 } 14796 } catch (IOException e) { 14797 pw.println(innerPrefix + "Failure while dumping the activity: " + e); 14798 } catch (RemoteException e) { 14799 pw.println(innerPrefix + "Got a RemoteException while dumping the activity"); 14800 } 14801 } 14802 } 14803 14804 void dumpBroadcastsLocked(FileDescriptor fd, PrintWriter pw, String[] args, 14805 int opti, boolean dumpAll, String dumpPackage) { 14806 boolean needSep = false; 14807 boolean onlyHistory = false; 14808 boolean printedAnything = false; 14809 14810 if ("history".equals(dumpPackage)) { 14811 if (opti < args.length && "-s".equals(args[opti])) { 14812 dumpAll = false; 14813 } 14814 onlyHistory = true; 14815 dumpPackage = null; 14816 } 14817 14818 pw.println("ACTIVITY MANAGER BROADCAST STATE (dumpsys activity broadcasts)"); 14819 if (!onlyHistory && dumpAll) { 14820 if (mRegisteredReceivers.size() > 0) { 14821 boolean printed = false; 14822 Iterator it = mRegisteredReceivers.values().iterator(); 14823 while (it.hasNext()) { 14824 ReceiverList r = (ReceiverList)it.next(); 14825 if (dumpPackage != null && (r.app == null || 14826 !dumpPackage.equals(r.app.info.packageName))) { 14827 continue; 14828 } 14829 if (!printed) { 14830 pw.println(" Registered Receivers:"); 14831 needSep = true; 14832 printed = true; 14833 printedAnything = true; 14834 } 14835 pw.print(" * "); pw.println(r); 14836 r.dump(pw, " "); 14837 } 14838 } 14839 14840 if (mReceiverResolver.dump(pw, needSep ? 14841 "\n Receiver Resolver Table:" : " Receiver Resolver Table:", 14842 " ", dumpPackage, false, false)) { 14843 needSep = true; 14844 printedAnything = true; 14845 } 14846 } 14847 14848 for (BroadcastQueue q : mBroadcastQueues) { 14849 needSep = q.dumpLocked(fd, pw, args, opti, dumpAll, dumpPackage, needSep); 14850 printedAnything |= needSep; 14851 } 14852 14853 needSep = true; 14854 14855 if (!onlyHistory && mStickyBroadcasts != null && dumpPackage == null) { 14856 for (int user=0; user<mStickyBroadcasts.size(); user++) { 14857 if (needSep) { 14858 pw.println(); 14859 } 14860 needSep = true; 14861 printedAnything = true; 14862 pw.print(" Sticky broadcasts for user "); 14863 pw.print(mStickyBroadcasts.keyAt(user)); pw.println(":"); 14864 StringBuilder sb = new StringBuilder(128); 14865 for (Map.Entry<String, ArrayList<Intent>> ent 14866 : mStickyBroadcasts.valueAt(user).entrySet()) { 14867 pw.print(" * Sticky action "); pw.print(ent.getKey()); 14868 if (dumpAll) { 14869 pw.println(":"); 14870 ArrayList<Intent> intents = ent.getValue(); 14871 final int N = intents.size(); 14872 for (int i=0; i<N; i++) { 14873 sb.setLength(0); 14874 sb.append(" Intent: "); 14875 intents.get(i).toShortString(sb, false, true, false, false); 14876 pw.println(sb.toString()); 14877 Bundle bundle = intents.get(i).getExtras(); 14878 if (bundle != null) { 14879 pw.print(" "); 14880 pw.println(bundle.toString()); 14881 } 14882 } 14883 } else { 14884 pw.println(""); 14885 } 14886 } 14887 } 14888 } 14889 14890 if (!onlyHistory && dumpAll) { 14891 pw.println(); 14892 for (BroadcastQueue queue : mBroadcastQueues) { 14893 pw.println(" mBroadcastsScheduled [" + queue.mQueueName + "]=" 14894 + queue.mBroadcastsScheduled); 14895 } 14896 pw.println(" mHandler:"); 14897 mHandler.dump(new PrintWriterPrinter(pw), " "); 14898 needSep = true; 14899 printedAnything = true; 14900 } 14901 14902 if (!printedAnything) { 14903 pw.println(" (nothing)"); 14904 } 14905 } 14906 14907 void dumpProvidersLocked(FileDescriptor fd, PrintWriter pw, String[] args, 14908 int opti, boolean dumpAll, String dumpPackage) { 14909 boolean needSep; 14910 boolean printedAnything = false; 14911 14912 ItemMatcher matcher = new ItemMatcher(); 14913 matcher.build(args, opti); 14914 14915 pw.println("ACTIVITY MANAGER CONTENT PROVIDERS (dumpsys activity providers)"); 14916 14917 needSep = mProviderMap.dumpProvidersLocked(pw, dumpAll, dumpPackage); 14918 printedAnything |= needSep; 14919 14920 if (mLaunchingProviders.size() > 0) { 14921 boolean printed = false; 14922 for (int i=mLaunchingProviders.size()-1; i>=0; i--) { 14923 ContentProviderRecord r = mLaunchingProviders.get(i); 14924 if (dumpPackage != null && !dumpPackage.equals(r.name.getPackageName())) { 14925 continue; 14926 } 14927 if (!printed) { 14928 if (needSep) pw.println(); 14929 needSep = true; 14930 pw.println(" Launching content providers:"); 14931 printed = true; 14932 printedAnything = true; 14933 } 14934 pw.print(" Launching #"); pw.print(i); pw.print(": "); 14935 pw.println(r); 14936 } 14937 } 14938 14939 if (!printedAnything) { 14940 pw.println(" (nothing)"); 14941 } 14942 } 14943 14944 void dumpPermissionsLocked(FileDescriptor fd, PrintWriter pw, String[] args, 14945 int opti, boolean dumpAll, String dumpPackage) { 14946 boolean needSep = false; 14947 boolean printedAnything = false; 14948 14949 pw.println("ACTIVITY MANAGER URI PERMISSIONS (dumpsys activity permissions)"); 14950 14951 if (mGrantedUriPermissions.size() > 0) { 14952 boolean printed = false; 14953 int dumpUid = -2; 14954 if (dumpPackage != null) { 14955 try { 14956 dumpUid = mContext.getPackageManager().getPackageUidAsUser(dumpPackage, 14957 MATCH_UNINSTALLED_PACKAGES, 0); 14958 } catch (NameNotFoundException e) { 14959 dumpUid = -1; 14960 } 14961 } 14962 for (int i=0; i<mGrantedUriPermissions.size(); i++) { 14963 int uid = mGrantedUriPermissions.keyAt(i); 14964 if (dumpUid >= -1 && UserHandle.getAppId(uid) != dumpUid) { 14965 continue; 14966 } 14967 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i); 14968 if (!printed) { 14969 if (needSep) pw.println(); 14970 needSep = true; 14971 pw.println(" Granted Uri Permissions:"); 14972 printed = true; 14973 printedAnything = true; 14974 } 14975 pw.print(" * UID "); pw.print(uid); pw.println(" holds:"); 14976 for (UriPermission perm : perms.values()) { 14977 pw.print(" "); pw.println(perm); 14978 if (dumpAll) { 14979 perm.dump(pw, " "); 14980 } 14981 } 14982 } 14983 } 14984 14985 if (!printedAnything) { 14986 pw.println(" (nothing)"); 14987 } 14988 } 14989 14990 void dumpPendingIntentsLocked(FileDescriptor fd, PrintWriter pw, String[] args, 14991 int opti, boolean dumpAll, String dumpPackage) { 14992 boolean printed = false; 14993 14994 pw.println("ACTIVITY MANAGER PENDING INTENTS (dumpsys activity intents)"); 14995 14996 if (mIntentSenderRecords.size() > 0) { 14997 Iterator<WeakReference<PendingIntentRecord>> it 14998 = mIntentSenderRecords.values().iterator(); 14999 while (it.hasNext()) { 15000 WeakReference<PendingIntentRecord> ref = it.next(); 15001 PendingIntentRecord rec = ref != null ? ref.get(): null; 15002 if (dumpPackage != null && (rec == null 15003 || !dumpPackage.equals(rec.key.packageName))) { 15004 continue; 15005 } 15006 printed = true; 15007 if (rec != null) { 15008 pw.print(" * "); pw.println(rec); 15009 if (dumpAll) { 15010 rec.dump(pw, " "); 15011 } 15012 } else { 15013 pw.print(" * "); pw.println(ref); 15014 } 15015 } 15016 } 15017 15018 if (!printed) { 15019 pw.println(" (nothing)"); 15020 } 15021 } 15022 15023 private static final int dumpProcessList(PrintWriter pw, 15024 ActivityManagerService service, List list, 15025 String prefix, String normalLabel, String persistentLabel, 15026 String dumpPackage) { 15027 int numPers = 0; 15028 final int N = list.size()-1; 15029 for (int i=N; i>=0; i--) { 15030 ProcessRecord r = (ProcessRecord)list.get(i); 15031 if (dumpPackage != null && !dumpPackage.equals(r.info.packageName)) { 15032 continue; 15033 } 15034 pw.println(String.format("%s%s #%2d: %s", 15035 prefix, (r.persistent ? persistentLabel : normalLabel), 15036 i, r.toString())); 15037 if (r.persistent) { 15038 numPers++; 15039 } 15040 } 15041 return numPers; 15042 } 15043 15044 private static final boolean dumpProcessOomList(PrintWriter pw, 15045 ActivityManagerService service, List<ProcessRecord> origList, 15046 String prefix, String normalLabel, String persistentLabel, 15047 boolean inclDetails, String dumpPackage) { 15048 15049 ArrayList<Pair<ProcessRecord, Integer>> list 15050 = new ArrayList<Pair<ProcessRecord, Integer>>(origList.size()); 15051 for (int i=0; i<origList.size(); i++) { 15052 ProcessRecord r = origList.get(i); 15053 if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) { 15054 continue; 15055 } 15056 list.add(new Pair<ProcessRecord, Integer>(origList.get(i), i)); 15057 } 15058 15059 if (list.size() <= 0) { 15060 return false; 15061 } 15062 15063 Comparator<Pair<ProcessRecord, Integer>> comparator 15064 = new Comparator<Pair<ProcessRecord, Integer>>() { 15065 @Override 15066 public int compare(Pair<ProcessRecord, Integer> object1, 15067 Pair<ProcessRecord, Integer> object2) { 15068 if (object1.first.setAdj != object2.first.setAdj) { 15069 return object1.first.setAdj > object2.first.setAdj ? -1 : 1; 15070 } 15071 if (object1.first.setProcState != object2.first.setProcState) { 15072 return object1.first.setProcState > object2.first.setProcState ? -1 : 1; 15073 } 15074 if (object1.second.intValue() != object2.second.intValue()) { 15075 return object1.second.intValue() > object2.second.intValue() ? -1 : 1; 15076 } 15077 return 0; 15078 } 15079 }; 15080 15081 Collections.sort(list, comparator); 15082 15083 final long curRealtime = SystemClock.elapsedRealtime(); 15084 final long realtimeSince = curRealtime - service.mLastPowerCheckRealtime; 15085 final long curUptime = SystemClock.uptimeMillis(); 15086 final long uptimeSince = curUptime - service.mLastPowerCheckUptime; 15087 15088 for (int i=list.size()-1; i>=0; i--) { 15089 ProcessRecord r = list.get(i).first; 15090 String oomAdj = ProcessList.makeOomAdjString(r.setAdj); 15091 char schedGroup; 15092 switch (r.setSchedGroup) { 15093 case ProcessList.SCHED_GROUP_BACKGROUND: 15094 schedGroup = 'B'; 15095 break; 15096 case ProcessList.SCHED_GROUP_DEFAULT: 15097 schedGroup = 'F'; 15098 break; 15099 case ProcessList.SCHED_GROUP_TOP_APP: 15100 schedGroup = 'T'; 15101 break; 15102 default: 15103 schedGroup = '?'; 15104 break; 15105 } 15106 char foreground; 15107 if (r.foregroundActivities) { 15108 foreground = 'A'; 15109 } else if (r.foregroundServices) { 15110 foreground = 'S'; 15111 } else { 15112 foreground = ' '; 15113 } 15114 String procState = ProcessList.makeProcStateString(r.curProcState); 15115 pw.print(prefix); 15116 pw.print(r.persistent ? persistentLabel : normalLabel); 15117 pw.print(" #"); 15118 int num = (origList.size()-1)-list.get(i).second; 15119 if (num < 10) pw.print(' '); 15120 pw.print(num); 15121 pw.print(": "); 15122 pw.print(oomAdj); 15123 pw.print(' '); 15124 pw.print(schedGroup); 15125 pw.print('/'); 15126 pw.print(foreground); 15127 pw.print('/'); 15128 pw.print(procState); 15129 pw.print(" trm:"); 15130 if (r.trimMemoryLevel < 10) pw.print(' '); 15131 pw.print(r.trimMemoryLevel); 15132 pw.print(' '); 15133 pw.print(r.toShortString()); 15134 pw.print(" ("); 15135 pw.print(r.adjType); 15136 pw.println(')'); 15137 if (r.adjSource != null || r.adjTarget != null) { 15138 pw.print(prefix); 15139 pw.print(" "); 15140 if (r.adjTarget instanceof ComponentName) { 15141 pw.print(((ComponentName)r.adjTarget).flattenToShortString()); 15142 } else if (r.adjTarget != null) { 15143 pw.print(r.adjTarget.toString()); 15144 } else { 15145 pw.print("{null}"); 15146 } 15147 pw.print("<="); 15148 if (r.adjSource instanceof ProcessRecord) { 15149 pw.print("Proc{"); 15150 pw.print(((ProcessRecord)r.adjSource).toShortString()); 15151 pw.println("}"); 15152 } else if (r.adjSource != null) { 15153 pw.println(r.adjSource.toString()); 15154 } else { 15155 pw.println("{null}"); 15156 } 15157 } 15158 if (inclDetails) { 15159 pw.print(prefix); 15160 pw.print(" "); 15161 pw.print("oom: max="); pw.print(r.maxAdj); 15162 pw.print(" curRaw="); pw.print(r.curRawAdj); 15163 pw.print(" setRaw="); pw.print(r.setRawAdj); 15164 pw.print(" cur="); pw.print(r.curAdj); 15165 pw.print(" set="); pw.println(r.setAdj); 15166 pw.print(prefix); 15167 pw.print(" "); 15168 pw.print("state: cur="); pw.print(ProcessList.makeProcStateString(r.curProcState)); 15169 pw.print(" set="); pw.print(ProcessList.makeProcStateString(r.setProcState)); 15170 pw.print(" lastPss="); DebugUtils.printSizeValue(pw, r.lastPss*1024); 15171 pw.print(" lastSwapPss="); DebugUtils.printSizeValue(pw, r.lastSwapPss*1024); 15172 pw.print(" lastCachedPss="); DebugUtils.printSizeValue(pw, r.lastCachedPss*1024); 15173 pw.println(); 15174 pw.print(prefix); 15175 pw.print(" "); 15176 pw.print("cached="); pw.print(r.cached); 15177 pw.print(" empty="); pw.print(r.empty); 15178 pw.print(" hasAboveClient="); pw.println(r.hasAboveClient); 15179 15180 if (r.setProcState >= ActivityManager.PROCESS_STATE_SERVICE) { 15181 if (r.lastWakeTime != 0) { 15182 long wtime; 15183 BatteryStatsImpl stats = service.mBatteryStatsService.getActiveStatistics(); 15184 synchronized (stats) { 15185 wtime = stats.getProcessWakeTime(r.info.uid, 15186 r.pid, curRealtime); 15187 } 15188 long timeUsed = wtime - r.lastWakeTime; 15189 pw.print(prefix); 15190 pw.print(" "); 15191 pw.print("keep awake over "); 15192 TimeUtils.formatDuration(realtimeSince, pw); 15193 pw.print(" used "); 15194 TimeUtils.formatDuration(timeUsed, pw); 15195 pw.print(" ("); 15196 pw.print((timeUsed*100)/realtimeSince); 15197 pw.println("%)"); 15198 } 15199 if (r.lastCpuTime != 0) { 15200 long timeUsed = r.curCpuTime - r.lastCpuTime; 15201 pw.print(prefix); 15202 pw.print(" "); 15203 pw.print("run cpu over "); 15204 TimeUtils.formatDuration(uptimeSince, pw); 15205 pw.print(" used "); 15206 TimeUtils.formatDuration(timeUsed, pw); 15207 pw.print(" ("); 15208 pw.print((timeUsed*100)/uptimeSince); 15209 pw.println("%)"); 15210 } 15211 } 15212 } 15213 } 15214 return true; 15215 } 15216 15217 ArrayList<ProcessRecord> collectProcesses(PrintWriter pw, int start, boolean allPkgs, 15218 String[] args) { 15219 ArrayList<ProcessRecord> procs; 15220 synchronized (this) { 15221 if (args != null && args.length > start 15222 && args[start].charAt(0) != '-') { 15223 procs = new ArrayList<ProcessRecord>(); 15224 int pid = -1; 15225 try { 15226 pid = Integer.parseInt(args[start]); 15227 } catch (NumberFormatException e) { 15228 } 15229 for (int i=mLruProcesses.size()-1; i>=0; i--) { 15230 ProcessRecord proc = mLruProcesses.get(i); 15231 if (proc.pid == pid) { 15232 procs.add(proc); 15233 } else if (allPkgs && proc.pkgList != null 15234 && proc.pkgList.containsKey(args[start])) { 15235 procs.add(proc); 15236 } else if (proc.processName.equals(args[start])) { 15237 procs.add(proc); 15238 } 15239 } 15240 if (procs.size() <= 0) { 15241 return null; 15242 } 15243 } else { 15244 procs = new ArrayList<ProcessRecord>(mLruProcesses); 15245 } 15246 } 15247 return procs; 15248 } 15249 15250 final void dumpGraphicsHardwareUsage(FileDescriptor fd, 15251 PrintWriter pw, String[] args) { 15252 ArrayList<ProcessRecord> procs = collectProcesses(pw, 0, false, args); 15253 if (procs == null) { 15254 pw.println("No process found for: " + args[0]); 15255 return; 15256 } 15257 15258 long uptime = SystemClock.uptimeMillis(); 15259 long realtime = SystemClock.elapsedRealtime(); 15260 pw.println("Applications Graphics Acceleration Info:"); 15261 pw.println("Uptime: " + uptime + " Realtime: " + realtime); 15262 15263 for (int i = procs.size() - 1 ; i >= 0 ; i--) { 15264 ProcessRecord r = procs.get(i); 15265 if (r.thread != null) { 15266 pw.println("\n** Graphics info for pid " + r.pid + " [" + r.processName + "] **"); 15267 pw.flush(); 15268 try { 15269 TransferPipe tp = new TransferPipe(); 15270 try { 15271 r.thread.dumpGfxInfo(tp.getWriteFd().getFileDescriptor(), args); 15272 tp.go(fd); 15273 } finally { 15274 tp.kill(); 15275 } 15276 } catch (IOException e) { 15277 pw.println("Failure while dumping the app: " + r); 15278 pw.flush(); 15279 } catch (RemoteException e) { 15280 pw.println("Got a RemoteException while dumping the app " + r); 15281 pw.flush(); 15282 } 15283 } 15284 } 15285 } 15286 15287 final void dumpDbInfo(FileDescriptor fd, PrintWriter pw, String[] args) { 15288 ArrayList<ProcessRecord> procs = collectProcesses(pw, 0, false, args); 15289 if (procs == null) { 15290 pw.println("No process found for: " + args[0]); 15291 return; 15292 } 15293 15294 pw.println("Applications Database Info:"); 15295 15296 for (int i = procs.size() - 1 ; i >= 0 ; i--) { 15297 ProcessRecord r = procs.get(i); 15298 if (r.thread != null) { 15299 pw.println("\n** Database info for pid " + r.pid + " [" + r.processName + "] **"); 15300 pw.flush(); 15301 try { 15302 TransferPipe tp = new TransferPipe(); 15303 try { 15304 r.thread.dumpDbInfo(tp.getWriteFd().getFileDescriptor(), args); 15305 tp.go(fd); 15306 } finally { 15307 tp.kill(); 15308 } 15309 } catch (IOException e) { 15310 pw.println("Failure while dumping the app: " + r); 15311 pw.flush(); 15312 } catch (RemoteException e) { 15313 pw.println("Got a RemoteException while dumping the app " + r); 15314 pw.flush(); 15315 } 15316 } 15317 } 15318 } 15319 15320 final static class MemItem { 15321 final boolean isProc; 15322 final String label; 15323 final String shortLabel; 15324 final long pss; 15325 final long swapPss; 15326 final int id; 15327 final boolean hasActivities; 15328 ArrayList<MemItem> subitems; 15329 15330 public MemItem(String _label, String _shortLabel, long _pss, long _swapPss, int _id, 15331 boolean _hasActivities) { 15332 isProc = true; 15333 label = _label; 15334 shortLabel = _shortLabel; 15335 pss = _pss; 15336 swapPss = _swapPss; 15337 id = _id; 15338 hasActivities = _hasActivities; 15339 } 15340 15341 public MemItem(String _label, String _shortLabel, long _pss, long _swapPss, int _id) { 15342 isProc = false; 15343 label = _label; 15344 shortLabel = _shortLabel; 15345 pss = _pss; 15346 swapPss = _swapPss; 15347 id = _id; 15348 hasActivities = false; 15349 } 15350 } 15351 15352 static final void dumpMemItems(PrintWriter pw, String prefix, String tag, 15353 ArrayList<MemItem> items, boolean sort, boolean isCompact, boolean dumpSwapPss) { 15354 if (sort && !isCompact) { 15355 Collections.sort(items, new Comparator<MemItem>() { 15356 @Override 15357 public int compare(MemItem lhs, MemItem rhs) { 15358 if (lhs.pss < rhs.pss) { 15359 return 1; 15360 } else if (lhs.pss > rhs.pss) { 15361 return -1; 15362 } 15363 return 0; 15364 } 15365 }); 15366 } 15367 15368 for (int i=0; i<items.size(); i++) { 15369 MemItem mi = items.get(i); 15370 if (!isCompact) { 15371 if (dumpSwapPss) { 15372 pw.printf("%s%s: %-60s (%s in swap)\n", prefix, stringifyKBSize(mi.pss), 15373 mi.label, stringifyKBSize(mi.swapPss)); 15374 } else { 15375 pw.printf("%s%s: %s\n", prefix, stringifyKBSize(mi.pss), mi.label); 15376 } 15377 } else if (mi.isProc) { 15378 pw.print("proc,"); pw.print(tag); pw.print(","); pw.print(mi.shortLabel); 15379 pw.print(","); pw.print(mi.id); pw.print(","); pw.print(mi.pss); pw.print(","); 15380 pw.print(dumpSwapPss ? mi.swapPss : "N/A"); 15381 pw.println(mi.hasActivities ? ",a" : ",e"); 15382 } else { 15383 pw.print(tag); pw.print(","); pw.print(mi.shortLabel); pw.print(","); 15384 pw.print(mi.pss); pw.print(","); pw.println(dumpSwapPss ? mi.swapPss : "N/A"); 15385 } 15386 if (mi.subitems != null) { 15387 dumpMemItems(pw, prefix + " ", mi.shortLabel, mi.subitems, 15388 true, isCompact, dumpSwapPss); 15389 } 15390 } 15391 } 15392 15393 // These are in KB. 15394 static final long[] DUMP_MEM_BUCKETS = new long[] { 15395 5*1024, 7*1024, 10*1024, 15*1024, 20*1024, 30*1024, 40*1024, 80*1024, 15396 120*1024, 160*1024, 200*1024, 15397 250*1024, 300*1024, 350*1024, 400*1024, 500*1024, 600*1024, 800*1024, 15398 1*1024*1024, 2*1024*1024, 5*1024*1024, 10*1024*1024, 20*1024*1024 15399 }; 15400 15401 static final void appendMemBucket(StringBuilder out, long memKB, String label, 15402 boolean stackLike) { 15403 int start = label.lastIndexOf('.'); 15404 if (start >= 0) start++; 15405 else start = 0; 15406 int end = label.length(); 15407 for (int i=0; i<DUMP_MEM_BUCKETS.length; i++) { 15408 if (DUMP_MEM_BUCKETS[i] >= memKB) { 15409 long bucket = DUMP_MEM_BUCKETS[i]/1024; 15410 out.append(bucket); 15411 out.append(stackLike ? "MB." : "MB "); 15412 out.append(label, start, end); 15413 return; 15414 } 15415 } 15416 out.append(memKB/1024); 15417 out.append(stackLike ? "MB." : "MB "); 15418 out.append(label, start, end); 15419 } 15420 15421 static final int[] DUMP_MEM_OOM_ADJ = new int[] { 15422 ProcessList.NATIVE_ADJ, 15423 ProcessList.SYSTEM_ADJ, ProcessList.PERSISTENT_PROC_ADJ, 15424 ProcessList.PERSISTENT_SERVICE_ADJ, ProcessList.FOREGROUND_APP_ADJ, 15425 ProcessList.VISIBLE_APP_ADJ, ProcessList.PERCEPTIBLE_APP_ADJ, 15426 ProcessList.BACKUP_APP_ADJ, ProcessList.HEAVY_WEIGHT_APP_ADJ, 15427 ProcessList.SERVICE_ADJ, ProcessList.HOME_APP_ADJ, 15428 ProcessList.PREVIOUS_APP_ADJ, ProcessList.SERVICE_B_ADJ, ProcessList.CACHED_APP_MIN_ADJ 15429 }; 15430 static final String[] DUMP_MEM_OOM_LABEL = new String[] { 15431 "Native", 15432 "System", "Persistent", "Persistent Service", "Foreground", 15433 "Visible", "Perceptible", 15434 "Heavy Weight", "Backup", 15435 "A Services", "Home", 15436 "Previous", "B Services", "Cached" 15437 }; 15438 static final String[] DUMP_MEM_OOM_COMPACT_LABEL = new String[] { 15439 "native", 15440 "sys", "pers", "persvc", "fore", 15441 "vis", "percept", 15442 "heavy", "backup", 15443 "servicea", "home", 15444 "prev", "serviceb", "cached" 15445 }; 15446 15447 private final void dumpApplicationMemoryUsageHeader(PrintWriter pw, long uptime, 15448 long realtime, boolean isCheckinRequest, boolean isCompact) { 15449 if (isCompact) { 15450 pw.print("version,"); pw.println(MEMINFO_COMPACT_VERSION); 15451 } 15452 if (isCheckinRequest || isCompact) { 15453 // short checkin version 15454 pw.print("time,"); pw.print(uptime); pw.print(","); pw.println(realtime); 15455 } else { 15456 pw.println("Applications Memory Usage (in Kilobytes):"); 15457 pw.println("Uptime: " + uptime + " Realtime: " + realtime); 15458 } 15459 } 15460 15461 private static final int KSM_SHARED = 0; 15462 private static final int KSM_SHARING = 1; 15463 private static final int KSM_UNSHARED = 2; 15464 private static final int KSM_VOLATILE = 3; 15465 15466 private final long[] getKsmInfo() { 15467 long[] longOut = new long[4]; 15468 final int[] SINGLE_LONG_FORMAT = new int[] { 15469 Process.PROC_SPACE_TERM|Process.PROC_OUT_LONG 15470 }; 15471 long[] longTmp = new long[1]; 15472 Process.readProcFile("/sys/kernel/mm/ksm/pages_shared", 15473 SINGLE_LONG_FORMAT, null, longTmp, null); 15474 longOut[KSM_SHARED] = longTmp[0] * ProcessList.PAGE_SIZE / 1024; 15475 longTmp[0] = 0; 15476 Process.readProcFile("/sys/kernel/mm/ksm/pages_sharing", 15477 SINGLE_LONG_FORMAT, null, longTmp, null); 15478 longOut[KSM_SHARING] = longTmp[0] * ProcessList.PAGE_SIZE / 1024; 15479 longTmp[0] = 0; 15480 Process.readProcFile("/sys/kernel/mm/ksm/pages_unshared", 15481 SINGLE_LONG_FORMAT, null, longTmp, null); 15482 longOut[KSM_UNSHARED] = longTmp[0] * ProcessList.PAGE_SIZE / 1024; 15483 longTmp[0] = 0; 15484 Process.readProcFile("/sys/kernel/mm/ksm/pages_volatile", 15485 SINGLE_LONG_FORMAT, null, longTmp, null); 15486 longOut[KSM_VOLATILE] = longTmp[0] * ProcessList.PAGE_SIZE / 1024; 15487 return longOut; 15488 } 15489 15490 private static String stringifySize(long size, int order) { 15491 Locale locale = Locale.US; 15492 switch (order) { 15493 case 1: 15494 return String.format(locale, "%,13d", size); 15495 case 1024: 15496 return String.format(locale, "%,9dK", size / 1024); 15497 case 1024 * 1024: 15498 return String.format(locale, "%,5dM", size / 1024 / 1024); 15499 case 1024 * 1024 * 1024: 15500 return String.format(locale, "%,1dG", size / 1024 / 1024 / 1024); 15501 default: 15502 throw new IllegalArgumentException("Invalid size order"); 15503 } 15504 } 15505 15506 private static String stringifyKBSize(long size) { 15507 return stringifySize(size * 1024, 1024); 15508 } 15509 15510 // Update this version number in case you change the 'compact' format 15511 private static final int MEMINFO_COMPACT_VERSION = 1; 15512 15513 final void dumpApplicationMemoryUsage(FileDescriptor fd, 15514 PrintWriter pw, String prefix, String[] args, boolean brief, PrintWriter categoryPw) { 15515 boolean dumpDetails = false; 15516 boolean dumpFullDetails = false; 15517 boolean dumpDalvik = false; 15518 boolean dumpSummaryOnly = false; 15519 boolean dumpUnreachable = false; 15520 boolean oomOnly = false; 15521 boolean isCompact = false; 15522 boolean localOnly = false; 15523 boolean packages = false; 15524 boolean isCheckinRequest = false; 15525 boolean dumpSwapPss = false; 15526 15527 int opti = 0; 15528 while (opti < args.length) { 15529 String opt = args[opti]; 15530 if (opt == null || opt.length() <= 0 || opt.charAt(0) != '-') { 15531 break; 15532 } 15533 opti++; 15534 if ("-a".equals(opt)) { 15535 dumpDetails = true; 15536 dumpFullDetails = true; 15537 dumpDalvik = true; 15538 dumpSwapPss = true; 15539 } else if ("-d".equals(opt)) { 15540 dumpDalvik = true; 15541 } else if ("-c".equals(opt)) { 15542 isCompact = true; 15543 } else if ("-s".equals(opt)) { 15544 dumpDetails = true; 15545 dumpSummaryOnly = true; 15546 } else if ("-S".equals(opt)) { 15547 dumpSwapPss = true; 15548 } else if ("--unreachable".equals(opt)) { 15549 dumpUnreachable = true; 15550 } else if ("--oom".equals(opt)) { 15551 oomOnly = true; 15552 } else if ("--local".equals(opt)) { 15553 localOnly = true; 15554 } else if ("--package".equals(opt)) { 15555 packages = true; 15556 } else if ("--checkin".equals(opt)) { 15557 isCheckinRequest = true; 15558 15559 } else if ("-h".equals(opt)) { 15560 pw.println("meminfo dump options: [-a] [-d] [-c] [-s] [--oom] [process]"); 15561 pw.println(" -a: include all available information for each process."); 15562 pw.println(" -d: include dalvik details."); 15563 pw.println(" -c: dump in a compact machine-parseable representation."); 15564 pw.println(" -s: dump only summary of application memory usage."); 15565 pw.println(" -S: dump also SwapPss."); 15566 pw.println(" --oom: only show processes organized by oom adj."); 15567 pw.println(" --local: only collect details locally, don't call process."); 15568 pw.println(" --package: interpret process arg as package, dumping all"); 15569 pw.println(" processes that have loaded that package."); 15570 pw.println(" --checkin: dump data for a checkin"); 15571 pw.println("If [process] is specified it can be the name or "); 15572 pw.println("pid of a specific process to dump."); 15573 return; 15574 } else { 15575 pw.println("Unknown argument: " + opt + "; use -h for help"); 15576 } 15577 } 15578 15579 long uptime = SystemClock.uptimeMillis(); 15580 long realtime = SystemClock.elapsedRealtime(); 15581 final long[] tmpLong = new long[1]; 15582 15583 ArrayList<ProcessRecord> procs = collectProcesses(pw, opti, packages, args); 15584 if (procs == null) { 15585 // No Java processes. Maybe they want to print a native process. 15586 if (args != null && args.length > opti 15587 && args[opti].charAt(0) != '-') { 15588 ArrayList<ProcessCpuTracker.Stats> nativeProcs 15589 = new ArrayList<ProcessCpuTracker.Stats>(); 15590 updateCpuStatsNow(); 15591 int findPid = -1; 15592 try { 15593 findPid = Integer.parseInt(args[opti]); 15594 } catch (NumberFormatException e) { 15595 } 15596 synchronized (mProcessCpuTracker) { 15597 final int N = mProcessCpuTracker.countStats(); 15598 for (int i=0; i<N; i++) { 15599 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(i); 15600 if (st.pid == findPid || (st.baseName != null 15601 && st.baseName.equals(args[opti]))) { 15602 nativeProcs.add(st); 15603 } 15604 } 15605 } 15606 if (nativeProcs.size() > 0) { 15607 dumpApplicationMemoryUsageHeader(pw, uptime, realtime, isCheckinRequest, 15608 isCompact); 15609 Debug.MemoryInfo mi = null; 15610 for (int i = nativeProcs.size() - 1 ; i >= 0 ; i--) { 15611 final ProcessCpuTracker.Stats r = nativeProcs.get(i); 15612 final int pid = r.pid; 15613 if (!isCheckinRequest && dumpDetails) { 15614 pw.println("\n** MEMINFO in pid " + pid + " [" + r.baseName + "] **"); 15615 } 15616 if (mi == null) { 15617 mi = new Debug.MemoryInfo(); 15618 } 15619 if (dumpDetails || (!brief && !oomOnly)) { 15620 Debug.getMemoryInfo(pid, mi); 15621 } else { 15622 mi.dalvikPss = (int)Debug.getPss(pid, tmpLong, null); 15623 mi.dalvikPrivateDirty = (int)tmpLong[0]; 15624 } 15625 ActivityThread.dumpMemInfoTable(pw, mi, isCheckinRequest, dumpFullDetails, 15626 dumpDalvik, dumpSummaryOnly, pid, r.baseName, 0, 0, 0, 0, 0, 0); 15627 if (isCheckinRequest) { 15628 pw.println(); 15629 } 15630 } 15631 return; 15632 } 15633 } 15634 pw.println("No process found for: " + args[opti]); 15635 return; 15636 } 15637 15638 if (!brief && !oomOnly && (procs.size() == 1 || isCheckinRequest || packages)) { 15639 dumpDetails = true; 15640 } 15641 15642 dumpApplicationMemoryUsageHeader(pw, uptime, realtime, isCheckinRequest, isCompact); 15643 15644 String[] innerArgs = new String[args.length-opti]; 15645 System.arraycopy(args, opti, innerArgs, 0, args.length-opti); 15646 15647 ArrayList<MemItem> procMems = new ArrayList<MemItem>(); 15648 final SparseArray<MemItem> procMemsMap = new SparseArray<MemItem>(); 15649 long nativePss = 0; 15650 long nativeSwapPss = 0; 15651 long dalvikPss = 0; 15652 long dalvikSwapPss = 0; 15653 long[] dalvikSubitemPss = dumpDalvik ? new long[Debug.MemoryInfo.NUM_DVK_STATS] : 15654 EmptyArray.LONG; 15655 long[] dalvikSubitemSwapPss = dumpDalvik ? new long[Debug.MemoryInfo.NUM_DVK_STATS] : 15656 EmptyArray.LONG; 15657 long otherPss = 0; 15658 long otherSwapPss = 0; 15659 long[] miscPss = new long[Debug.MemoryInfo.NUM_OTHER_STATS]; 15660 long[] miscSwapPss = new long[Debug.MemoryInfo.NUM_OTHER_STATS]; 15661 15662 long oomPss[] = new long[DUMP_MEM_OOM_LABEL.length]; 15663 long oomSwapPss[] = new long[DUMP_MEM_OOM_LABEL.length]; 15664 ArrayList<MemItem>[] oomProcs = (ArrayList<MemItem>[]) 15665 new ArrayList[DUMP_MEM_OOM_LABEL.length]; 15666 15667 long totalPss = 0; 15668 long totalSwapPss = 0; 15669 long cachedPss = 0; 15670 long cachedSwapPss = 0; 15671 boolean hasSwapPss = false; 15672 15673 Debug.MemoryInfo mi = null; 15674 for (int i = procs.size() - 1 ; i >= 0 ; i--) { 15675 final ProcessRecord r = procs.get(i); 15676 final IApplicationThread thread; 15677 final int pid; 15678 final int oomAdj; 15679 final boolean hasActivities; 15680 synchronized (this) { 15681 thread = r.thread; 15682 pid = r.pid; 15683 oomAdj = r.getSetAdjWithServices(); 15684 hasActivities = r.activities.size() > 0; 15685 } 15686 if (thread != null) { 15687 if (!isCheckinRequest && dumpDetails) { 15688 pw.println("\n** MEMINFO in pid " + pid + " [" + r.processName + "] **"); 15689 } 15690 if (mi == null) { 15691 mi = new Debug.MemoryInfo(); 15692 } 15693 if (dumpDetails || (!brief && !oomOnly)) { 15694 Debug.getMemoryInfo(pid, mi); 15695 hasSwapPss = mi.hasSwappedOutPss; 15696 } else { 15697 mi.dalvikPss = (int)Debug.getPss(pid, tmpLong, null); 15698 mi.dalvikPrivateDirty = (int)tmpLong[0]; 15699 } 15700 if (dumpDetails) { 15701 if (localOnly) { 15702 ActivityThread.dumpMemInfoTable(pw, mi, isCheckinRequest, dumpFullDetails, 15703 dumpDalvik, dumpSummaryOnly, pid, r.processName, 0, 0, 0, 0, 0, 0); 15704 if (isCheckinRequest) { 15705 pw.println(); 15706 } 15707 } else { 15708 try { 15709 pw.flush(); 15710 thread.dumpMemInfo(fd, mi, isCheckinRequest, dumpFullDetails, 15711 dumpDalvik, dumpSummaryOnly, dumpUnreachable, innerArgs); 15712 } catch (RemoteException e) { 15713 if (!isCheckinRequest) { 15714 pw.println("Got RemoteException!"); 15715 pw.flush(); 15716 } 15717 } 15718 } 15719 } 15720 15721 final long myTotalPss = mi.getTotalPss(); 15722 final long myTotalUss = mi.getTotalUss(); 15723 final long myTotalSwapPss = mi.getTotalSwappedOutPss(); 15724 15725 synchronized (this) { 15726 if (r.thread != null && oomAdj == r.getSetAdjWithServices()) { 15727 // Record this for posterity if the process has been stable. 15728 r.baseProcessTracker.addPss(myTotalPss, myTotalUss, true, r.pkgList); 15729 } 15730 } 15731 15732 if (!isCheckinRequest && mi != null) { 15733 totalPss += myTotalPss; 15734 totalSwapPss += myTotalSwapPss; 15735 MemItem pssItem = new MemItem(r.processName + " (pid " + pid + 15736 (hasActivities ? " / activities)" : ")"), r.processName, myTotalPss, 15737 myTotalSwapPss, pid, hasActivities); 15738 procMems.add(pssItem); 15739 procMemsMap.put(pid, pssItem); 15740 15741 nativePss += mi.nativePss; 15742 nativeSwapPss += mi.nativeSwappedOutPss; 15743 dalvikPss += mi.dalvikPss; 15744 dalvikSwapPss += mi.dalvikSwappedOutPss; 15745 for (int j=0; j<dalvikSubitemPss.length; j++) { 15746 dalvikSubitemPss[j] += mi.getOtherPss(Debug.MemoryInfo.NUM_OTHER_STATS + j); 15747 dalvikSubitemSwapPss[j] += 15748 mi.getOtherSwappedOutPss(Debug.MemoryInfo.NUM_OTHER_STATS + j); 15749 } 15750 otherPss += mi.otherPss; 15751 otherSwapPss += mi.otherSwappedOutPss; 15752 for (int j=0; j<Debug.MemoryInfo.NUM_OTHER_STATS; j++) { 15753 long mem = mi.getOtherPss(j); 15754 miscPss[j] += mem; 15755 otherPss -= mem; 15756 mem = mi.getOtherSwappedOutPss(j); 15757 miscSwapPss[j] += mem; 15758 otherSwapPss -= mem; 15759 } 15760 15761 if (oomAdj >= ProcessList.CACHED_APP_MIN_ADJ) { 15762 cachedPss += myTotalPss; 15763 cachedSwapPss += myTotalSwapPss; 15764 } 15765 15766 for (int oomIndex=0; oomIndex<oomPss.length; oomIndex++) { 15767 if (oomIndex == (oomPss.length - 1) 15768 || (oomAdj >= DUMP_MEM_OOM_ADJ[oomIndex] 15769 && oomAdj < DUMP_MEM_OOM_ADJ[oomIndex + 1])) { 15770 oomPss[oomIndex] += myTotalPss; 15771 oomSwapPss[oomIndex] += myTotalSwapPss; 15772 if (oomProcs[oomIndex] == null) { 15773 oomProcs[oomIndex] = new ArrayList<MemItem>(); 15774 } 15775 oomProcs[oomIndex].add(pssItem); 15776 break; 15777 } 15778 } 15779 } 15780 } 15781 } 15782 15783 long nativeProcTotalPss = 0; 15784 15785 if (!isCheckinRequest && procs.size() > 1 && !packages) { 15786 // If we are showing aggregations, also look for native processes to 15787 // include so that our aggregations are more accurate. 15788 updateCpuStatsNow(); 15789 mi = null; 15790 synchronized (mProcessCpuTracker) { 15791 final int N = mProcessCpuTracker.countStats(); 15792 for (int i=0; i<N; i++) { 15793 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(i); 15794 if (st.vsize > 0 && procMemsMap.indexOfKey(st.pid) < 0) { 15795 if (mi == null) { 15796 mi = new Debug.MemoryInfo(); 15797 } 15798 if (!brief && !oomOnly) { 15799 Debug.getMemoryInfo(st.pid, mi); 15800 } else { 15801 mi.nativePss = (int)Debug.getPss(st.pid, tmpLong, null); 15802 mi.nativePrivateDirty = (int)tmpLong[0]; 15803 } 15804 15805 final long myTotalPss = mi.getTotalPss(); 15806 final long myTotalSwapPss = mi.getTotalSwappedOutPss(); 15807 totalPss += myTotalPss; 15808 nativeProcTotalPss += myTotalPss; 15809 15810 MemItem pssItem = new MemItem(st.name + " (pid " + st.pid + ")", 15811 st.name, myTotalPss, mi.getSummaryTotalSwapPss(), st.pid, false); 15812 procMems.add(pssItem); 15813 15814 nativePss += mi.nativePss; 15815 nativeSwapPss += mi.nativeSwappedOutPss; 15816 dalvikPss += mi.dalvikPss; 15817 dalvikSwapPss += mi.dalvikSwappedOutPss; 15818 for (int j=0; j<dalvikSubitemPss.length; j++) { 15819 dalvikSubitemPss[j] += mi.getOtherPss(Debug.MemoryInfo.NUM_OTHER_STATS + j); 15820 dalvikSubitemSwapPss[j] += 15821 mi.getOtherSwappedOutPss(Debug.MemoryInfo.NUM_OTHER_STATS + j); 15822 } 15823 otherPss += mi.otherPss; 15824 otherSwapPss += mi.otherSwappedOutPss; 15825 for (int j=0; j<Debug.MemoryInfo.NUM_OTHER_STATS; j++) { 15826 long mem = mi.getOtherPss(j); 15827 miscPss[j] += mem; 15828 otherPss -= mem; 15829 mem = mi.getOtherSwappedOutPss(j); 15830 miscSwapPss[j] += mem; 15831 otherSwapPss -= mem; 15832 } 15833 oomPss[0] += myTotalPss; 15834 oomSwapPss[0] += myTotalSwapPss; 15835 if (oomProcs[0] == null) { 15836 oomProcs[0] = new ArrayList<MemItem>(); 15837 } 15838 oomProcs[0].add(pssItem); 15839 } 15840 } 15841 } 15842 15843 ArrayList<MemItem> catMems = new ArrayList<MemItem>(); 15844 15845 catMems.add(new MemItem("Native", "Native", nativePss, nativeSwapPss, -1)); 15846 final MemItem dalvikItem = 15847 new MemItem("Dalvik", "Dalvik", dalvikPss, dalvikSwapPss, -2); 15848 if (dalvikSubitemPss.length > 0) { 15849 dalvikItem.subitems = new ArrayList<MemItem>(); 15850 for (int j=0; j<dalvikSubitemPss.length; j++) { 15851 final String name = Debug.MemoryInfo.getOtherLabel( 15852 Debug.MemoryInfo.NUM_OTHER_STATS + j); 15853 dalvikItem.subitems.add(new MemItem(name, name, dalvikSubitemPss[j], 15854 dalvikSubitemSwapPss[j], j)); 15855 } 15856 } 15857 catMems.add(dalvikItem); 15858 catMems.add(new MemItem("Unknown", "Unknown", otherPss, otherSwapPss, -3)); 15859 for (int j=0; j<Debug.MemoryInfo.NUM_OTHER_STATS; j++) { 15860 String label = Debug.MemoryInfo.getOtherLabel(j); 15861 catMems.add(new MemItem(label, label, miscPss[j], miscSwapPss[j], j)); 15862 } 15863 15864 ArrayList<MemItem> oomMems = new ArrayList<MemItem>(); 15865 for (int j=0; j<oomPss.length; j++) { 15866 if (oomPss[j] != 0) { 15867 String label = isCompact ? DUMP_MEM_OOM_COMPACT_LABEL[j] 15868 : DUMP_MEM_OOM_LABEL[j]; 15869 MemItem item = new MemItem(label, label, oomPss[j], oomSwapPss[j], 15870 DUMP_MEM_OOM_ADJ[j]); 15871 item.subitems = oomProcs[j]; 15872 oomMems.add(item); 15873 } 15874 } 15875 15876 dumpSwapPss = dumpSwapPss && hasSwapPss && totalSwapPss != 0; 15877 if (!brief && !oomOnly && !isCompact) { 15878 pw.println(); 15879 pw.println("Total PSS by process:"); 15880 dumpMemItems(pw, " ", "proc", procMems, true, isCompact, dumpSwapPss); 15881 pw.println(); 15882 } 15883 if (!isCompact) { 15884 pw.println("Total PSS by OOM adjustment:"); 15885 } 15886 dumpMemItems(pw, " ", "oom", oomMems, false, isCompact, dumpSwapPss); 15887 if (!brief && !oomOnly) { 15888 PrintWriter out = categoryPw != null ? categoryPw : pw; 15889 if (!isCompact) { 15890 out.println(); 15891 out.println("Total PSS by category:"); 15892 } 15893 dumpMemItems(out, " ", "cat", catMems, true, isCompact, dumpSwapPss); 15894 } 15895 if (!isCompact) { 15896 pw.println(); 15897 } 15898 MemInfoReader memInfo = new MemInfoReader(); 15899 memInfo.readMemInfo(); 15900 if (nativeProcTotalPss > 0) { 15901 synchronized (this) { 15902 final long cachedKb = memInfo.getCachedSizeKb(); 15903 final long freeKb = memInfo.getFreeSizeKb(); 15904 final long zramKb = memInfo.getZramTotalSizeKb(); 15905 final long kernelKb = memInfo.getKernelUsedSizeKb(); 15906 EventLogTags.writeAmMeminfo(cachedKb*1024, freeKb*1024, zramKb*1024, 15907 kernelKb*1024, nativeProcTotalPss*1024); 15908 mProcessStats.addSysMemUsageLocked(cachedKb, freeKb, zramKb, kernelKb, 15909 nativeProcTotalPss); 15910 } 15911 } 15912 if (!brief) { 15913 if (!isCompact) { 15914 pw.print("Total RAM: "); pw.print(stringifyKBSize(memInfo.getTotalSizeKb())); 15915 pw.print(" (status "); 15916 switch (mLastMemoryLevel) { 15917 case ProcessStats.ADJ_MEM_FACTOR_NORMAL: 15918 pw.println("normal)"); 15919 break; 15920 case ProcessStats.ADJ_MEM_FACTOR_MODERATE: 15921 pw.println("moderate)"); 15922 break; 15923 case ProcessStats.ADJ_MEM_FACTOR_LOW: 15924 pw.println("low)"); 15925 break; 15926 case ProcessStats.ADJ_MEM_FACTOR_CRITICAL: 15927 pw.println("critical)"); 15928 break; 15929 default: 15930 pw.print(mLastMemoryLevel); 15931 pw.println(")"); 15932 break; 15933 } 15934 pw.print(" Free RAM: "); 15935 pw.print(stringifyKBSize(cachedPss + memInfo.getCachedSizeKb() 15936 + memInfo.getFreeSizeKb())); 15937 pw.print(" ("); 15938 pw.print(stringifyKBSize(cachedPss)); 15939 pw.print(" cached pss + "); 15940 pw.print(stringifyKBSize(memInfo.getCachedSizeKb())); 15941 pw.print(" cached kernel + "); 15942 pw.print(stringifyKBSize(memInfo.getFreeSizeKb())); 15943 pw.println(" free)"); 15944 } else { 15945 pw.print("ram,"); pw.print(memInfo.getTotalSizeKb()); pw.print(","); 15946 pw.print(cachedPss + memInfo.getCachedSizeKb() 15947 + memInfo.getFreeSizeKb()); pw.print(","); 15948 pw.println(totalPss - cachedPss); 15949 } 15950 } 15951 long lostRAM = memInfo.getTotalSizeKb() - (totalPss - totalSwapPss) 15952 - memInfo.getFreeSizeKb() - memInfo.getCachedSizeKb() 15953 - memInfo.getKernelUsedSizeKb() - memInfo.getZramTotalSizeKb(); 15954 if (!isCompact) { 15955 pw.print(" Used RAM: "); pw.print(stringifyKBSize(totalPss - cachedPss 15956 + memInfo.getKernelUsedSizeKb())); pw.print(" ("); 15957 pw.print(stringifyKBSize(totalPss - cachedPss)); pw.print(" used pss + "); 15958 pw.print(stringifyKBSize(memInfo.getKernelUsedSizeKb())); pw.print(" kernel)\n"); 15959 pw.print(" Lost RAM: "); pw.println(stringifyKBSize(lostRAM)); 15960 } else { 15961 pw.print("lostram,"); pw.println(lostRAM); 15962 } 15963 if (!brief) { 15964 if (memInfo.getZramTotalSizeKb() != 0) { 15965 if (!isCompact) { 15966 pw.print(" ZRAM: "); 15967 pw.print(stringifyKBSize(memInfo.getZramTotalSizeKb())); 15968 pw.print(" physical used for "); 15969 pw.print(stringifyKBSize(memInfo.getSwapTotalSizeKb() 15970 - memInfo.getSwapFreeSizeKb())); 15971 pw.print(" in swap ("); 15972 pw.print(stringifyKBSize(memInfo.getSwapTotalSizeKb())); 15973 pw.println(" total swap)"); 15974 } else { 15975 pw.print("zram,"); pw.print(memInfo.getZramTotalSizeKb()); pw.print(","); 15976 pw.print(memInfo.getSwapTotalSizeKb()); pw.print(","); 15977 pw.println(memInfo.getSwapFreeSizeKb()); 15978 } 15979 } 15980 final long[] ksm = getKsmInfo(); 15981 if (!isCompact) { 15982 if (ksm[KSM_SHARING] != 0 || ksm[KSM_SHARED] != 0 || ksm[KSM_UNSHARED] != 0 15983 || ksm[KSM_VOLATILE] != 0) { 15984 pw.print(" KSM: "); pw.print(stringifyKBSize(ksm[KSM_SHARING])); 15985 pw.print(" saved from shared "); 15986 pw.print(stringifyKBSize(ksm[KSM_SHARED])); 15987 pw.print(" "); pw.print(stringifyKBSize(ksm[KSM_UNSHARED])); 15988 pw.print(" unshared; "); 15989 pw.print(stringifyKBSize( 15990 ksm[KSM_VOLATILE])); pw.println(" volatile"); 15991 } 15992 pw.print(" Tuning: "); 15993 pw.print(ActivityManager.staticGetMemoryClass()); 15994 pw.print(" (large "); 15995 pw.print(ActivityManager.staticGetLargeMemoryClass()); 15996 pw.print("), oom "); 15997 pw.print(stringifySize( 15998 mProcessList.getMemLevel(ProcessList.CACHED_APP_MAX_ADJ), 1024)); 15999 pw.print(", restore limit "); 16000 pw.print(stringifyKBSize(mProcessList.getCachedRestoreThresholdKb())); 16001 if (ActivityManager.isLowRamDeviceStatic()) { 16002 pw.print(" (low-ram)"); 16003 } 16004 if (ActivityManager.isHighEndGfx()) { 16005 pw.print(" (high-end-gfx)"); 16006 } 16007 pw.println(); 16008 } else { 16009 pw.print("ksm,"); pw.print(ksm[KSM_SHARING]); pw.print(","); 16010 pw.print(ksm[KSM_SHARED]); pw.print(","); pw.print(ksm[KSM_UNSHARED]); 16011 pw.print(","); pw.println(ksm[KSM_VOLATILE]); 16012 pw.print("tuning,"); 16013 pw.print(ActivityManager.staticGetMemoryClass()); 16014 pw.print(','); 16015 pw.print(ActivityManager.staticGetLargeMemoryClass()); 16016 pw.print(','); 16017 pw.print(mProcessList.getMemLevel(ProcessList.CACHED_APP_MAX_ADJ)/1024); 16018 if (ActivityManager.isLowRamDeviceStatic()) { 16019 pw.print(",low-ram"); 16020 } 16021 if (ActivityManager.isHighEndGfx()) { 16022 pw.print(",high-end-gfx"); 16023 } 16024 pw.println(); 16025 } 16026 } 16027 } 16028 } 16029 16030 private void appendBasicMemEntry(StringBuilder sb, int oomAdj, int procState, long pss, 16031 long memtrack, String name) { 16032 sb.append(" "); 16033 sb.append(ProcessList.makeOomAdjString(oomAdj)); 16034 sb.append(' '); 16035 sb.append(ProcessList.makeProcStateString(procState)); 16036 sb.append(' '); 16037 ProcessList.appendRamKb(sb, pss); 16038 sb.append(": "); 16039 sb.append(name); 16040 if (memtrack > 0) { 16041 sb.append(" ("); 16042 sb.append(stringifyKBSize(memtrack)); 16043 sb.append(" memtrack)"); 16044 } 16045 } 16046 16047 private void appendMemInfo(StringBuilder sb, ProcessMemInfo mi) { 16048 appendBasicMemEntry(sb, mi.oomAdj, mi.procState, mi.pss, mi.memtrack, mi.name); 16049 sb.append(" (pid "); 16050 sb.append(mi.pid); 16051 sb.append(") "); 16052 sb.append(mi.adjType); 16053 sb.append('\n'); 16054 if (mi.adjReason != null) { 16055 sb.append(" "); 16056 sb.append(mi.adjReason); 16057 sb.append('\n'); 16058 } 16059 } 16060 16061 void reportMemUsage(ArrayList<ProcessMemInfo> memInfos) { 16062 final SparseArray<ProcessMemInfo> infoMap = new SparseArray<>(memInfos.size()); 16063 for (int i=0, N=memInfos.size(); i<N; i++) { 16064 ProcessMemInfo mi = memInfos.get(i); 16065 infoMap.put(mi.pid, mi); 16066 } 16067 updateCpuStatsNow(); 16068 long[] memtrackTmp = new long[1]; 16069 synchronized (mProcessCpuTracker) { 16070 final int N = mProcessCpuTracker.countStats(); 16071 for (int i=0; i<N; i++) { 16072 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(i); 16073 if (st.vsize > 0) { 16074 long pss = Debug.getPss(st.pid, null, memtrackTmp); 16075 if (pss > 0) { 16076 if (infoMap.indexOfKey(st.pid) < 0) { 16077 ProcessMemInfo mi = new ProcessMemInfo(st.name, st.pid, 16078 ProcessList.NATIVE_ADJ, -1, "native", null); 16079 mi.pss = pss; 16080 mi.memtrack = memtrackTmp[0]; 16081 memInfos.add(mi); 16082 } 16083 } 16084 } 16085 } 16086 } 16087 16088 long totalPss = 0; 16089 long totalMemtrack = 0; 16090 for (int i=0, N=memInfos.size(); i<N; i++) { 16091 ProcessMemInfo mi = memInfos.get(i); 16092 if (mi.pss == 0) { 16093 mi.pss = Debug.getPss(mi.pid, null, memtrackTmp); 16094 mi.memtrack = memtrackTmp[0]; 16095 } 16096 totalPss += mi.pss; 16097 totalMemtrack += mi.memtrack; 16098 } 16099 Collections.sort(memInfos, new Comparator<ProcessMemInfo>() { 16100 @Override public int compare(ProcessMemInfo lhs, ProcessMemInfo rhs) { 16101 if (lhs.oomAdj != rhs.oomAdj) { 16102 return lhs.oomAdj < rhs.oomAdj ? -1 : 1; 16103 } 16104 if (lhs.pss != rhs.pss) { 16105 return lhs.pss < rhs.pss ? 1 : -1; 16106 } 16107 return 0; 16108 } 16109 }); 16110 16111 StringBuilder tag = new StringBuilder(128); 16112 StringBuilder stack = new StringBuilder(128); 16113 tag.append("Low on memory -- "); 16114 appendMemBucket(tag, totalPss, "total", false); 16115 appendMemBucket(stack, totalPss, "total", true); 16116 16117 StringBuilder fullNativeBuilder = new StringBuilder(1024); 16118 StringBuilder shortNativeBuilder = new StringBuilder(1024); 16119 StringBuilder fullJavaBuilder = new StringBuilder(1024); 16120 16121 boolean firstLine = true; 16122 int lastOomAdj = Integer.MIN_VALUE; 16123 long extraNativeRam = 0; 16124 long extraNativeMemtrack = 0; 16125 long cachedPss = 0; 16126 for (int i=0, N=memInfos.size(); i<N; i++) { 16127 ProcessMemInfo mi = memInfos.get(i); 16128 16129 if (mi.oomAdj >= ProcessList.CACHED_APP_MIN_ADJ) { 16130 cachedPss += mi.pss; 16131 } 16132 16133 if (mi.oomAdj != ProcessList.NATIVE_ADJ 16134 && (mi.oomAdj < ProcessList.SERVICE_ADJ 16135 || mi.oomAdj == ProcessList.HOME_APP_ADJ 16136 || mi.oomAdj == ProcessList.PREVIOUS_APP_ADJ)) { 16137 if (lastOomAdj != mi.oomAdj) { 16138 lastOomAdj = mi.oomAdj; 16139 if (mi.oomAdj <= ProcessList.FOREGROUND_APP_ADJ) { 16140 tag.append(" / "); 16141 } 16142 if (mi.oomAdj >= ProcessList.FOREGROUND_APP_ADJ) { 16143 if (firstLine) { 16144 stack.append(":"); 16145 firstLine = false; 16146 } 16147 stack.append("\n\t at "); 16148 } else { 16149 stack.append("$"); 16150 } 16151 } else { 16152 tag.append(" "); 16153 stack.append("$"); 16154 } 16155 if (mi.oomAdj <= ProcessList.FOREGROUND_APP_ADJ) { 16156 appendMemBucket(tag, mi.pss, mi.name, false); 16157 } 16158 appendMemBucket(stack, mi.pss, mi.name, true); 16159 if (mi.oomAdj >= ProcessList.FOREGROUND_APP_ADJ 16160 && ((i+1) >= N || memInfos.get(i+1).oomAdj != lastOomAdj)) { 16161 stack.append("("); 16162 for (int k=0; k<DUMP_MEM_OOM_ADJ.length; k++) { 16163 if (DUMP_MEM_OOM_ADJ[k] == mi.oomAdj) { 16164 stack.append(DUMP_MEM_OOM_LABEL[k]); 16165 stack.append(":"); 16166 stack.append(DUMP_MEM_OOM_ADJ[k]); 16167 } 16168 } 16169 stack.append(")"); 16170 } 16171 } 16172 16173 appendMemInfo(fullNativeBuilder, mi); 16174 if (mi.oomAdj == ProcessList.NATIVE_ADJ) { 16175 // The short form only has native processes that are >= 512K. 16176 if (mi.pss >= 512) { 16177 appendMemInfo(shortNativeBuilder, mi); 16178 } else { 16179 extraNativeRam += mi.pss; 16180 extraNativeMemtrack += mi.memtrack; 16181 } 16182 } else { 16183 // Short form has all other details, but if we have collected RAM 16184 // from smaller native processes let's dump a summary of that. 16185 if (extraNativeRam > 0) { 16186 appendBasicMemEntry(shortNativeBuilder, ProcessList.NATIVE_ADJ, 16187 -1, extraNativeRam, extraNativeMemtrack, "(Other native)"); 16188 shortNativeBuilder.append('\n'); 16189 extraNativeRam = 0; 16190 } 16191 appendMemInfo(fullJavaBuilder, mi); 16192 } 16193 } 16194 16195 fullJavaBuilder.append(" "); 16196 ProcessList.appendRamKb(fullJavaBuilder, totalPss); 16197 fullJavaBuilder.append(": TOTAL"); 16198 if (totalMemtrack > 0) { 16199 fullJavaBuilder.append(" ("); 16200 fullJavaBuilder.append(stringifyKBSize(totalMemtrack)); 16201 fullJavaBuilder.append(" memtrack)"); 16202 } else { 16203 } 16204 fullJavaBuilder.append("\n"); 16205 16206 MemInfoReader memInfo = new MemInfoReader(); 16207 memInfo.readMemInfo(); 16208 final long[] infos = memInfo.getRawInfo(); 16209 16210 StringBuilder memInfoBuilder = new StringBuilder(1024); 16211 Debug.getMemInfo(infos); 16212 memInfoBuilder.append(" MemInfo: "); 16213 memInfoBuilder.append(stringifyKBSize(infos[Debug.MEMINFO_SLAB])).append(" slab, "); 16214 memInfoBuilder.append(stringifyKBSize(infos[Debug.MEMINFO_SHMEM])).append(" shmem, "); 16215 memInfoBuilder.append(stringifyKBSize( 16216 infos[Debug.MEMINFO_VM_ALLOC_USED])).append(" vm alloc, "); 16217 memInfoBuilder.append(stringifyKBSize( 16218 infos[Debug.MEMINFO_PAGE_TABLES])).append(" page tables "); 16219 memInfoBuilder.append(stringifyKBSize( 16220 infos[Debug.MEMINFO_KERNEL_STACK])).append(" kernel stack\n"); 16221 memInfoBuilder.append(" "); 16222 memInfoBuilder.append(stringifyKBSize(infos[Debug.MEMINFO_BUFFERS])).append(" buffers, "); 16223 memInfoBuilder.append(stringifyKBSize(infos[Debug.MEMINFO_CACHED])).append(" cached, "); 16224 memInfoBuilder.append(stringifyKBSize(infos[Debug.MEMINFO_MAPPED])).append(" mapped, "); 16225 memInfoBuilder.append(stringifyKBSize(infos[Debug.MEMINFO_FREE])).append(" free\n"); 16226 if (infos[Debug.MEMINFO_ZRAM_TOTAL] != 0) { 16227 memInfoBuilder.append(" ZRAM: "); 16228 memInfoBuilder.append(stringifyKBSize(infos[Debug.MEMINFO_ZRAM_TOTAL])); 16229 memInfoBuilder.append(" RAM, "); 16230 memInfoBuilder.append(stringifyKBSize(infos[Debug.MEMINFO_SWAP_TOTAL])); 16231 memInfoBuilder.append(" swap total, "); 16232 memInfoBuilder.append(stringifyKBSize(infos[Debug.MEMINFO_SWAP_FREE])); 16233 memInfoBuilder.append(" swap free\n"); 16234 } 16235 final long[] ksm = getKsmInfo(); 16236 if (ksm[KSM_SHARING] != 0 || ksm[KSM_SHARED] != 0 || ksm[KSM_UNSHARED] != 0 16237 || ksm[KSM_VOLATILE] != 0) { 16238 memInfoBuilder.append(" KSM: "); 16239 memInfoBuilder.append(stringifyKBSize(ksm[KSM_SHARING])); 16240 memInfoBuilder.append(" saved from shared "); 16241 memInfoBuilder.append(stringifyKBSize(ksm[KSM_SHARED])); 16242 memInfoBuilder.append("\n "); 16243 memInfoBuilder.append(stringifyKBSize(ksm[KSM_UNSHARED])); 16244 memInfoBuilder.append(" unshared; "); 16245 memInfoBuilder.append(stringifyKBSize(ksm[KSM_VOLATILE])); 16246 memInfoBuilder.append(" volatile\n"); 16247 } 16248 memInfoBuilder.append(" Free RAM: "); 16249 memInfoBuilder.append(stringifyKBSize(cachedPss + memInfo.getCachedSizeKb() 16250 + memInfo.getFreeSizeKb())); 16251 memInfoBuilder.append("\n"); 16252 memInfoBuilder.append(" Used RAM: "); 16253 memInfoBuilder.append(stringifyKBSize( 16254 totalPss - cachedPss + memInfo.getKernelUsedSizeKb())); 16255 memInfoBuilder.append("\n"); 16256 memInfoBuilder.append(" Lost RAM: "); 16257 memInfoBuilder.append(stringifyKBSize(memInfo.getTotalSizeKb() 16258 - totalPss - memInfo.getFreeSizeKb() - memInfo.getCachedSizeKb() 16259 - memInfo.getKernelUsedSizeKb() - memInfo.getZramTotalSizeKb())); 16260 memInfoBuilder.append("\n"); 16261 Slog.i(TAG, "Low on memory:"); 16262 Slog.i(TAG, shortNativeBuilder.toString()); 16263 Slog.i(TAG, fullJavaBuilder.toString()); 16264 Slog.i(TAG, memInfoBuilder.toString()); 16265 16266 StringBuilder dropBuilder = new StringBuilder(1024); 16267 /* 16268 StringWriter oomSw = new StringWriter(); 16269 PrintWriter oomPw = new FastPrintWriter(oomSw, false, 256); 16270 StringWriter catSw = new StringWriter(); 16271 PrintWriter catPw = new FastPrintWriter(catSw, false, 256); 16272 String[] emptyArgs = new String[] { }; 16273 dumpApplicationMemoryUsage(null, oomPw, " ", emptyArgs, true, catPw); 16274 oomPw.flush(); 16275 String oomString = oomSw.toString(); 16276 */ 16277 dropBuilder.append("Low on memory:"); 16278 dropBuilder.append(stack); 16279 dropBuilder.append('\n'); 16280 dropBuilder.append(fullNativeBuilder); 16281 dropBuilder.append(fullJavaBuilder); 16282 dropBuilder.append('\n'); 16283 dropBuilder.append(memInfoBuilder); 16284 dropBuilder.append('\n'); 16285 /* 16286 dropBuilder.append(oomString); 16287 dropBuilder.append('\n'); 16288 */ 16289 StringWriter catSw = new StringWriter(); 16290 synchronized (ActivityManagerService.this) { 16291 PrintWriter catPw = new FastPrintWriter(catSw, false, 256); 16292 String[] emptyArgs = new String[] { }; 16293 catPw.println(); 16294 dumpProcessesLocked(null, catPw, emptyArgs, 0, false, null); 16295 catPw.println(); 16296 mServices.newServiceDumperLocked(null, catPw, emptyArgs, 0, 16297 false, null).dumpLocked(); 16298 catPw.println(); 16299 dumpActivitiesLocked(null, catPw, emptyArgs, 0, false, false, null); 16300 catPw.flush(); 16301 } 16302 dropBuilder.append(catSw.toString()); 16303 addErrorToDropBox("lowmem", null, "system_server", null, 16304 null, tag.toString(), dropBuilder.toString(), null, null); 16305 //Slog.i(TAG, "Sent to dropbox:"); 16306 //Slog.i(TAG, dropBuilder.toString()); 16307 synchronized (ActivityManagerService.this) { 16308 long now = SystemClock.uptimeMillis(); 16309 if (mLastMemUsageReportTime < now) { 16310 mLastMemUsageReportTime = now; 16311 } 16312 } 16313 } 16314 16315 /** 16316 * Searches array of arguments for the specified string 16317 * @param args array of argument strings 16318 * @param value value to search for 16319 * @return true if the value is contained in the array 16320 */ 16321 private static boolean scanArgs(String[] args, String value) { 16322 if (args != null) { 16323 for (String arg : args) { 16324 if (value.equals(arg)) { 16325 return true; 16326 } 16327 } 16328 } 16329 return false; 16330 } 16331 16332 private final boolean removeDyingProviderLocked(ProcessRecord proc, 16333 ContentProviderRecord cpr, boolean always) { 16334 final boolean inLaunching = mLaunchingProviders.contains(cpr); 16335 16336 if (!inLaunching || always) { 16337 synchronized (cpr) { 16338 cpr.launchingApp = null; 16339 cpr.notifyAll(); 16340 } 16341 mProviderMap.removeProviderByClass(cpr.name, UserHandle.getUserId(cpr.uid)); 16342 String names[] = cpr.info.authority.split(";"); 16343 for (int j = 0; j < names.length; j++) { 16344 mProviderMap.removeProviderByName(names[j], UserHandle.getUserId(cpr.uid)); 16345 } 16346 } 16347 16348 for (int i = cpr.connections.size() - 1; i >= 0; i--) { 16349 ContentProviderConnection conn = cpr.connections.get(i); 16350 if (conn.waiting) { 16351 // If this connection is waiting for the provider, then we don't 16352 // need to mess with its process unless we are always removing 16353 // or for some reason the provider is not currently launching. 16354 if (inLaunching && !always) { 16355 continue; 16356 } 16357 } 16358 ProcessRecord capp = conn.client; 16359 conn.dead = true; 16360 if (conn.stableCount > 0) { 16361 if (!capp.persistent && capp.thread != null 16362 && capp.pid != 0 16363 && capp.pid != MY_PID) { 16364 capp.kill("depends on provider " 16365 + cpr.name.flattenToShortString() 16366 + " in dying proc " + (proc != null ? proc.processName : "??"), true); 16367 } 16368 } else if (capp.thread != null && conn.provider.provider != null) { 16369 try { 16370 capp.thread.unstableProviderDied(conn.provider.provider.asBinder()); 16371 } catch (RemoteException e) { 16372 } 16373 // In the protocol here, we don't expect the client to correctly 16374 // clean up this connection, we'll just remove it. 16375 cpr.connections.remove(i); 16376 if (conn.client.conProviders.remove(conn)) { 16377 stopAssociationLocked(capp.uid, capp.processName, cpr.uid, cpr.name); 16378 } 16379 } 16380 } 16381 16382 if (inLaunching && always) { 16383 mLaunchingProviders.remove(cpr); 16384 } 16385 return inLaunching; 16386 } 16387 16388 /** 16389 * Main code for cleaning up a process when it has gone away. This is 16390 * called both as a result of the process dying, or directly when stopping 16391 * a process when running in single process mode. 16392 * 16393 * @return Returns true if the given process has been restarted, so the 16394 * app that was passed in must remain on the process lists. 16395 */ 16396 private final boolean cleanUpApplicationRecordLocked(ProcessRecord app, 16397 boolean restarting, boolean allowRestart, int index) { 16398 if (index >= 0) { 16399 removeLruProcessLocked(app); 16400 ProcessList.remove(app.pid); 16401 } 16402 16403 mProcessesToGc.remove(app); 16404 mPendingPssProcesses.remove(app); 16405 16406 // Dismiss any open dialogs. 16407 if (app.crashDialog != null && !app.forceCrashReport) { 16408 app.crashDialog.dismiss(); 16409 app.crashDialog = null; 16410 } 16411 if (app.anrDialog != null) { 16412 app.anrDialog.dismiss(); 16413 app.anrDialog = null; 16414 } 16415 if (app.waitDialog != null) { 16416 app.waitDialog.dismiss(); 16417 app.waitDialog = null; 16418 } 16419 16420 app.crashing = false; 16421 app.notResponding = false; 16422 16423 app.resetPackageList(mProcessStats); 16424 app.unlinkDeathRecipient(); 16425 app.makeInactive(mProcessStats); 16426 app.waitingToKill = null; 16427 app.forcingToForeground = null; 16428 updateProcessForegroundLocked(app, false, false); 16429 app.foregroundActivities = false; 16430 app.hasShownUi = false; 16431 app.treatLikeActivity = false; 16432 app.hasAboveClient = false; 16433 app.hasClientActivities = false; 16434 16435 mServices.killServicesLocked(app, allowRestart); 16436 16437 boolean restart = false; 16438 16439 // Remove published content providers. 16440 for (int i = app.pubProviders.size() - 1; i >= 0; i--) { 16441 ContentProviderRecord cpr = app.pubProviders.valueAt(i); 16442 final boolean always = app.bad || !allowRestart; 16443 boolean inLaunching = removeDyingProviderLocked(app, cpr, always); 16444 if ((inLaunching || always) && cpr.hasConnectionOrHandle()) { 16445 // We left the provider in the launching list, need to 16446 // restart it. 16447 restart = true; 16448 } 16449 16450 cpr.provider = null; 16451 cpr.proc = null; 16452 } 16453 app.pubProviders.clear(); 16454 16455 // Take care of any launching providers waiting for this process. 16456 if (cleanupAppInLaunchingProvidersLocked(app, false)) { 16457 restart = true; 16458 } 16459 16460 // Unregister from connected content providers. 16461 if (!app.conProviders.isEmpty()) { 16462 for (int i = app.conProviders.size() - 1; i >= 0; i--) { 16463 ContentProviderConnection conn = app.conProviders.get(i); 16464 conn.provider.connections.remove(conn); 16465 stopAssociationLocked(app.uid, app.processName, conn.provider.uid, 16466 conn.provider.name); 16467 } 16468 app.conProviders.clear(); 16469 } 16470 16471 // At this point there may be remaining entries in mLaunchingProviders 16472 // where we were the only one waiting, so they are no longer of use. 16473 // Look for these and clean up if found. 16474 // XXX Commented out for now. Trying to figure out a way to reproduce 16475 // the actual situation to identify what is actually going on. 16476 if (false) { 16477 for (int i = mLaunchingProviders.size() - 1; i >= 0; i--) { 16478 ContentProviderRecord cpr = mLaunchingProviders.get(i); 16479 if (cpr.connections.size() <= 0 && !cpr.hasExternalProcessHandles()) { 16480 synchronized (cpr) { 16481 cpr.launchingApp = null; 16482 cpr.notifyAll(); 16483 } 16484 } 16485 } 16486 } 16487 16488 skipCurrentReceiverLocked(app); 16489 16490 // Unregister any receivers. 16491 for (int i = app.receivers.size() - 1; i >= 0; i--) { 16492 removeReceiverLocked(app.receivers.valueAt(i)); 16493 } 16494 app.receivers.clear(); 16495 16496 // If the app is undergoing backup, tell the backup manager about it 16497 if (mBackupTarget != null && app.pid == mBackupTarget.app.pid) { 16498 if (DEBUG_BACKUP || DEBUG_CLEANUP) Slog.d(TAG_CLEANUP, "App " 16499 + mBackupTarget.appInfo + " died during backup"); 16500 try { 16501 IBackupManager bm = IBackupManager.Stub.asInterface( 16502 ServiceManager.getService(Context.BACKUP_SERVICE)); 16503 bm.agentDisconnected(app.info.packageName); 16504 } catch (RemoteException e) { 16505 // can't happen; backup manager is local 16506 } 16507 } 16508 16509 for (int i = mPendingProcessChanges.size() - 1; i >= 0; i--) { 16510 ProcessChangeItem item = mPendingProcessChanges.get(i); 16511 if (item.pid == app.pid) { 16512 mPendingProcessChanges.remove(i); 16513 mAvailProcessChanges.add(item); 16514 } 16515 } 16516 mUiHandler.obtainMessage(DISPATCH_PROCESS_DIED_UI_MSG, app.pid, app.info.uid, 16517 null).sendToTarget(); 16518 16519 // If the caller is restarting this app, then leave it in its 16520 // current lists and let the caller take care of it. 16521 if (restarting) { 16522 return false; 16523 } 16524 16525 if (!app.persistent || app.isolated) { 16526 if (DEBUG_PROCESSES || DEBUG_CLEANUP) Slog.v(TAG_CLEANUP, 16527 "Removing non-persistent process during cleanup: " + app); 16528 removeProcessNameLocked(app.processName, app.uid); 16529 if (mHeavyWeightProcess == app) { 16530 mHandler.sendMessage(mHandler.obtainMessage(CANCEL_HEAVY_NOTIFICATION_MSG, 16531 mHeavyWeightProcess.userId, 0)); 16532 mHeavyWeightProcess = null; 16533 } 16534 } else if (!app.removed) { 16535 // This app is persistent, so we need to keep its record around. 16536 // If it is not already on the pending app list, add it there 16537 // and start a new process for it. 16538 if (mPersistentStartingProcesses.indexOf(app) < 0) { 16539 mPersistentStartingProcesses.add(app); 16540 restart = true; 16541 } 16542 } 16543 if ((DEBUG_PROCESSES || DEBUG_CLEANUP) && mProcessesOnHold.contains(app)) Slog.v( 16544 TAG_CLEANUP, "Clean-up removing on hold: " + app); 16545 mProcessesOnHold.remove(app); 16546 16547 if (app == mHomeProcess) { 16548 mHomeProcess = null; 16549 } 16550 if (app == mPreviousProcess) { 16551 mPreviousProcess = null; 16552 } 16553 16554 if (restart && !app.isolated) { 16555 // We have components that still need to be running in the 16556 // process, so re-launch it. 16557 if (index < 0) { 16558 ProcessList.remove(app.pid); 16559 } 16560 addProcessNameLocked(app); 16561 startProcessLocked(app, "restart", app.processName); 16562 return true; 16563 } else if (app.pid > 0 && app.pid != MY_PID) { 16564 // Goodbye! 16565 boolean removed; 16566 synchronized (mPidsSelfLocked) { 16567 mPidsSelfLocked.remove(app.pid); 16568 mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app); 16569 } 16570 mBatteryStatsService.noteProcessFinish(app.processName, app.info.uid); 16571 if (app.isolated) { 16572 mBatteryStatsService.removeIsolatedUid(app.uid, app.info.uid); 16573 } 16574 app.setPid(0); 16575 } 16576 return false; 16577 } 16578 16579 boolean checkAppInLaunchingProvidersLocked(ProcessRecord app) { 16580 for (int i = mLaunchingProviders.size() - 1; i >= 0; i--) { 16581 ContentProviderRecord cpr = mLaunchingProviders.get(i); 16582 if (cpr.launchingApp == app) { 16583 return true; 16584 } 16585 } 16586 return false; 16587 } 16588 16589 boolean cleanupAppInLaunchingProvidersLocked(ProcessRecord app, boolean alwaysBad) { 16590 // Look through the content providers we are waiting to have launched, 16591 // and if any run in this process then either schedule a restart of 16592 // the process or kill the client waiting for it if this process has 16593 // gone bad. 16594 boolean restart = false; 16595 for (int i = mLaunchingProviders.size() - 1; i >= 0; i--) { 16596 ContentProviderRecord cpr = mLaunchingProviders.get(i); 16597 if (cpr.launchingApp == app) { 16598 if (!alwaysBad && !app.bad && cpr.hasConnectionOrHandle()) { 16599 restart = true; 16600 } else { 16601 removeDyingProviderLocked(app, cpr, true); 16602 } 16603 } 16604 } 16605 return restart; 16606 } 16607 16608 // ========================================================= 16609 // SERVICES 16610 // ========================================================= 16611 16612 @Override 16613 public List<ActivityManager.RunningServiceInfo> getServices(int maxNum, 16614 int flags) { 16615 enforceNotIsolatedCaller("getServices"); 16616 synchronized (this) { 16617 return mServices.getRunningServiceInfoLocked(maxNum, flags); 16618 } 16619 } 16620 16621 @Override 16622 public PendingIntent getRunningServiceControlPanel(ComponentName name) { 16623 enforceNotIsolatedCaller("getRunningServiceControlPanel"); 16624 synchronized (this) { 16625 return mServices.getRunningServiceControlPanelLocked(name); 16626 } 16627 } 16628 16629 @Override 16630 public ComponentName startService(IApplicationThread caller, Intent service, 16631 String resolvedType, String callingPackage, int userId) 16632 throws TransactionTooLargeException { 16633 enforceNotIsolatedCaller("startService"); 16634 // Refuse possible leaked file descriptors 16635 if (service != null && service.hasFileDescriptors() == true) { 16636 throw new IllegalArgumentException("File descriptors passed in Intent"); 16637 } 16638 16639 if (callingPackage == null) { 16640 throw new IllegalArgumentException("callingPackage cannot be null"); 16641 } 16642 16643 if (DEBUG_SERVICE) Slog.v(TAG_SERVICE, 16644 "startService: " + service + " type=" + resolvedType); 16645 synchronized(this) { 16646 final int callingPid = Binder.getCallingPid(); 16647 final int callingUid = Binder.getCallingUid(); 16648 final long origId = Binder.clearCallingIdentity(); 16649 ComponentName res = mServices.startServiceLocked(caller, service, 16650 resolvedType, callingPid, callingUid, callingPackage, userId); 16651 Binder.restoreCallingIdentity(origId); 16652 return res; 16653 } 16654 } 16655 16656 ComponentName startServiceInPackage(int uid, Intent service, String resolvedType, 16657 String callingPackage, int userId) 16658 throws TransactionTooLargeException { 16659 synchronized(this) { 16660 if (DEBUG_SERVICE) Slog.v(TAG_SERVICE, 16661 "startServiceInPackage: " + service + " type=" + resolvedType); 16662 final long origId = Binder.clearCallingIdentity(); 16663 ComponentName res = mServices.startServiceLocked(null, service, 16664 resolvedType, -1, uid, callingPackage, userId); 16665 Binder.restoreCallingIdentity(origId); 16666 return res; 16667 } 16668 } 16669 16670 @Override 16671 public int stopService(IApplicationThread caller, Intent service, 16672 String resolvedType, int userId) { 16673 enforceNotIsolatedCaller("stopService"); 16674 // Refuse possible leaked file descriptors 16675 if (service != null && service.hasFileDescriptors() == true) { 16676 throw new IllegalArgumentException("File descriptors passed in Intent"); 16677 } 16678 16679 synchronized(this) { 16680 return mServices.stopServiceLocked(caller, service, resolvedType, userId); 16681 } 16682 } 16683 16684 @Override 16685 public IBinder peekService(Intent service, String resolvedType, String callingPackage) { 16686 enforceNotIsolatedCaller("peekService"); 16687 // Refuse possible leaked file descriptors 16688 if (service != null && service.hasFileDescriptors() == true) { 16689 throw new IllegalArgumentException("File descriptors passed in Intent"); 16690 } 16691 16692 if (callingPackage == null) { 16693 throw new IllegalArgumentException("callingPackage cannot be null"); 16694 } 16695 16696 synchronized(this) { 16697 return mServices.peekServiceLocked(service, resolvedType, callingPackage); 16698 } 16699 } 16700 16701 @Override 16702 public boolean stopServiceToken(ComponentName className, IBinder token, 16703 int startId) { 16704 synchronized(this) { 16705 return mServices.stopServiceTokenLocked(className, token, startId); 16706 } 16707 } 16708 16709 @Override 16710 public void setServiceForeground(ComponentName className, IBinder token, 16711 int id, Notification notification, int flags) { 16712 synchronized(this) { 16713 mServices.setServiceForegroundLocked(className, token, id, notification, flags); 16714 } 16715 } 16716 16717 @Override 16718 public int handleIncomingUser(int callingPid, int callingUid, int userId, boolean allowAll, 16719 boolean requireFull, String name, String callerPackage) { 16720 return mUserController.handleIncomingUser(callingPid, callingUid, userId, allowAll, 16721 requireFull ? ALLOW_FULL_ONLY : ALLOW_NON_FULL, name, callerPackage); 16722 } 16723 16724 boolean isSingleton(String componentProcessName, ApplicationInfo aInfo, 16725 String className, int flags) { 16726 boolean result = false; 16727 // For apps that don't have pre-defined UIDs, check for permission 16728 if (UserHandle.getAppId(aInfo.uid) >= Process.FIRST_APPLICATION_UID) { 16729 if ((flags & ServiceInfo.FLAG_SINGLE_USER) != 0) { 16730 if (ActivityManager.checkUidPermission( 16731 INTERACT_ACROSS_USERS, 16732 aInfo.uid) != PackageManager.PERMISSION_GRANTED) { 16733 ComponentName comp = new ComponentName(aInfo.packageName, className); 16734 String msg = "Permission Denial: Component " + comp.flattenToShortString() 16735 + " requests FLAG_SINGLE_USER, but app does not hold " 16736 + INTERACT_ACROSS_USERS; 16737 Slog.w(TAG, msg); 16738 throw new SecurityException(msg); 16739 } 16740 // Permission passed 16741 result = true; 16742 } 16743 } else if ("system".equals(componentProcessName)) { 16744 result = true; 16745 } else if ((flags & ServiceInfo.FLAG_SINGLE_USER) != 0) { 16746 // Phone app and persistent apps are allowed to export singleuser providers. 16747 result = UserHandle.isSameApp(aInfo.uid, Process.PHONE_UID) 16748 || (aInfo.flags & ApplicationInfo.FLAG_PERSISTENT) != 0; 16749 } 16750 if (DEBUG_MU) Slog.v(TAG_MU, 16751 "isSingleton(" + componentProcessName + ", " + aInfo + ", " + className + ", 0x" 16752 + Integer.toHexString(flags) + ") = " + result); 16753 return result; 16754 } 16755 16756 /** 16757 * Checks to see if the caller is in the same app as the singleton 16758 * component, or the component is in a special app. It allows special apps 16759 * to export singleton components but prevents exporting singleton 16760 * components for regular apps. 16761 */ 16762 boolean isValidSingletonCall(int callingUid, int componentUid) { 16763 int componentAppId = UserHandle.getAppId(componentUid); 16764 return UserHandle.isSameApp(callingUid, componentUid) 16765 || componentAppId == Process.SYSTEM_UID 16766 || componentAppId == Process.PHONE_UID 16767 || ActivityManager.checkUidPermission(INTERACT_ACROSS_USERS_FULL, componentUid) 16768 == PackageManager.PERMISSION_GRANTED; 16769 } 16770 16771 public int bindService(IApplicationThread caller, IBinder token, Intent service, 16772 String resolvedType, IServiceConnection connection, int flags, String callingPackage, 16773 int userId) throws TransactionTooLargeException { 16774 enforceNotIsolatedCaller("bindService"); 16775 16776 // Refuse possible leaked file descriptors 16777 if (service != null && service.hasFileDescriptors() == true) { 16778 throw new IllegalArgumentException("File descriptors passed in Intent"); 16779 } 16780 16781 if (callingPackage == null) { 16782 throw new IllegalArgumentException("callingPackage cannot be null"); 16783 } 16784 16785 synchronized(this) { 16786 return mServices.bindServiceLocked(caller, token, service, 16787 resolvedType, connection, flags, callingPackage, userId); 16788 } 16789 } 16790 16791 public boolean unbindService(IServiceConnection connection) { 16792 synchronized (this) { 16793 return mServices.unbindServiceLocked(connection); 16794 } 16795 } 16796 16797 public void publishService(IBinder token, Intent intent, IBinder service) { 16798 // Refuse possible leaked file descriptors 16799 if (intent != null && intent.hasFileDescriptors() == true) { 16800 throw new IllegalArgumentException("File descriptors passed in Intent"); 16801 } 16802 16803 synchronized(this) { 16804 if (!(token instanceof ServiceRecord)) { 16805 throw new IllegalArgumentException("Invalid service token"); 16806 } 16807 mServices.publishServiceLocked((ServiceRecord)token, intent, service); 16808 } 16809 } 16810 16811 public void unbindFinished(IBinder token, Intent intent, boolean doRebind) { 16812 // Refuse possible leaked file descriptors 16813 if (intent != null && intent.hasFileDescriptors() == true) { 16814 throw new IllegalArgumentException("File descriptors passed in Intent"); 16815 } 16816 16817 synchronized(this) { 16818 mServices.unbindFinishedLocked((ServiceRecord)token, intent, doRebind); 16819 } 16820 } 16821 16822 public void serviceDoneExecuting(IBinder token, int type, int startId, int res) { 16823 synchronized(this) { 16824 if (!(token instanceof ServiceRecord)) { 16825 Slog.e(TAG, "serviceDoneExecuting: Invalid service token=" + token); 16826 throw new IllegalArgumentException("Invalid service token"); 16827 } 16828 mServices.serviceDoneExecutingLocked((ServiceRecord)token, type, startId, res); 16829 } 16830 } 16831 16832 // ========================================================= 16833 // BACKUP AND RESTORE 16834 // ========================================================= 16835 16836 // Cause the target app to be launched if necessary and its backup agent 16837 // instantiated. The backup agent will invoke backupAgentCreated() on the 16838 // activity manager to announce its creation. 16839 public boolean bindBackupAgent(ApplicationInfo app, int backupMode) { 16840 if (DEBUG_BACKUP) Slog.v(TAG_BACKUP, 16841 "bindBackupAgent: app=" + app + " mode=" + backupMode); 16842 enforceCallingPermission("android.permission.CONFIRM_FULL_BACKUP", "bindBackupAgent"); 16843 16844 synchronized(this) { 16845 // !!! TODO: currently no check here that we're already bound 16846 BatteryStatsImpl.Uid.Pkg.Serv ss = null; 16847 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 16848 synchronized (stats) { 16849 ss = stats.getServiceStatsLocked(app.uid, app.packageName, app.name); 16850 } 16851 16852 // Backup agent is now in use, its package can't be stopped. 16853 try { 16854 AppGlobals.getPackageManager().setPackageStoppedState( 16855 app.packageName, false, UserHandle.getUserId(app.uid)); 16856 } catch (RemoteException e) { 16857 } catch (IllegalArgumentException e) { 16858 Slog.w(TAG, "Failed trying to unstop package " 16859 + app.packageName + ": " + e); 16860 } 16861 16862 BackupRecord r = new BackupRecord(ss, app, backupMode); 16863 ComponentName hostingName = (backupMode == IApplicationThread.BACKUP_MODE_INCREMENTAL) 16864 ? new ComponentName(app.packageName, app.backupAgentName) 16865 : new ComponentName("android", "FullBackupAgent"); 16866 // startProcessLocked() returns existing proc's record if it's already running 16867 ProcessRecord proc = startProcessLocked(app.processName, app, 16868 false, 0, "backup", hostingName, false, false, false); 16869 if (proc == null) { 16870 Slog.e(TAG, "Unable to start backup agent process " + r); 16871 return false; 16872 } 16873 16874 // If the app is a regular app (uid >= 10000) and not the system server or phone 16875 // process, etc, then mark it as being in full backup so that certain calls to the 16876 // process can be blocked. This is not reset to false anywhere because we kill the 16877 // process after the full backup is done and the ProcessRecord will vaporize anyway. 16878 if (UserHandle.isApp(app.uid) && backupMode == IApplicationThread.BACKUP_MODE_FULL) { 16879 proc.inFullBackup = true; 16880 } 16881 r.app = proc; 16882 mBackupTarget = r; 16883 mBackupAppName = app.packageName; 16884 16885 // Try not to kill the process during backup 16886 updateOomAdjLocked(proc); 16887 16888 // If the process is already attached, schedule the creation of the backup agent now. 16889 // If it is not yet live, this will be done when it attaches to the framework. 16890 if (proc.thread != null) { 16891 if (DEBUG_BACKUP) Slog.v(TAG_BACKUP, "Agent proc already running: " + proc); 16892 try { 16893 proc.thread.scheduleCreateBackupAgent(app, 16894 compatibilityInfoForPackageLocked(app), backupMode); 16895 } catch (RemoteException e) { 16896 // Will time out on the backup manager side 16897 } 16898 } else { 16899 if (DEBUG_BACKUP) Slog.v(TAG_BACKUP, "Agent proc not running, waiting for attach"); 16900 } 16901 // Invariants: at this point, the target app process exists and the application 16902 // is either already running or in the process of coming up. mBackupTarget and 16903 // mBackupAppName describe the app, so that when it binds back to the AM we 16904 // know that it's scheduled for a backup-agent operation. 16905 } 16906 16907 return true; 16908 } 16909 16910 @Override 16911 public void clearPendingBackup() { 16912 if (DEBUG_BACKUP) Slog.v(TAG_BACKUP, "clearPendingBackup"); 16913 enforceCallingPermission("android.permission.BACKUP", "clearPendingBackup"); 16914 16915 synchronized (this) { 16916 mBackupTarget = null; 16917 mBackupAppName = null; 16918 } 16919 } 16920 16921 // A backup agent has just come up 16922 public void backupAgentCreated(String agentPackageName, IBinder agent) { 16923 if (DEBUG_BACKUP) Slog.v(TAG_BACKUP, "backupAgentCreated: " + agentPackageName 16924 + " = " + agent); 16925 16926 synchronized(this) { 16927 if (!agentPackageName.equals(mBackupAppName)) { 16928 Slog.e(TAG, "Backup agent created for " + agentPackageName + " but not requested!"); 16929 return; 16930 } 16931 } 16932 16933 long oldIdent = Binder.clearCallingIdentity(); 16934 try { 16935 IBackupManager bm = IBackupManager.Stub.asInterface( 16936 ServiceManager.getService(Context.BACKUP_SERVICE)); 16937 bm.agentConnected(agentPackageName, agent); 16938 } catch (RemoteException e) { 16939 // can't happen; the backup manager service is local 16940 } catch (Exception e) { 16941 Slog.w(TAG, "Exception trying to deliver BackupAgent binding: "); 16942 e.printStackTrace(); 16943 } finally { 16944 Binder.restoreCallingIdentity(oldIdent); 16945 } 16946 } 16947 16948 // done with this agent 16949 public void unbindBackupAgent(ApplicationInfo appInfo) { 16950 if (DEBUG_BACKUP) Slog.v(TAG_BACKUP, "unbindBackupAgent: " + appInfo); 16951 if (appInfo == null) { 16952 Slog.w(TAG, "unbind backup agent for null app"); 16953 return; 16954 } 16955 16956 synchronized(this) { 16957 try { 16958 if (mBackupAppName == null) { 16959 Slog.w(TAG, "Unbinding backup agent with no active backup"); 16960 return; 16961 } 16962 16963 if (!mBackupAppName.equals(appInfo.packageName)) { 16964 Slog.e(TAG, "Unbind of " + appInfo + " but is not the current backup target"); 16965 return; 16966 } 16967 16968 // Not backing this app up any more; reset its OOM adjustment 16969 final ProcessRecord proc = mBackupTarget.app; 16970 updateOomAdjLocked(proc); 16971 16972 // If the app crashed during backup, 'thread' will be null here 16973 if (proc.thread != null) { 16974 try { 16975 proc.thread.scheduleDestroyBackupAgent(appInfo, 16976 compatibilityInfoForPackageLocked(appInfo)); 16977 } catch (Exception e) { 16978 Slog.e(TAG, "Exception when unbinding backup agent:"); 16979 e.printStackTrace(); 16980 } 16981 } 16982 } finally { 16983 mBackupTarget = null; 16984 mBackupAppName = null; 16985 } 16986 } 16987 } 16988 // ========================================================= 16989 // BROADCASTS 16990 // ========================================================= 16991 16992 boolean isPendingBroadcastProcessLocked(int pid) { 16993 return mFgBroadcastQueue.isPendingBroadcastProcessLocked(pid) 16994 || mBgBroadcastQueue.isPendingBroadcastProcessLocked(pid); 16995 } 16996 16997 void skipPendingBroadcastLocked(int pid) { 16998 Slog.w(TAG, "Unattached app died before broadcast acknowledged, skipping"); 16999 for (BroadcastQueue queue : mBroadcastQueues) { 17000 queue.skipPendingBroadcastLocked(pid); 17001 } 17002 } 17003 17004 // The app just attached; send any pending broadcasts that it should receive 17005 boolean sendPendingBroadcastsLocked(ProcessRecord app) { 17006 boolean didSomething = false; 17007 for (BroadcastQueue queue : mBroadcastQueues) { 17008 didSomething |= queue.sendPendingBroadcastsLocked(app); 17009 } 17010 return didSomething; 17011 } 17012 17013 public Intent registerReceiver(IApplicationThread caller, String callerPackage, 17014 IIntentReceiver receiver, IntentFilter filter, String permission, int userId) { 17015 enforceNotIsolatedCaller("registerReceiver"); 17016 ArrayList<Intent> stickyIntents = null; 17017 ProcessRecord callerApp = null; 17018 int callingUid; 17019 int callingPid; 17020 synchronized(this) { 17021 if (caller != null) { 17022 callerApp = getRecordForAppLocked(caller); 17023 if (callerApp == null) { 17024 throw new SecurityException( 17025 "Unable to find app for caller " + caller 17026 + " (pid=" + Binder.getCallingPid() 17027 + ") when registering receiver " + receiver); 17028 } 17029 if (callerApp.info.uid != Process.SYSTEM_UID && 17030 !callerApp.pkgList.containsKey(callerPackage) && 17031 !"android".equals(callerPackage)) { 17032 throw new SecurityException("Given caller package " + callerPackage 17033 + " is not running in process " + callerApp); 17034 } 17035 callingUid = callerApp.info.uid; 17036 callingPid = callerApp.pid; 17037 } else { 17038 callerPackage = null; 17039 callingUid = Binder.getCallingUid(); 17040 callingPid = Binder.getCallingPid(); 17041 } 17042 17043 userId = mUserController.handleIncomingUser(callingPid, callingUid, userId, true, 17044 ALLOW_FULL_ONLY, "registerReceiver", callerPackage); 17045 17046 Iterator<String> actions = filter.actionsIterator(); 17047 if (actions == null) { 17048 ArrayList<String> noAction = new ArrayList<String>(1); 17049 noAction.add(null); 17050 actions = noAction.iterator(); 17051 } 17052 17053 // Collect stickies of users 17054 int[] userIds = { UserHandle.USER_ALL, UserHandle.getUserId(callingUid) }; 17055 while (actions.hasNext()) { 17056 String action = actions.next(); 17057 for (int id : userIds) { 17058 ArrayMap<String, ArrayList<Intent>> stickies = mStickyBroadcasts.get(id); 17059 if (stickies != null) { 17060 ArrayList<Intent> intents = stickies.get(action); 17061 if (intents != null) { 17062 if (stickyIntents == null) { 17063 stickyIntents = new ArrayList<Intent>(); 17064 } 17065 stickyIntents.addAll(intents); 17066 } 17067 } 17068 } 17069 } 17070 } 17071 17072 ArrayList<Intent> allSticky = null; 17073 if (stickyIntents != null) { 17074 final ContentResolver resolver = mContext.getContentResolver(); 17075 // Look for any matching sticky broadcasts... 17076 for (int i = 0, N = stickyIntents.size(); i < N; i++) { 17077 Intent intent = stickyIntents.get(i); 17078 // If intent has scheme "content", it will need to acccess 17079 // provider that needs to lock mProviderMap in ActivityThread 17080 // and also it may need to wait application response, so we 17081 // cannot lock ActivityManagerService here. 17082 if (filter.match(resolver, intent, true, TAG) >= 0) { 17083 if (allSticky == null) { 17084 allSticky = new ArrayList<Intent>(); 17085 } 17086 allSticky.add(intent); 17087 } 17088 } 17089 } 17090 17091 // The first sticky in the list is returned directly back to the client. 17092 Intent sticky = allSticky != null ? allSticky.get(0) : null; 17093 if (DEBUG_BROADCAST) Slog.v(TAG_BROADCAST, "Register receiver " + filter + ": " + sticky); 17094 if (receiver == null) { 17095 return sticky; 17096 } 17097 17098 synchronized (this) { 17099 if (callerApp != null && (callerApp.thread == null 17100 || callerApp.thread.asBinder() != caller.asBinder())) { 17101 // Original caller already died 17102 return null; 17103 } 17104 ReceiverList rl = mRegisteredReceivers.get(receiver.asBinder()); 17105 if (rl == null) { 17106 rl = new ReceiverList(this, callerApp, callingPid, callingUid, 17107 userId, receiver); 17108 if (rl.app != null) { 17109 rl.app.receivers.add(rl); 17110 } else { 17111 try { 17112 receiver.asBinder().linkToDeath(rl, 0); 17113 } catch (RemoteException e) { 17114 return sticky; 17115 } 17116 rl.linkedToDeath = true; 17117 } 17118 mRegisteredReceivers.put(receiver.asBinder(), rl); 17119 } else if (rl.uid != callingUid) { 17120 throw new IllegalArgumentException( 17121 "Receiver requested to register for uid " + callingUid 17122 + " was previously registered for uid " + rl.uid); 17123 } else if (rl.pid != callingPid) { 17124 throw new IllegalArgumentException( 17125 "Receiver requested to register for pid " + callingPid 17126 + " was previously registered for pid " + rl.pid); 17127 } else if (rl.userId != userId) { 17128 throw new IllegalArgumentException( 17129 "Receiver requested to register for user " + userId 17130 + " was previously registered for user " + rl.userId); 17131 } 17132 BroadcastFilter bf = new BroadcastFilter(filter, rl, callerPackage, 17133 permission, callingUid, userId); 17134 rl.add(bf); 17135 if (!bf.debugCheck()) { 17136 Slog.w(TAG, "==> For Dynamic broadcast"); 17137 } 17138 mReceiverResolver.addFilter(bf); 17139 17140 // Enqueue broadcasts for all existing stickies that match 17141 // this filter. 17142 if (allSticky != null) { 17143 ArrayList receivers = new ArrayList(); 17144 receivers.add(bf); 17145 17146 final int stickyCount = allSticky.size(); 17147 for (int i = 0; i < stickyCount; i++) { 17148 Intent intent = allSticky.get(i); 17149 BroadcastQueue queue = broadcastQueueForIntent(intent); 17150 BroadcastRecord r = new BroadcastRecord(queue, intent, null, 17151 null, -1, -1, null, null, AppOpsManager.OP_NONE, null, receivers, 17152 null, 0, null, null, false, true, true, -1); 17153 queue.enqueueParallelBroadcastLocked(r); 17154 queue.scheduleBroadcastsLocked(); 17155 } 17156 } 17157 17158 return sticky; 17159 } 17160 } 17161 17162 public void unregisterReceiver(IIntentReceiver receiver) { 17163 if (DEBUG_BROADCAST) Slog.v(TAG_BROADCAST, "Unregister receiver: " + receiver); 17164 17165 final long origId = Binder.clearCallingIdentity(); 17166 try { 17167 boolean doTrim = false; 17168 17169 synchronized(this) { 17170 ReceiverList rl = mRegisteredReceivers.get(receiver.asBinder()); 17171 if (rl != null) { 17172 final BroadcastRecord r = rl.curBroadcast; 17173 if (r != null && r == r.queue.getMatchingOrderedReceiver(r)) { 17174 final boolean doNext = r.queue.finishReceiverLocked( 17175 r, r.resultCode, r.resultData, r.resultExtras, 17176 r.resultAbort, false); 17177 if (doNext) { 17178 doTrim = true; 17179 r.queue.processNextBroadcast(false); 17180 } 17181 } 17182 17183 if (rl.app != null) { 17184 rl.app.receivers.remove(rl); 17185 } 17186 removeReceiverLocked(rl); 17187 if (rl.linkedToDeath) { 17188 rl.linkedToDeath = false; 17189 rl.receiver.asBinder().unlinkToDeath(rl, 0); 17190 } 17191 } 17192 } 17193 17194 // If we actually concluded any broadcasts, we might now be able 17195 // to trim the recipients' apps from our working set 17196 if (doTrim) { 17197 trimApplications(); 17198 return; 17199 } 17200 17201 } finally { 17202 Binder.restoreCallingIdentity(origId); 17203 } 17204 } 17205 17206 void removeReceiverLocked(ReceiverList rl) { 17207 mRegisteredReceivers.remove(rl.receiver.asBinder()); 17208 for (int i = rl.size() - 1; i >= 0; i--) { 17209 mReceiverResolver.removeFilter(rl.get(i)); 17210 } 17211 } 17212 17213 private final void sendPackageBroadcastLocked(int cmd, String[] packages, int userId) { 17214 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 17215 ProcessRecord r = mLruProcesses.get(i); 17216 if (r.thread != null && (userId == UserHandle.USER_ALL || r.userId == userId)) { 17217 try { 17218 r.thread.dispatchPackageBroadcast(cmd, packages); 17219 } catch (RemoteException ex) { 17220 } 17221 } 17222 } 17223 } 17224 17225 private List<ResolveInfo> collectReceiverComponents(Intent intent, String resolvedType, 17226 int callingUid, int[] users) { 17227 // TODO: come back and remove this assumption to triage all broadcasts 17228 int pmFlags = STOCK_PM_FLAGS | MATCH_DEBUG_TRIAGED_MISSING; 17229 17230 List<ResolveInfo> receivers = null; 17231 try { 17232 HashSet<ComponentName> singleUserReceivers = null; 17233 boolean scannedFirstReceivers = false; 17234 for (int user : users) { 17235 // Skip users that have Shell restrictions, with exception of always permitted 17236 // Shell broadcasts 17237 if (callingUid == Process.SHELL_UID 17238 && mUserController.hasUserRestriction( 17239 UserManager.DISALLOW_DEBUGGING_FEATURES, user) 17240 && !isPermittedShellBroadcast(intent)) { 17241 continue; 17242 } 17243 List<ResolveInfo> newReceivers = AppGlobals.getPackageManager() 17244 .queryIntentReceivers(intent, resolvedType, pmFlags, user).getList(); 17245 if (user != UserHandle.USER_SYSTEM && newReceivers != null) { 17246 // If this is not the system user, we need to check for 17247 // any receivers that should be filtered out. 17248 for (int i=0; i<newReceivers.size(); i++) { 17249 ResolveInfo ri = newReceivers.get(i); 17250 if ((ri.activityInfo.flags&ActivityInfo.FLAG_SYSTEM_USER_ONLY) != 0) { 17251 newReceivers.remove(i); 17252 i--; 17253 } 17254 } 17255 } 17256 if (newReceivers != null && newReceivers.size() == 0) { 17257 newReceivers = null; 17258 } 17259 if (receivers == null) { 17260 receivers = newReceivers; 17261 } else if (newReceivers != null) { 17262 // We need to concatenate the additional receivers 17263 // found with what we have do far. This would be easy, 17264 // but we also need to de-dup any receivers that are 17265 // singleUser. 17266 if (!scannedFirstReceivers) { 17267 // Collect any single user receivers we had already retrieved. 17268 scannedFirstReceivers = true; 17269 for (int i=0; i<receivers.size(); i++) { 17270 ResolveInfo ri = receivers.get(i); 17271 if ((ri.activityInfo.flags&ActivityInfo.FLAG_SINGLE_USER) != 0) { 17272 ComponentName cn = new ComponentName( 17273 ri.activityInfo.packageName, ri.activityInfo.name); 17274 if (singleUserReceivers == null) { 17275 singleUserReceivers = new HashSet<ComponentName>(); 17276 } 17277 singleUserReceivers.add(cn); 17278 } 17279 } 17280 } 17281 // Add the new results to the existing results, tracking 17282 // and de-dupping single user receivers. 17283 for (int i=0; i<newReceivers.size(); i++) { 17284 ResolveInfo ri = newReceivers.get(i); 17285 if ((ri.activityInfo.flags&ActivityInfo.FLAG_SINGLE_USER) != 0) { 17286 ComponentName cn = new ComponentName( 17287 ri.activityInfo.packageName, ri.activityInfo.name); 17288 if (singleUserReceivers == null) { 17289 singleUserReceivers = new HashSet<ComponentName>(); 17290 } 17291 if (!singleUserReceivers.contains(cn)) { 17292 singleUserReceivers.add(cn); 17293 receivers.add(ri); 17294 } 17295 } else { 17296 receivers.add(ri); 17297 } 17298 } 17299 } 17300 } 17301 } catch (RemoteException ex) { 17302 // pm is in same process, this will never happen. 17303 } 17304 return receivers; 17305 } 17306 17307 private boolean isPermittedShellBroadcast(Intent intent) { 17308 // remote bugreport should always be allowed to be taken 17309 return INTENT_REMOTE_BUGREPORT_FINISHED.equals(intent.getAction()); 17310 } 17311 17312 final int broadcastIntentLocked(ProcessRecord callerApp, 17313 String callerPackage, Intent intent, String resolvedType, 17314 IIntentReceiver resultTo, int resultCode, String resultData, 17315 Bundle resultExtras, String[] requiredPermissions, int appOp, Bundle bOptions, 17316 boolean ordered, boolean sticky, int callingPid, int callingUid, int userId) { 17317 intent = new Intent(intent); 17318 17319 // By default broadcasts do not go to stopped apps. 17320 intent.addFlags(Intent.FLAG_EXCLUDE_STOPPED_PACKAGES); 17321 17322 // If we have not finished booting, don't allow this to launch new processes. 17323 if (!mProcessesReady && (intent.getFlags()&Intent.FLAG_RECEIVER_BOOT_UPGRADE) == 0) { 17324 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 17325 } 17326 17327 if (DEBUG_BROADCAST_LIGHT) Slog.v(TAG_BROADCAST, 17328 (sticky ? "Broadcast sticky: ": "Broadcast: ") + intent 17329 + " ordered=" + ordered + " userid=" + userId); 17330 if ((resultTo != null) && !ordered) { 17331 Slog.w(TAG, "Broadcast " + intent + " not ordered but result callback requested!"); 17332 } 17333 17334 userId = mUserController.handleIncomingUser(callingPid, callingUid, userId, true, 17335 ALLOW_NON_FULL, "broadcast", callerPackage); 17336 17337 // Make sure that the user who is receiving this broadcast is running. 17338 // If not, we will just skip it. Make an exception for shutdown broadcasts 17339 // and upgrade steps. 17340 17341 if (userId != UserHandle.USER_ALL && !mUserController.isUserRunningLocked(userId, 0)) { 17342 if ((callingUid != Process.SYSTEM_UID 17343 || (intent.getFlags() & Intent.FLAG_RECEIVER_BOOT_UPGRADE) == 0) 17344 && !Intent.ACTION_SHUTDOWN.equals(intent.getAction())) { 17345 Slog.w(TAG, "Skipping broadcast of " + intent 17346 + ": user " + userId + " is stopped"); 17347 return ActivityManager.BROADCAST_FAILED_USER_STOPPED; 17348 } 17349 } 17350 17351 BroadcastOptions brOptions = null; 17352 if (bOptions != null) { 17353 brOptions = new BroadcastOptions(bOptions); 17354 if (brOptions.getTemporaryAppWhitelistDuration() > 0) { 17355 // See if the caller is allowed to do this. Note we are checking against 17356 // the actual real caller (not whoever provided the operation as say a 17357 // PendingIntent), because that who is actually supplied the arguments. 17358 if (checkComponentPermission( 17359 android.Manifest.permission.CHANGE_DEVICE_IDLE_TEMP_WHITELIST, 17360 Binder.getCallingPid(), Binder.getCallingUid(), -1, true) 17361 != PackageManager.PERMISSION_GRANTED) { 17362 String msg = "Permission Denial: " + intent.getAction() 17363 + " broadcast from " + callerPackage + " (pid=" + callingPid 17364 + ", uid=" + callingUid + ")" 17365 + " requires " 17366 + android.Manifest.permission.CHANGE_DEVICE_IDLE_TEMP_WHITELIST; 17367 Slog.w(TAG, msg); 17368 throw new SecurityException(msg); 17369 } 17370 } 17371 } 17372 17373 // Verify that protected broadcasts are only being sent by system code, 17374 // and that system code is only sending protected broadcasts. 17375 final String action = intent.getAction(); 17376 final boolean isProtectedBroadcast; 17377 try { 17378 isProtectedBroadcast = AppGlobals.getPackageManager().isProtectedBroadcast(action); 17379 } catch (RemoteException e) { 17380 Slog.w(TAG, "Remote exception", e); 17381 return ActivityManager.BROADCAST_SUCCESS; 17382 } 17383 17384 final boolean isCallerSystem; 17385 switch (UserHandle.getAppId(callingUid)) { 17386 case Process.ROOT_UID: 17387 case Process.SYSTEM_UID: 17388 case Process.PHONE_UID: 17389 case Process.BLUETOOTH_UID: 17390 case Process.NFC_UID: 17391 isCallerSystem = true; 17392 break; 17393 default: 17394 isCallerSystem = (callerApp != null) && callerApp.persistent; 17395 break; 17396 } 17397 17398 if (isCallerSystem) { 17399 if (isProtectedBroadcast 17400 || Intent.ACTION_CLOSE_SYSTEM_DIALOGS.equals(action) 17401 || Intent.ACTION_DISMISS_KEYBOARD_SHORTCUTS.equals(action) 17402 || Intent.ACTION_MEDIA_BUTTON.equals(action) 17403 || Intent.ACTION_MEDIA_SCANNER_SCAN_FILE.equals(action) 17404 || Intent.ACTION_SHOW_KEYBOARD_SHORTCUTS.equals(action) 17405 || AppWidgetManager.ACTION_APPWIDGET_CONFIGURE.equals(action) 17406 || AppWidgetManager.ACTION_APPWIDGET_UPDATE.equals(action) 17407 || LocationManager.HIGH_POWER_REQUEST_CHANGE_ACTION.equals(action) 17408 || TelephonyIntents.ACTION_REQUEST_OMADM_CONFIGURATION_UPDATE.equals(action) 17409 || SuggestionSpan.ACTION_SUGGESTION_PICKED.equals(action)) { 17410 // Broadcast is either protected, or it's a public action that 17411 // we've relaxed, so it's fine for system internals to send. 17412 } else { 17413 // The vast majority of broadcasts sent from system internals 17414 // should be protected to avoid security holes, so yell loudly 17415 // to ensure we examine these cases. 17416 if (callerApp != null) { 17417 Log.wtf(TAG, "Sending non-protected broadcast " + action 17418 + " from system " + callerApp.toShortString() + " pkg " + callerPackage, 17419 new Throwable()); 17420 } else { 17421 Log.wtf(TAG, "Sending non-protected broadcast " + action 17422 + " from system uid " + UserHandle.formatUid(callingUid) 17423 + " pkg " + callerPackage, 17424 new Throwable()); 17425 } 17426 } 17427 17428 } else { 17429 if (isProtectedBroadcast) { 17430 String msg = "Permission Denial: not allowed to send broadcast " 17431 + action + " from pid=" 17432 + callingPid + ", uid=" + callingUid; 17433 Slog.w(TAG, msg); 17434 throw new SecurityException(msg); 17435 17436 } else if (AppWidgetManager.ACTION_APPWIDGET_CONFIGURE.equals(action) 17437 || AppWidgetManager.ACTION_APPWIDGET_UPDATE.equals(action)) { 17438 // Special case for compatibility: we don't want apps to send this, 17439 // but historically it has not been protected and apps may be using it 17440 // to poke their own app widget. So, instead of making it protected, 17441 // just limit it to the caller. 17442 if (callerPackage == null) { 17443 String msg = "Permission Denial: not allowed to send broadcast " 17444 + action + " from unknown caller."; 17445 Slog.w(TAG, msg); 17446 throw new SecurityException(msg); 17447 } else if (intent.getComponent() != null) { 17448 // They are good enough to send to an explicit component... verify 17449 // it is being sent to the calling app. 17450 if (!intent.getComponent().getPackageName().equals( 17451 callerPackage)) { 17452 String msg = "Permission Denial: not allowed to send broadcast " 17453 + action + " to " 17454 + intent.getComponent().getPackageName() + " from " 17455 + callerPackage; 17456 Slog.w(TAG, msg); 17457 throw new SecurityException(msg); 17458 } 17459 } else { 17460 // Limit broadcast to their own package. 17461 intent.setPackage(callerPackage); 17462 } 17463 } 17464 } 17465 17466 if (action != null) { 17467 switch (action) { 17468 case Intent.ACTION_UID_REMOVED: 17469 case Intent.ACTION_PACKAGE_REMOVED: 17470 case Intent.ACTION_PACKAGE_CHANGED: 17471 case Intent.ACTION_EXTERNAL_APPLICATIONS_UNAVAILABLE: 17472 case Intent.ACTION_EXTERNAL_APPLICATIONS_AVAILABLE: 17473 case Intent.ACTION_PACKAGES_SUSPENDED: 17474 case Intent.ACTION_PACKAGES_UNSUSPENDED: 17475 // Handle special intents: if this broadcast is from the package 17476 // manager about a package being removed, we need to remove all of 17477 // its activities from the history stack. 17478 if (checkComponentPermission( 17479 android.Manifest.permission.BROADCAST_PACKAGE_REMOVED, 17480 callingPid, callingUid, -1, true) 17481 != PackageManager.PERMISSION_GRANTED) { 17482 String msg = "Permission Denial: " + intent.getAction() 17483 + " broadcast from " + callerPackage + " (pid=" + callingPid 17484 + ", uid=" + callingUid + ")" 17485 + " requires " 17486 + android.Manifest.permission.BROADCAST_PACKAGE_REMOVED; 17487 Slog.w(TAG, msg); 17488 throw new SecurityException(msg); 17489 } 17490 switch (action) { 17491 case Intent.ACTION_UID_REMOVED: 17492 final Bundle intentExtras = intent.getExtras(); 17493 final int uid = intentExtras != null 17494 ? intentExtras.getInt(Intent.EXTRA_UID) : -1; 17495 if (uid >= 0) { 17496 mBatteryStatsService.removeUid(uid); 17497 mAppOpsService.uidRemoved(uid); 17498 } 17499 break; 17500 case Intent.ACTION_EXTERNAL_APPLICATIONS_UNAVAILABLE: 17501 // If resources are unavailable just force stop all those packages 17502 // and flush the attribute cache as well. 17503 String list[] = 17504 intent.getStringArrayExtra(Intent.EXTRA_CHANGED_PACKAGE_LIST); 17505 if (list != null && list.length > 0) { 17506 for (int i = 0; i < list.length; i++) { 17507 forceStopPackageLocked(list[i], -1, false, true, true, 17508 false, false, userId, "storage unmount"); 17509 } 17510 mRecentTasks.cleanupLocked(UserHandle.USER_ALL); 17511 sendPackageBroadcastLocked( 17512 IApplicationThread.EXTERNAL_STORAGE_UNAVAILABLE, list, 17513 userId); 17514 } 17515 break; 17516 case Intent.ACTION_EXTERNAL_APPLICATIONS_AVAILABLE: 17517 mRecentTasks.cleanupLocked(UserHandle.USER_ALL); 17518 break; 17519 case Intent.ACTION_PACKAGE_REMOVED: 17520 case Intent.ACTION_PACKAGE_CHANGED: 17521 Uri data = intent.getData(); 17522 String ssp; 17523 if (data != null && (ssp=data.getSchemeSpecificPart()) != null) { 17524 boolean removed = Intent.ACTION_PACKAGE_REMOVED.equals(action); 17525 final boolean replacing = 17526 intent.getBooleanExtra(Intent.EXTRA_REPLACING, false); 17527 final boolean killProcess = 17528 !intent.getBooleanExtra(Intent.EXTRA_DONT_KILL_APP, false); 17529 final boolean fullUninstall = removed && !replacing; 17530 if (killProcess) { 17531 forceStopPackageLocked(ssp, UserHandle.getAppId( 17532 intent.getIntExtra(Intent.EXTRA_UID, -1)), 17533 false, true, true, false, fullUninstall, userId, 17534 removed ? "pkg removed" : "pkg changed"); 17535 } 17536 if (removed) { 17537 final int cmd = killProcess 17538 ? IApplicationThread.PACKAGE_REMOVED 17539 : IApplicationThread.PACKAGE_REMOVED_DONT_KILL; 17540 sendPackageBroadcastLocked(cmd, 17541 new String[] {ssp}, userId); 17542 if (fullUninstall) { 17543 mAppOpsService.packageRemoved( 17544 intent.getIntExtra(Intent.EXTRA_UID, -1), ssp); 17545 17546 // Remove all permissions granted from/to this package 17547 removeUriPermissionsForPackageLocked(ssp, userId, true); 17548 17549 removeTasksByPackageNameLocked(ssp, userId); 17550 mBatteryStatsService.notePackageUninstalled(ssp); 17551 } 17552 } else { 17553 cleanupDisabledPackageComponentsLocked(ssp, userId, killProcess, 17554 intent.getStringArrayExtra( 17555 Intent.EXTRA_CHANGED_COMPONENT_NAME_LIST)); 17556 } 17557 } 17558 break; 17559 case Intent.ACTION_PACKAGES_SUSPENDED: 17560 case Intent.ACTION_PACKAGES_UNSUSPENDED: 17561 final boolean suspended = Intent.ACTION_PACKAGES_SUSPENDED.equals( 17562 intent.getAction()); 17563 final String[] packageNames = intent.getStringArrayExtra( 17564 Intent.EXTRA_CHANGED_PACKAGE_LIST); 17565 final int userHandle = intent.getIntExtra( 17566 Intent.EXTRA_USER_HANDLE, UserHandle.USER_NULL); 17567 17568 synchronized(ActivityManagerService.this) { 17569 mRecentTasks.onPackagesSuspendedChanged( 17570 packageNames, suspended, userHandle); 17571 } 17572 break; 17573 } 17574 break; 17575 case Intent.ACTION_PACKAGE_REPLACED: 17576 { 17577 final Uri data = intent.getData(); 17578 final String ssp; 17579 if (data != null && (ssp = data.getSchemeSpecificPart()) != null) { 17580 final ApplicationInfo aInfo = 17581 getPackageManagerInternalLocked().getApplicationInfo( 17582 ssp, 17583 userId); 17584 mStackSupervisor.updateActivityApplicationInfoLocked(aInfo); 17585 sendPackageBroadcastLocked(IApplicationThread.PACKAGE_REPLACED, 17586 new String[] {ssp}, userId); 17587 } 17588 break; 17589 } 17590 case Intent.ACTION_PACKAGE_ADDED: 17591 { 17592 // Special case for adding a package: by default turn on compatibility mode. 17593 Uri data = intent.getData(); 17594 String ssp; 17595 if (data != null && (ssp = data.getSchemeSpecificPart()) != null) { 17596 final boolean replacing = 17597 intent.getBooleanExtra(Intent.EXTRA_REPLACING, false); 17598 mCompatModePackages.handlePackageAddedLocked(ssp, replacing); 17599 17600 try { 17601 ApplicationInfo ai = AppGlobals.getPackageManager(). 17602 getApplicationInfo(ssp, 0, 0); 17603 mBatteryStatsService.notePackageInstalled(ssp, 17604 ai != null ? ai.versionCode : 0); 17605 } catch (RemoteException e) { 17606 } 17607 } 17608 break; 17609 } 17610 case Intent.ACTION_TIMEZONE_CHANGED: 17611 // If this is the time zone changed action, queue up a message that will reset 17612 // the timezone of all currently running processes. This message will get 17613 // queued up before the broadcast happens. 17614 mHandler.sendEmptyMessage(UPDATE_TIME_ZONE); 17615 break; 17616 case Intent.ACTION_TIME_CHANGED: 17617 // If the user set the time, let all running processes know. 17618 final int is24Hour = 17619 intent.getBooleanExtra(Intent.EXTRA_TIME_PREF_24_HOUR_FORMAT, false) ? 1 17620 : 0; 17621 mHandler.sendMessage(mHandler.obtainMessage(UPDATE_TIME, is24Hour, 0)); 17622 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 17623 synchronized (stats) { 17624 stats.noteCurrentTimeChangedLocked(); 17625 } 17626 break; 17627 case Intent.ACTION_CLEAR_DNS_CACHE: 17628 mHandler.sendEmptyMessage(CLEAR_DNS_CACHE_MSG); 17629 break; 17630 case Proxy.PROXY_CHANGE_ACTION: 17631 ProxyInfo proxy = intent.getParcelableExtra(Proxy.EXTRA_PROXY_INFO); 17632 mHandler.sendMessage(mHandler.obtainMessage(UPDATE_HTTP_PROXY_MSG, proxy)); 17633 break; 17634 case android.hardware.Camera.ACTION_NEW_PICTURE: 17635 case android.hardware.Camera.ACTION_NEW_VIDEO: 17636 // These broadcasts are no longer allowed by the system, since they can 17637 // cause significant thrashing at a crictical point (using the camera). 17638 // Apps should use JobScehduler to monitor for media provider changes. 17639 Slog.w(TAG, action + " no longer allowed; dropping from " 17640 + UserHandle.formatUid(callingUid)); 17641 // Lie; we don't want to crash the app. 17642 return ActivityManager.BROADCAST_SUCCESS; 17643 } 17644 } 17645 17646 // Add to the sticky list if requested. 17647 if (sticky) { 17648 if (checkPermission(android.Manifest.permission.BROADCAST_STICKY, 17649 callingPid, callingUid) 17650 != PackageManager.PERMISSION_GRANTED) { 17651 String msg = "Permission Denial: broadcastIntent() requesting a sticky broadcast from pid=" 17652 + callingPid + ", uid=" + callingUid 17653 + " requires " + android.Manifest.permission.BROADCAST_STICKY; 17654 Slog.w(TAG, msg); 17655 throw new SecurityException(msg); 17656 } 17657 if (requiredPermissions != null && requiredPermissions.length > 0) { 17658 Slog.w(TAG, "Can't broadcast sticky intent " + intent 17659 + " and enforce permissions " + Arrays.toString(requiredPermissions)); 17660 return ActivityManager.BROADCAST_STICKY_CANT_HAVE_PERMISSION; 17661 } 17662 if (intent.getComponent() != null) { 17663 throw new SecurityException( 17664 "Sticky broadcasts can't target a specific component"); 17665 } 17666 // We use userId directly here, since the "all" target is maintained 17667 // as a separate set of sticky broadcasts. 17668 if (userId != UserHandle.USER_ALL) { 17669 // But first, if this is not a broadcast to all users, then 17670 // make sure it doesn't conflict with an existing broadcast to 17671 // all users. 17672 ArrayMap<String, ArrayList<Intent>> stickies = mStickyBroadcasts.get( 17673 UserHandle.USER_ALL); 17674 if (stickies != null) { 17675 ArrayList<Intent> list = stickies.get(intent.getAction()); 17676 if (list != null) { 17677 int N = list.size(); 17678 int i; 17679 for (i=0; i<N; i++) { 17680 if (intent.filterEquals(list.get(i))) { 17681 throw new IllegalArgumentException( 17682 "Sticky broadcast " + intent + " for user " 17683 + userId + " conflicts with existing global broadcast"); 17684 } 17685 } 17686 } 17687 } 17688 } 17689 ArrayMap<String, ArrayList<Intent>> stickies = mStickyBroadcasts.get(userId); 17690 if (stickies == null) { 17691 stickies = new ArrayMap<>(); 17692 mStickyBroadcasts.put(userId, stickies); 17693 } 17694 ArrayList<Intent> list = stickies.get(intent.getAction()); 17695 if (list == null) { 17696 list = new ArrayList<>(); 17697 stickies.put(intent.getAction(), list); 17698 } 17699 final int stickiesCount = list.size(); 17700 int i; 17701 for (i = 0; i < stickiesCount; i++) { 17702 if (intent.filterEquals(list.get(i))) { 17703 // This sticky already exists, replace it. 17704 list.set(i, new Intent(intent)); 17705 break; 17706 } 17707 } 17708 if (i >= stickiesCount) { 17709 list.add(new Intent(intent)); 17710 } 17711 } 17712 17713 int[] users; 17714 if (userId == UserHandle.USER_ALL) { 17715 // Caller wants broadcast to go to all started users. 17716 users = mUserController.getStartedUserArrayLocked(); 17717 } else { 17718 // Caller wants broadcast to go to one specific user. 17719 users = new int[] {userId}; 17720 } 17721 17722 // Figure out who all will receive this broadcast. 17723 List receivers = null; 17724 List<BroadcastFilter> registeredReceivers = null; 17725 // Need to resolve the intent to interested receivers... 17726 if ((intent.getFlags()&Intent.FLAG_RECEIVER_REGISTERED_ONLY) 17727 == 0) { 17728 receivers = collectReceiverComponents(intent, resolvedType, callingUid, users); 17729 } 17730 if (intent.getComponent() == null) { 17731 if (userId == UserHandle.USER_ALL && callingUid == Process.SHELL_UID) { 17732 // Query one target user at a time, excluding shell-restricted users 17733 for (int i = 0; i < users.length; i++) { 17734 if (mUserController.hasUserRestriction( 17735 UserManager.DISALLOW_DEBUGGING_FEATURES, users[i])) { 17736 continue; 17737 } 17738 List<BroadcastFilter> registeredReceiversForUser = 17739 mReceiverResolver.queryIntent(intent, 17740 resolvedType, false, users[i]); 17741 if (registeredReceivers == null) { 17742 registeredReceivers = registeredReceiversForUser; 17743 } else if (registeredReceiversForUser != null) { 17744 registeredReceivers.addAll(registeredReceiversForUser); 17745 } 17746 } 17747 } else { 17748 registeredReceivers = mReceiverResolver.queryIntent(intent, 17749 resolvedType, false, userId); 17750 } 17751 } 17752 17753 final boolean replacePending = 17754 (intent.getFlags()&Intent.FLAG_RECEIVER_REPLACE_PENDING) != 0; 17755 17756 if (DEBUG_BROADCAST) Slog.v(TAG_BROADCAST, "Enqueing broadcast: " + intent.getAction() 17757 + " replacePending=" + replacePending); 17758 17759 int NR = registeredReceivers != null ? registeredReceivers.size() : 0; 17760 if (!ordered && NR > 0) { 17761 // If we are not serializing this broadcast, then send the 17762 // registered receivers separately so they don't wait for the 17763 // components to be launched. 17764 final BroadcastQueue queue = broadcastQueueForIntent(intent); 17765 BroadcastRecord r = new BroadcastRecord(queue, intent, callerApp, 17766 callerPackage, callingPid, callingUid, resolvedType, requiredPermissions, 17767 appOp, brOptions, registeredReceivers, resultTo, resultCode, resultData, 17768 resultExtras, ordered, sticky, false, userId); 17769 if (DEBUG_BROADCAST) Slog.v(TAG_BROADCAST, "Enqueueing parallel broadcast " + r); 17770 final boolean replaced = replacePending && queue.replaceParallelBroadcastLocked(r); 17771 if (!replaced) { 17772 queue.enqueueParallelBroadcastLocked(r); 17773 queue.scheduleBroadcastsLocked(); 17774 } 17775 registeredReceivers = null; 17776 NR = 0; 17777 } 17778 17779 // Merge into one list. 17780 int ir = 0; 17781 if (receivers != null) { 17782 // A special case for PACKAGE_ADDED: do not allow the package 17783 // being added to see this broadcast. This prevents them from 17784 // using this as a back door to get run as soon as they are 17785 // installed. Maybe in the future we want to have a special install 17786 // broadcast or such for apps, but we'd like to deliberately make 17787 // this decision. 17788 String skipPackages[] = null; 17789 if (Intent.ACTION_PACKAGE_ADDED.equals(intent.getAction()) 17790 || Intent.ACTION_PACKAGE_RESTARTED.equals(intent.getAction()) 17791 || Intent.ACTION_PACKAGE_DATA_CLEARED.equals(intent.getAction())) { 17792 Uri data = intent.getData(); 17793 if (data != null) { 17794 String pkgName = data.getSchemeSpecificPart(); 17795 if (pkgName != null) { 17796 skipPackages = new String[] { pkgName }; 17797 } 17798 } 17799 } else if (Intent.ACTION_EXTERNAL_APPLICATIONS_AVAILABLE.equals(intent.getAction())) { 17800 skipPackages = intent.getStringArrayExtra(Intent.EXTRA_CHANGED_PACKAGE_LIST); 17801 } 17802 if (skipPackages != null && (skipPackages.length > 0)) { 17803 for (String skipPackage : skipPackages) { 17804 if (skipPackage != null) { 17805 int NT = receivers.size(); 17806 for (int it=0; it<NT; it++) { 17807 ResolveInfo curt = (ResolveInfo)receivers.get(it); 17808 if (curt.activityInfo.packageName.equals(skipPackage)) { 17809 receivers.remove(it); 17810 it--; 17811 NT--; 17812 } 17813 } 17814 } 17815 } 17816 } 17817 17818 int NT = receivers != null ? receivers.size() : 0; 17819 int it = 0; 17820 ResolveInfo curt = null; 17821 BroadcastFilter curr = null; 17822 while (it < NT && ir < NR) { 17823 if (curt == null) { 17824 curt = (ResolveInfo)receivers.get(it); 17825 } 17826 if (curr == null) { 17827 curr = registeredReceivers.get(ir); 17828 } 17829 if (curr.getPriority() >= curt.priority) { 17830 // Insert this broadcast record into the final list. 17831 receivers.add(it, curr); 17832 ir++; 17833 curr = null; 17834 it++; 17835 NT++; 17836 } else { 17837 // Skip to the next ResolveInfo in the final list. 17838 it++; 17839 curt = null; 17840 } 17841 } 17842 } 17843 while (ir < NR) { 17844 if (receivers == null) { 17845 receivers = new ArrayList(); 17846 } 17847 receivers.add(registeredReceivers.get(ir)); 17848 ir++; 17849 } 17850 17851 if ((receivers != null && receivers.size() > 0) 17852 || resultTo != null) { 17853 BroadcastQueue queue = broadcastQueueForIntent(intent); 17854 BroadcastRecord r = new BroadcastRecord(queue, intent, callerApp, 17855 callerPackage, callingPid, callingUid, resolvedType, 17856 requiredPermissions, appOp, brOptions, receivers, resultTo, resultCode, 17857 resultData, resultExtras, ordered, sticky, false, userId); 17858 17859 if (DEBUG_BROADCAST) Slog.v(TAG_BROADCAST, "Enqueueing ordered broadcast " + r 17860 + ": prev had " + queue.mOrderedBroadcasts.size()); 17861 if (DEBUG_BROADCAST) Slog.i(TAG_BROADCAST, 17862 "Enqueueing broadcast " + r.intent.getAction()); 17863 17864 boolean replaced = replacePending && queue.replaceOrderedBroadcastLocked(r); 17865 if (!replaced) { 17866 queue.enqueueOrderedBroadcastLocked(r); 17867 queue.scheduleBroadcastsLocked(); 17868 } 17869 } 17870 17871 return ActivityManager.BROADCAST_SUCCESS; 17872 } 17873 17874 final Intent verifyBroadcastLocked(Intent intent) { 17875 // Refuse possible leaked file descriptors 17876 if (intent != null && intent.hasFileDescriptors() == true) { 17877 throw new IllegalArgumentException("File descriptors passed in Intent"); 17878 } 17879 17880 int flags = intent.getFlags(); 17881 17882 if (!mProcessesReady) { 17883 // if the caller really truly claims to know what they're doing, go 17884 // ahead and allow the broadcast without launching any receivers 17885 if ((flags&Intent.FLAG_RECEIVER_REGISTERED_ONLY_BEFORE_BOOT) != 0) { 17886 // This will be turned into a FLAG_RECEIVER_REGISTERED_ONLY later on if needed. 17887 } else if ((flags&Intent.FLAG_RECEIVER_REGISTERED_ONLY) == 0) { 17888 Slog.e(TAG, "Attempt to launch receivers of broadcast intent " + intent 17889 + " before boot completion"); 17890 throw new IllegalStateException("Cannot broadcast before boot completed"); 17891 } 17892 } 17893 17894 if ((flags&Intent.FLAG_RECEIVER_BOOT_UPGRADE) != 0) { 17895 throw new IllegalArgumentException( 17896 "Can't use FLAG_RECEIVER_BOOT_UPGRADE here"); 17897 } 17898 17899 return intent; 17900 } 17901 17902 public final int broadcastIntent(IApplicationThread caller, 17903 Intent intent, String resolvedType, IIntentReceiver resultTo, 17904 int resultCode, String resultData, Bundle resultExtras, 17905 String[] requiredPermissions, int appOp, Bundle bOptions, 17906 boolean serialized, boolean sticky, int userId) { 17907 enforceNotIsolatedCaller("broadcastIntent"); 17908 synchronized(this) { 17909 intent = verifyBroadcastLocked(intent); 17910 17911 final ProcessRecord callerApp = getRecordForAppLocked(caller); 17912 final int callingPid = Binder.getCallingPid(); 17913 final int callingUid = Binder.getCallingUid(); 17914 final long origId = Binder.clearCallingIdentity(); 17915 int res = broadcastIntentLocked(callerApp, 17916 callerApp != null ? callerApp.info.packageName : null, 17917 intent, resolvedType, resultTo, resultCode, resultData, resultExtras, 17918 requiredPermissions, appOp, bOptions, serialized, sticky, 17919 callingPid, callingUid, userId); 17920 Binder.restoreCallingIdentity(origId); 17921 return res; 17922 } 17923 } 17924 17925 17926 int broadcastIntentInPackage(String packageName, int uid, 17927 Intent intent, String resolvedType, IIntentReceiver resultTo, 17928 int resultCode, String resultData, Bundle resultExtras, 17929 String requiredPermission, Bundle bOptions, boolean serialized, boolean sticky, 17930 int userId) { 17931 synchronized(this) { 17932 intent = verifyBroadcastLocked(intent); 17933 17934 final long origId = Binder.clearCallingIdentity(); 17935 String[] requiredPermissions = requiredPermission == null ? null 17936 : new String[] {requiredPermission}; 17937 int res = broadcastIntentLocked(null, packageName, intent, resolvedType, 17938 resultTo, resultCode, resultData, resultExtras, 17939 requiredPermissions, AppOpsManager.OP_NONE, bOptions, serialized, 17940 sticky, -1, uid, userId); 17941 Binder.restoreCallingIdentity(origId); 17942 return res; 17943 } 17944 } 17945 17946 public final void unbroadcastIntent(IApplicationThread caller, Intent intent, int userId) { 17947 // Refuse possible leaked file descriptors 17948 if (intent != null && intent.hasFileDescriptors() == true) { 17949 throw new IllegalArgumentException("File descriptors passed in Intent"); 17950 } 17951 17952 userId = mUserController.handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 17953 userId, true, ALLOW_NON_FULL, "removeStickyBroadcast", null); 17954 17955 synchronized(this) { 17956 if (checkCallingPermission(android.Manifest.permission.BROADCAST_STICKY) 17957 != PackageManager.PERMISSION_GRANTED) { 17958 String msg = "Permission Denial: unbroadcastIntent() from pid=" 17959 + Binder.getCallingPid() 17960 + ", uid=" + Binder.getCallingUid() 17961 + " requires " + android.Manifest.permission.BROADCAST_STICKY; 17962 Slog.w(TAG, msg); 17963 throw new SecurityException(msg); 17964 } 17965 ArrayMap<String, ArrayList<Intent>> stickies = mStickyBroadcasts.get(userId); 17966 if (stickies != null) { 17967 ArrayList<Intent> list = stickies.get(intent.getAction()); 17968 if (list != null) { 17969 int N = list.size(); 17970 int i; 17971 for (i=0; i<N; i++) { 17972 if (intent.filterEquals(list.get(i))) { 17973 list.remove(i); 17974 break; 17975 } 17976 } 17977 if (list.size() <= 0) { 17978 stickies.remove(intent.getAction()); 17979 } 17980 } 17981 if (stickies.size() <= 0) { 17982 mStickyBroadcasts.remove(userId); 17983 } 17984 } 17985 } 17986 } 17987 17988 void backgroundServicesFinishedLocked(int userId) { 17989 for (BroadcastQueue queue : mBroadcastQueues) { 17990 queue.backgroundServicesFinishedLocked(userId); 17991 } 17992 } 17993 17994 public void finishReceiver(IBinder who, int resultCode, String resultData, 17995 Bundle resultExtras, boolean resultAbort, int flags) { 17996 if (DEBUG_BROADCAST) Slog.v(TAG_BROADCAST, "Finish receiver: " + who); 17997 17998 // Refuse possible leaked file descriptors 17999 if (resultExtras != null && resultExtras.hasFileDescriptors()) { 18000 throw new IllegalArgumentException("File descriptors passed in Bundle"); 18001 } 18002 18003 final long origId = Binder.clearCallingIdentity(); 18004 try { 18005 boolean doNext = false; 18006 BroadcastRecord r; 18007 18008 synchronized(this) { 18009 BroadcastQueue queue = (flags & Intent.FLAG_RECEIVER_FOREGROUND) != 0 18010 ? mFgBroadcastQueue : mBgBroadcastQueue; 18011 r = queue.getMatchingOrderedReceiver(who); 18012 if (r != null) { 18013 doNext = r.queue.finishReceiverLocked(r, resultCode, 18014 resultData, resultExtras, resultAbort, true); 18015 } 18016 } 18017 18018 if (doNext) { 18019 r.queue.processNextBroadcast(false); 18020 } 18021 trimApplications(); 18022 } finally { 18023 Binder.restoreCallingIdentity(origId); 18024 } 18025 } 18026 18027 // ========================================================= 18028 // INSTRUMENTATION 18029 // ========================================================= 18030 18031 public boolean startInstrumentation(ComponentName className, 18032 String profileFile, int flags, Bundle arguments, 18033 IInstrumentationWatcher watcher, IUiAutomationConnection uiAutomationConnection, 18034 int userId, String abiOverride) { 18035 enforceNotIsolatedCaller("startInstrumentation"); 18036 userId = mUserController.handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 18037 userId, false, ALLOW_FULL_ONLY, "startInstrumentation", null); 18038 // Refuse possible leaked file descriptors 18039 if (arguments != null && arguments.hasFileDescriptors()) { 18040 throw new IllegalArgumentException("File descriptors passed in Bundle"); 18041 } 18042 18043 synchronized(this) { 18044 InstrumentationInfo ii = null; 18045 ApplicationInfo ai = null; 18046 try { 18047 ii = mContext.getPackageManager().getInstrumentationInfo( 18048 className, STOCK_PM_FLAGS); 18049 ai = AppGlobals.getPackageManager().getApplicationInfo( 18050 ii.targetPackage, STOCK_PM_FLAGS, userId); 18051 } catch (PackageManager.NameNotFoundException e) { 18052 } catch (RemoteException e) { 18053 } 18054 if (ii == null) { 18055 reportStartInstrumentationFailureLocked(watcher, className, 18056 "Unable to find instrumentation info for: " + className); 18057 return false; 18058 } 18059 if (ai == null) { 18060 reportStartInstrumentationFailureLocked(watcher, className, 18061 "Unable to find instrumentation target package: " + ii.targetPackage); 18062 return false; 18063 } 18064 if (!ai.hasCode()) { 18065 reportStartInstrumentationFailureLocked(watcher, className, 18066 "Instrumentation target has no code: " + ii.targetPackage); 18067 return false; 18068 } 18069 18070 int match = mContext.getPackageManager().checkSignatures( 18071 ii.targetPackage, ii.packageName); 18072 if (match < 0 && match != PackageManager.SIGNATURE_FIRST_NOT_SIGNED) { 18073 String msg = "Permission Denial: starting instrumentation " 18074 + className + " from pid=" 18075 + Binder.getCallingPid() 18076 + ", uid=" + Binder.getCallingPid() 18077 + " not allowed because package " + ii.packageName 18078 + " does not have a signature matching the target " 18079 + ii.targetPackage; 18080 reportStartInstrumentationFailureLocked(watcher, className, msg); 18081 throw new SecurityException(msg); 18082 } 18083 18084 final long origId = Binder.clearCallingIdentity(); 18085 // Instrumentation can kill and relaunch even persistent processes 18086 forceStopPackageLocked(ii.targetPackage, -1, true, false, true, true, false, userId, 18087 "start instr"); 18088 ProcessRecord app = addAppLocked(ai, false, abiOverride); 18089 app.instrumentationClass = className; 18090 app.instrumentationInfo = ai; 18091 app.instrumentationProfileFile = profileFile; 18092 app.instrumentationArguments = arguments; 18093 app.instrumentationWatcher = watcher; 18094 app.instrumentationUiAutomationConnection = uiAutomationConnection; 18095 app.instrumentationResultClass = className; 18096 Binder.restoreCallingIdentity(origId); 18097 } 18098 18099 return true; 18100 } 18101 18102 /** 18103 * Report errors that occur while attempting to start Instrumentation. Always writes the 18104 * error to the logs, but if somebody is watching, send the report there too. This enables 18105 * the "am" command to report errors with more information. 18106 * 18107 * @param watcher The IInstrumentationWatcher. Null if there isn't one. 18108 * @param cn The component name of the instrumentation. 18109 * @param report The error report. 18110 */ 18111 private void reportStartInstrumentationFailureLocked(IInstrumentationWatcher watcher, 18112 ComponentName cn, String report) { 18113 Slog.w(TAG, report); 18114 if (watcher != null) { 18115 Bundle results = new Bundle(); 18116 results.putString(Instrumentation.REPORT_KEY_IDENTIFIER, "ActivityManagerService"); 18117 results.putString("Error", report); 18118 mInstrumentationReporter.reportStatus(watcher, cn, -1, results); 18119 } 18120 } 18121 18122 void finishInstrumentationLocked(ProcessRecord app, int resultCode, Bundle results) { 18123 if (app.instrumentationWatcher != null) { 18124 mInstrumentationReporter.reportFinished(app.instrumentationWatcher, 18125 app.instrumentationClass, resultCode, results); 18126 } 18127 18128 // Can't call out of the system process with a lock held, so post a message. 18129 if (app.instrumentationUiAutomationConnection != null) { 18130 mHandler.obtainMessage(SHUTDOWN_UI_AUTOMATION_CONNECTION_MSG, 18131 app.instrumentationUiAutomationConnection).sendToTarget(); 18132 } 18133 18134 app.instrumentationWatcher = null; 18135 app.instrumentationUiAutomationConnection = null; 18136 app.instrumentationClass = null; 18137 app.instrumentationInfo = null; 18138 app.instrumentationProfileFile = null; 18139 app.instrumentationArguments = null; 18140 18141 forceStopPackageLocked(app.info.packageName, -1, false, false, true, true, false, app.userId, 18142 "finished inst"); 18143 } 18144 18145 public void finishInstrumentation(IApplicationThread target, 18146 int resultCode, Bundle results) { 18147 int userId = UserHandle.getCallingUserId(); 18148 // Refuse possible leaked file descriptors 18149 if (results != null && results.hasFileDescriptors()) { 18150 throw new IllegalArgumentException("File descriptors passed in Intent"); 18151 } 18152 18153 synchronized(this) { 18154 ProcessRecord app = getRecordForAppLocked(target); 18155 if (app == null) { 18156 Slog.w(TAG, "finishInstrumentation: no app for " + target); 18157 return; 18158 } 18159 final long origId = Binder.clearCallingIdentity(); 18160 finishInstrumentationLocked(app, resultCode, results); 18161 Binder.restoreCallingIdentity(origId); 18162 } 18163 } 18164 18165 // ========================================================= 18166 // CONFIGURATION 18167 // ========================================================= 18168 18169 public ConfigurationInfo getDeviceConfigurationInfo() { 18170 ConfigurationInfo config = new ConfigurationInfo(); 18171 synchronized (this) { 18172 config.reqTouchScreen = mConfiguration.touchscreen; 18173 config.reqKeyboardType = mConfiguration.keyboard; 18174 config.reqNavigation = mConfiguration.navigation; 18175 if (mConfiguration.navigation == Configuration.NAVIGATION_DPAD 18176 || mConfiguration.navigation == Configuration.NAVIGATION_TRACKBALL) { 18177 config.reqInputFeatures |= ConfigurationInfo.INPUT_FEATURE_FIVE_WAY_NAV; 18178 } 18179 if (mConfiguration.keyboard != Configuration.KEYBOARD_UNDEFINED 18180 && mConfiguration.keyboard != Configuration.KEYBOARD_NOKEYS) { 18181 config.reqInputFeatures |= ConfigurationInfo.INPUT_FEATURE_HARD_KEYBOARD; 18182 } 18183 config.reqGlEsVersion = GL_ES_VERSION; 18184 } 18185 return config; 18186 } 18187 18188 ActivityStack getFocusedStack() { 18189 return mStackSupervisor.getFocusedStack(); 18190 } 18191 18192 @Override 18193 public int getFocusedStackId() throws RemoteException { 18194 ActivityStack focusedStack = getFocusedStack(); 18195 if (focusedStack != null) { 18196 return focusedStack.getStackId(); 18197 } 18198 return -1; 18199 } 18200 18201 public Configuration getConfiguration() { 18202 Configuration ci; 18203 synchronized(this) { 18204 ci = new Configuration(mConfiguration); 18205 ci.userSetLocale = false; 18206 } 18207 return ci; 18208 } 18209 18210 @Override 18211 public void suppressResizeConfigChanges(boolean suppress) throws RemoteException { 18212 enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "suppressResizeConfigChanges()"); 18213 synchronized (this) { 18214 mSuppressResizeConfigChanges = suppress; 18215 } 18216 } 18217 18218 @Override 18219 public void moveTasksToFullscreenStack(int fromStackId, boolean onTop) { 18220 enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "moveTasksToFullscreenStack()"); 18221 if (fromStackId == HOME_STACK_ID) { 18222 throw new IllegalArgumentException("You can't move tasks from the home stack."); 18223 } 18224 synchronized (this) { 18225 final long origId = Binder.clearCallingIdentity(); 18226 try { 18227 mStackSupervisor.moveTasksToFullscreenStackLocked(fromStackId, onTop); 18228 } finally { 18229 Binder.restoreCallingIdentity(origId); 18230 } 18231 } 18232 } 18233 18234 @Override 18235 public void updatePersistentConfiguration(Configuration values) { 18236 enforceCallingPermission(android.Manifest.permission.CHANGE_CONFIGURATION, 18237 "updateConfiguration()"); 18238 enforceWriteSettingsPermission("updateConfiguration()"); 18239 if (values == null) { 18240 throw new NullPointerException("Configuration must not be null"); 18241 } 18242 18243 int userId = UserHandle.getCallingUserId(); 18244 18245 synchronized(this) { 18246 final long origId = Binder.clearCallingIdentity(); 18247 updateConfigurationLocked(values, null, false, true, userId); 18248 Binder.restoreCallingIdentity(origId); 18249 } 18250 } 18251 18252 private void updateFontScaleIfNeeded() { 18253 final int currentUserId; 18254 synchronized(this) { 18255 currentUserId = mUserController.getCurrentUserIdLocked(); 18256 } 18257 final float scaleFactor = Settings.System.getFloatForUser(mContext.getContentResolver(), 18258 FONT_SCALE, 1.0f, currentUserId); 18259 if (mConfiguration.fontScale != scaleFactor) { 18260 final Configuration configuration = mWindowManager.computeNewConfiguration(); 18261 configuration.fontScale = scaleFactor; 18262 updatePersistentConfiguration(configuration); 18263 } 18264 } 18265 18266 private void enforceWriteSettingsPermission(String func) { 18267 int uid = Binder.getCallingUid(); 18268 if (uid == Process.ROOT_UID) { 18269 return; 18270 } 18271 18272 if (Settings.checkAndNoteWriteSettingsOperation(mContext, uid, 18273 Settings.getPackageNameForUid(mContext, uid), false)) { 18274 return; 18275 } 18276 18277 String msg = "Permission Denial: " + func + " from pid=" 18278 + Binder.getCallingPid() 18279 + ", uid=" + uid 18280 + " requires " + android.Manifest.permission.WRITE_SETTINGS; 18281 Slog.w(TAG, msg); 18282 throw new SecurityException(msg); 18283 } 18284 18285 public void updateConfiguration(Configuration values) { 18286 enforceCallingPermission(android.Manifest.permission.CHANGE_CONFIGURATION, 18287 "updateConfiguration()"); 18288 18289 synchronized(this) { 18290 if (values == null && mWindowManager != null) { 18291 // sentinel: fetch the current configuration from the window manager 18292 values = mWindowManager.computeNewConfiguration(); 18293 } 18294 18295 if (mWindowManager != null) { 18296 mProcessList.applyDisplaySize(mWindowManager); 18297 } 18298 18299 final long origId = Binder.clearCallingIdentity(); 18300 if (values != null) { 18301 Settings.System.clearConfiguration(values); 18302 } 18303 updateConfigurationLocked(values, null, false); 18304 Binder.restoreCallingIdentity(origId); 18305 } 18306 } 18307 18308 void updateUserConfigurationLocked() { 18309 Configuration configuration = new Configuration(mConfiguration); 18310 Settings.System.getConfigurationForUser(mContext.getContentResolver(), configuration, 18311 mUserController.getCurrentUserIdLocked()); 18312 updateConfigurationLocked(configuration, null, false); 18313 } 18314 18315 boolean updateConfigurationLocked(Configuration values, 18316 ActivityRecord starting, boolean initLocale) { 18317 // pass UserHandle.USER_NULL as userId because we don't persist configuration for any user 18318 return updateConfigurationLocked(values, starting, initLocale, false, 18319 UserHandle.USER_NULL); 18320 } 18321 18322 // To cache the list of supported system locales 18323 private String[] mSupportedSystemLocales = null; 18324 18325 /** 18326 * Do either or both things: (1) change the current configuration, and (2) 18327 * make sure the given activity is running with the (now) current 18328 * configuration. Returns true if the activity has been left running, or 18329 * false if <var>starting</var> is being destroyed to match the new 18330 * configuration. 18331 * 18332 * @param userId is only used when persistent parameter is set to true to persist configuration 18333 * for that particular user 18334 */ 18335 private boolean updateConfigurationLocked(Configuration values, 18336 ActivityRecord starting, boolean initLocale, boolean persistent, int userId) { 18337 int changes = 0; 18338 18339 if (mWindowManager != null) { 18340 mWindowManager.deferSurfaceLayout(); 18341 } 18342 if (values != null) { 18343 Configuration newConfig = new Configuration(mConfiguration); 18344 changes = newConfig.updateFrom(values); 18345 if (changes != 0) { 18346 if (DEBUG_SWITCH || DEBUG_CONFIGURATION) Slog.i(TAG_CONFIGURATION, 18347 "Updating configuration to: " + values); 18348 18349 EventLog.writeEvent(EventLogTags.CONFIGURATION_CHANGED, changes); 18350 18351 if (!initLocale && !values.getLocales().isEmpty() && values.userSetLocale) { 18352 final LocaleList locales = values.getLocales(); 18353 int bestLocaleIndex = 0; 18354 if (locales.size() > 1) { 18355 if (mSupportedSystemLocales == null) { 18356 mSupportedSystemLocales = 18357 Resources.getSystem().getAssets().getLocales(); 18358 } 18359 bestLocaleIndex = Math.max(0, 18360 locales.getFirstMatchIndex(mSupportedSystemLocales)); 18361 } 18362 SystemProperties.set("persist.sys.locale", 18363 locales.get(bestLocaleIndex).toLanguageTag()); 18364 LocaleList.setDefault(locales, bestLocaleIndex); 18365 mHandler.sendMessage(mHandler.obtainMessage(SEND_LOCALE_TO_MOUNT_DAEMON_MSG, 18366 locales.get(bestLocaleIndex))); 18367 } 18368 18369 mConfigurationSeq++; 18370 if (mConfigurationSeq <= 0) { 18371 mConfigurationSeq = 1; 18372 } 18373 newConfig.seq = mConfigurationSeq; 18374 mConfiguration = newConfig; 18375 Slog.i(TAG, "Config changes=" + Integer.toHexString(changes) + " " + newConfig); 18376 mUsageStatsService.reportConfigurationChange(newConfig, 18377 mUserController.getCurrentUserIdLocked()); 18378 //mUsageStatsService.noteStartConfig(newConfig); 18379 18380 final Configuration configCopy = new Configuration(mConfiguration); 18381 18382 // TODO: If our config changes, should we auto dismiss any currently 18383 // showing dialogs? 18384 mShowDialogs = shouldShowDialogs(newConfig, mInVrMode); 18385 18386 AttributeCache ac = AttributeCache.instance(); 18387 if (ac != null) { 18388 ac.updateConfiguration(configCopy); 18389 } 18390 18391 // Make sure all resources in our process are updated 18392 // right now, so that anyone who is going to retrieve 18393 // resource values after we return will be sure to get 18394 // the new ones. This is especially important during 18395 // boot, where the first config change needs to guarantee 18396 // all resources have that config before following boot 18397 // code is executed. 18398 mSystemThread.applyConfigurationToResources(configCopy); 18399 18400 if (persistent && Settings.System.hasInterestingConfigurationChanges(changes)) { 18401 Message msg = mHandler.obtainMessage(UPDATE_CONFIGURATION_MSG); 18402 msg.obj = new Configuration(configCopy); 18403 msg.arg1 = userId; 18404 mHandler.sendMessage(msg); 18405 } 18406 18407 final boolean isDensityChange = (changes & ActivityInfo.CONFIG_DENSITY) != 0; 18408 if (isDensityChange) { 18409 killAllBackgroundProcessesExcept(Build.VERSION_CODES.N, 18410 ActivityManager.PROCESS_STATE_FOREGROUND_SERVICE); 18411 } 18412 18413 for (int i=mLruProcesses.size()-1; i>=0; i--) { 18414 ProcessRecord app = mLruProcesses.get(i); 18415 try { 18416 if (app.thread != null) { 18417 if (DEBUG_CONFIGURATION) Slog.v(TAG_CONFIGURATION, "Sending to proc " 18418 + app.processName + " new config " + mConfiguration); 18419 app.thread.scheduleConfigurationChanged(configCopy); 18420 } 18421 } catch (Exception e) { 18422 } 18423 } 18424 Intent intent = new Intent(Intent.ACTION_CONFIGURATION_CHANGED); 18425 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 18426 | Intent.FLAG_RECEIVER_REPLACE_PENDING 18427 | Intent.FLAG_RECEIVER_FOREGROUND); 18428 broadcastIntentLocked(null, null, intent, null, null, 0, null, null, 18429 null, AppOpsManager.OP_NONE, null, false, false, 18430 MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 18431 if ((changes&ActivityInfo.CONFIG_LOCALE) != 0) { 18432 // Tell the shortcut manager that the system locale changed. It needs to know 18433 // it before any other apps receive ACTION_LOCALE_CHANGED, which is why 18434 // we "push" from here, rather than having the service listen to the broadcast. 18435 final ShortcutServiceInternal shortcutService = 18436 LocalServices.getService(ShortcutServiceInternal.class); 18437 if (shortcutService != null) { 18438 shortcutService.onSystemLocaleChangedNoLock(); 18439 } 18440 18441 intent = new Intent(Intent.ACTION_LOCALE_CHANGED); 18442 intent.addFlags(Intent.FLAG_RECEIVER_FOREGROUND); 18443 if (!mProcessesReady) { 18444 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 18445 } 18446 broadcastIntentLocked(null, null, intent, 18447 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 18448 null, false, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 18449 } 18450 } 18451 // Update the configuration with WM first and check if any of the stacks need to be 18452 // resized due to the configuration change. If so, resize the stacks now and do any 18453 // relaunches if necessary. This way we don't need to relaunch again below in 18454 // ensureActivityConfigurationLocked(). 18455 if (mWindowManager != null) { 18456 final int[] resizedStacks = mWindowManager.setNewConfiguration(mConfiguration); 18457 if (resizedStacks != null) { 18458 for (int stackId : resizedStacks) { 18459 final Rect newBounds = mWindowManager.getBoundsForNewConfiguration(stackId); 18460 mStackSupervisor.resizeStackLocked( 18461 stackId, newBounds, null, null, false, false, !DEFER_RESUME); 18462 } 18463 } 18464 } 18465 } 18466 18467 boolean kept = true; 18468 final ActivityStack mainStack = mStackSupervisor.getFocusedStack(); 18469 // mainStack is null during startup. 18470 if (mainStack != null) { 18471 if (changes != 0 && starting == null) { 18472 // If the configuration changed, and the caller is not already 18473 // in the process of starting an activity, then find the top 18474 // activity to check if its configuration needs to change. 18475 starting = mainStack.topRunningActivityLocked(); 18476 } 18477 18478 if (starting != null) { 18479 kept = mainStack.ensureActivityConfigurationLocked(starting, changes, false); 18480 // And we need to make sure at this point that all other activities 18481 // are made visible with the correct configuration. 18482 mStackSupervisor.ensureActivitiesVisibleLocked(starting, changes, 18483 !PRESERVE_WINDOWS); 18484 } 18485 } 18486 if (mWindowManager != null) { 18487 mWindowManager.continueSurfaceLayout(); 18488 } 18489 return kept; 18490 } 18491 18492 /** 18493 * Decide based on the configuration whether we should shouw the ANR, 18494 * crash, etc dialogs. The idea is that if there is no affordnace to 18495 * press the on-screen buttons, we shouldn't show the dialog. 18496 * 18497 * A thought: SystemUI might also want to get told about this, the Power 18498 * dialog / global actions also might want different behaviors. 18499 */ 18500 private static final boolean shouldShowDialogs(Configuration config, boolean inVrMode) { 18501 final boolean inputMethodExists = !(config.keyboard == Configuration.KEYBOARD_NOKEYS 18502 && config.touchscreen == Configuration.TOUCHSCREEN_NOTOUCH 18503 && config.navigation == Configuration.NAVIGATION_NONAV); 18504 final boolean uiIsNotCarType = !((config.uiMode & Configuration.UI_MODE_TYPE_MASK) 18505 == Configuration.UI_MODE_TYPE_CAR); 18506 return inputMethodExists && uiIsNotCarType && !inVrMode; 18507 } 18508 18509 @Override 18510 public boolean shouldUpRecreateTask(IBinder token, String destAffinity) { 18511 synchronized (this) { 18512 ActivityRecord srec = ActivityRecord.forTokenLocked(token); 18513 if (srec != null) { 18514 return srec.task.stack.shouldUpRecreateTaskLocked(srec, destAffinity); 18515 } 18516 } 18517 return false; 18518 } 18519 18520 public boolean navigateUpTo(IBinder token, Intent destIntent, int resultCode, 18521 Intent resultData) { 18522 18523 synchronized (this) { 18524 final ActivityRecord r = ActivityRecord.forTokenLocked(token); 18525 if (r != null) { 18526 return r.task.stack.navigateUpToLocked(r, destIntent, resultCode, resultData); 18527 } 18528 return false; 18529 } 18530 } 18531 18532 public int getLaunchedFromUid(IBinder activityToken) { 18533 ActivityRecord srec; 18534 synchronized (this) { 18535 srec = ActivityRecord.forTokenLocked(activityToken); 18536 } 18537 if (srec == null) { 18538 return -1; 18539 } 18540 return srec.launchedFromUid; 18541 } 18542 18543 public String getLaunchedFromPackage(IBinder activityToken) { 18544 ActivityRecord srec; 18545 synchronized (this) { 18546 srec = ActivityRecord.forTokenLocked(activityToken); 18547 } 18548 if (srec == null) { 18549 return null; 18550 } 18551 return srec.launchedFromPackage; 18552 } 18553 18554 // ========================================================= 18555 // LIFETIME MANAGEMENT 18556 // ========================================================= 18557 18558 // Returns which broadcast queue the app is the current [or imminent] receiver 18559 // on, or 'null' if the app is not an active broadcast recipient. 18560 private BroadcastQueue isReceivingBroadcast(ProcessRecord app) { 18561 BroadcastRecord r = app.curReceiver; 18562 if (r != null) { 18563 return r.queue; 18564 } 18565 18566 // It's not the current receiver, but it might be starting up to become one 18567 synchronized (this) { 18568 for (BroadcastQueue queue : mBroadcastQueues) { 18569 r = queue.mPendingBroadcast; 18570 if (r != null && r.curApp == app) { 18571 // found it; report which queue it's in 18572 return queue; 18573 } 18574 } 18575 } 18576 18577 return null; 18578 } 18579 18580 Association startAssociationLocked(int sourceUid, String sourceProcess, int sourceState, 18581 int targetUid, ComponentName targetComponent, String targetProcess) { 18582 if (!mTrackingAssociations) { 18583 return null; 18584 } 18585 ArrayMap<ComponentName, SparseArray<ArrayMap<String, Association>>> components 18586 = mAssociations.get(targetUid); 18587 if (components == null) { 18588 components = new ArrayMap<>(); 18589 mAssociations.put(targetUid, components); 18590 } 18591 SparseArray<ArrayMap<String, Association>> sourceUids = components.get(targetComponent); 18592 if (sourceUids == null) { 18593 sourceUids = new SparseArray<>(); 18594 components.put(targetComponent, sourceUids); 18595 } 18596 ArrayMap<String, Association> sourceProcesses = sourceUids.get(sourceUid); 18597 if (sourceProcesses == null) { 18598 sourceProcesses = new ArrayMap<>(); 18599 sourceUids.put(sourceUid, sourceProcesses); 18600 } 18601 Association ass = sourceProcesses.get(sourceProcess); 18602 if (ass == null) { 18603 ass = new Association(sourceUid, sourceProcess, targetUid, targetComponent, 18604 targetProcess); 18605 sourceProcesses.put(sourceProcess, ass); 18606 } 18607 ass.mCount++; 18608 ass.mNesting++; 18609 if (ass.mNesting == 1) { 18610 ass.mStartTime = ass.mLastStateUptime = SystemClock.uptimeMillis(); 18611 ass.mLastState = sourceState; 18612 } 18613 return ass; 18614 } 18615 18616 void stopAssociationLocked(int sourceUid, String sourceProcess, int targetUid, 18617 ComponentName targetComponent) { 18618 if (!mTrackingAssociations) { 18619 return; 18620 } 18621 ArrayMap<ComponentName, SparseArray<ArrayMap<String, Association>>> components 18622 = mAssociations.get(targetUid); 18623 if (components == null) { 18624 return; 18625 } 18626 SparseArray<ArrayMap<String, Association>> sourceUids = components.get(targetComponent); 18627 if (sourceUids == null) { 18628 return; 18629 } 18630 ArrayMap<String, Association> sourceProcesses = sourceUids.get(sourceUid); 18631 if (sourceProcesses == null) { 18632 return; 18633 } 18634 Association ass = sourceProcesses.get(sourceProcess); 18635 if (ass == null || ass.mNesting <= 0) { 18636 return; 18637 } 18638 ass.mNesting--; 18639 if (ass.mNesting == 0) { 18640 long uptime = SystemClock.uptimeMillis(); 18641 ass.mTime += uptime - ass.mStartTime; 18642 ass.mStateTimes[ass.mLastState-ActivityManager.MIN_PROCESS_STATE] 18643 += uptime - ass.mLastStateUptime; 18644 ass.mLastState = ActivityManager.MAX_PROCESS_STATE + 2; 18645 } 18646 } 18647 18648 private void noteUidProcessState(final int uid, final int state) { 18649 mBatteryStatsService.noteUidProcessState(uid, state); 18650 if (mTrackingAssociations) { 18651 for (int i1=0, N1=mAssociations.size(); i1<N1; i1++) { 18652 ArrayMap<ComponentName, SparseArray<ArrayMap<String, Association>>> targetComponents 18653 = mAssociations.valueAt(i1); 18654 for (int i2=0, N2=targetComponents.size(); i2<N2; i2++) { 18655 SparseArray<ArrayMap<String, Association>> sourceUids 18656 = targetComponents.valueAt(i2); 18657 ArrayMap<String, Association> sourceProcesses = sourceUids.get(uid); 18658 if (sourceProcesses != null) { 18659 for (int i4=0, N4=sourceProcesses.size(); i4<N4; i4++) { 18660 Association ass = sourceProcesses.valueAt(i4); 18661 if (ass.mNesting >= 1) { 18662 // currently associated 18663 long uptime = SystemClock.uptimeMillis(); 18664 ass.mStateTimes[ass.mLastState-ActivityManager.MIN_PROCESS_STATE] 18665 += uptime - ass.mLastStateUptime; 18666 ass.mLastState = state; 18667 ass.mLastStateUptime = uptime; 18668 } 18669 } 18670 } 18671 } 18672 } 18673 } 18674 } 18675 18676 private final int computeOomAdjLocked(ProcessRecord app, int cachedAdj, ProcessRecord TOP_APP, 18677 boolean doingAll, long now) { 18678 if (mAdjSeq == app.adjSeq) { 18679 // This adjustment has already been computed. 18680 return app.curRawAdj; 18681 } 18682 18683 if (app.thread == null) { 18684 app.adjSeq = mAdjSeq; 18685 app.curSchedGroup = ProcessList.SCHED_GROUP_BACKGROUND; 18686 app.curProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 18687 return (app.curAdj=app.curRawAdj=ProcessList.CACHED_APP_MAX_ADJ); 18688 } 18689 18690 app.adjTypeCode = ActivityManager.RunningAppProcessInfo.REASON_UNKNOWN; 18691 app.adjSource = null; 18692 app.adjTarget = null; 18693 app.empty = false; 18694 app.cached = false; 18695 18696 final int activitiesSize = app.activities.size(); 18697 18698 if (app.maxAdj <= ProcessList.FOREGROUND_APP_ADJ) { 18699 // The max adjustment doesn't allow this app to be anything 18700 // below foreground, so it is not worth doing work for it. 18701 app.adjType = "fixed"; 18702 app.adjSeq = mAdjSeq; 18703 app.curRawAdj = app.maxAdj; 18704 app.foregroundActivities = false; 18705 app.curSchedGroup = ProcessList.SCHED_GROUP_DEFAULT; 18706 app.curProcState = ActivityManager.PROCESS_STATE_PERSISTENT; 18707 // System processes can do UI, and when they do we want to have 18708 // them trim their memory after the user leaves the UI. To 18709 // facilitate this, here we need to determine whether or not it 18710 // is currently showing UI. 18711 app.systemNoUi = true; 18712 if (app == TOP_APP) { 18713 app.systemNoUi = false; 18714 app.curSchedGroup = ProcessList.SCHED_GROUP_TOP_APP; 18715 app.adjType = "pers-top-activity"; 18716 } else if (activitiesSize > 0) { 18717 for (int j = 0; j < activitiesSize; j++) { 18718 final ActivityRecord r = app.activities.get(j); 18719 if (r.visible) { 18720 app.systemNoUi = false; 18721 } 18722 } 18723 } 18724 if (!app.systemNoUi) { 18725 app.curProcState = ActivityManager.PROCESS_STATE_PERSISTENT_UI; 18726 } 18727 return (app.curAdj=app.maxAdj); 18728 } 18729 18730 app.systemNoUi = false; 18731 18732 final int PROCESS_STATE_CUR_TOP = mTopProcessState; 18733 18734 // Determine the importance of the process, starting with most 18735 // important to least, and assign an appropriate OOM adjustment. 18736 int adj; 18737 int schedGroup; 18738 int procState; 18739 boolean foregroundActivities = false; 18740 BroadcastQueue queue; 18741 if (app == TOP_APP) { 18742 // The last app on the list is the foreground app. 18743 adj = ProcessList.FOREGROUND_APP_ADJ; 18744 schedGroup = ProcessList.SCHED_GROUP_TOP_APP; 18745 app.adjType = "top-activity"; 18746 foregroundActivities = true; 18747 procState = PROCESS_STATE_CUR_TOP; 18748 } else if (app.instrumentationClass != null) { 18749 // Don't want to kill running instrumentation. 18750 adj = ProcessList.FOREGROUND_APP_ADJ; 18751 schedGroup = ProcessList.SCHED_GROUP_DEFAULT; 18752 app.adjType = "instrumentation"; 18753 procState = ActivityManager.PROCESS_STATE_FOREGROUND_SERVICE; 18754 } else if ((queue = isReceivingBroadcast(app)) != null) { 18755 // An app that is currently receiving a broadcast also 18756 // counts as being in the foreground for OOM killer purposes. 18757 // It's placed in a sched group based on the nature of the 18758 // broadcast as reflected by which queue it's active in. 18759 adj = ProcessList.FOREGROUND_APP_ADJ; 18760 schedGroup = (queue == mFgBroadcastQueue) 18761 ? ProcessList.SCHED_GROUP_DEFAULT : ProcessList.SCHED_GROUP_BACKGROUND; 18762 app.adjType = "broadcast"; 18763 procState = ActivityManager.PROCESS_STATE_RECEIVER; 18764 } else if (app.executingServices.size() > 0) { 18765 // An app that is currently executing a service callback also 18766 // counts as being in the foreground. 18767 adj = ProcessList.FOREGROUND_APP_ADJ; 18768 schedGroup = app.execServicesFg ? 18769 ProcessList.SCHED_GROUP_DEFAULT : ProcessList.SCHED_GROUP_BACKGROUND; 18770 app.adjType = "exec-service"; 18771 procState = ActivityManager.PROCESS_STATE_SERVICE; 18772 //Slog.i(TAG, "EXEC " + (app.execServicesFg ? "FG" : "BG") + ": " + app); 18773 } else { 18774 // As far as we know the process is empty. We may change our mind later. 18775 schedGroup = ProcessList.SCHED_GROUP_BACKGROUND; 18776 // At this point we don't actually know the adjustment. Use the cached adj 18777 // value that the caller wants us to. 18778 adj = cachedAdj; 18779 procState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 18780 app.cached = true; 18781 app.empty = true; 18782 app.adjType = "cch-empty"; 18783 } 18784 18785 // Examine all activities if not already foreground. 18786 if (!foregroundActivities && activitiesSize > 0) { 18787 int minLayer = ProcessList.VISIBLE_APP_LAYER_MAX; 18788 for (int j = 0; j < activitiesSize; j++) { 18789 final ActivityRecord r = app.activities.get(j); 18790 if (r.app != app) { 18791 Log.wtf(TAG, "Found activity " + r + " in proc activity list using " + r.app 18792 + " instead of expected " + app); 18793 if (r.app == null || (r.app.uid == app.uid)) { 18794 // Only fix things up when they look sane 18795 r.app = app; 18796 } else { 18797 continue; 18798 } 18799 } 18800 if (r.visible) { 18801 // App has a visible activity; only upgrade adjustment. 18802 if (adj > ProcessList.VISIBLE_APP_ADJ) { 18803 adj = ProcessList.VISIBLE_APP_ADJ; 18804 app.adjType = "visible"; 18805 } 18806 if (procState > PROCESS_STATE_CUR_TOP) { 18807 procState = PROCESS_STATE_CUR_TOP; 18808 } 18809 schedGroup = ProcessList.SCHED_GROUP_DEFAULT; 18810 app.cached = false; 18811 app.empty = false; 18812 foregroundActivities = true; 18813 if (r.task != null && minLayer > 0) { 18814 final int layer = r.task.mLayerRank; 18815 if (layer >= 0 && minLayer > layer) { 18816 minLayer = layer; 18817 } 18818 } 18819 break; 18820 } else if (r.state == ActivityState.PAUSING || r.state == ActivityState.PAUSED) { 18821 if (adj > ProcessList.PERCEPTIBLE_APP_ADJ) { 18822 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 18823 app.adjType = "pausing"; 18824 } 18825 if (procState > PROCESS_STATE_CUR_TOP) { 18826 procState = PROCESS_STATE_CUR_TOP; 18827 } 18828 schedGroup = ProcessList.SCHED_GROUP_DEFAULT; 18829 app.cached = false; 18830 app.empty = false; 18831 foregroundActivities = true; 18832 } else if (r.state == ActivityState.STOPPING) { 18833 if (adj > ProcessList.PERCEPTIBLE_APP_ADJ) { 18834 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 18835 app.adjType = "stopping"; 18836 } 18837 // For the process state, we will at this point consider the 18838 // process to be cached. It will be cached either as an activity 18839 // or empty depending on whether the activity is finishing. We do 18840 // this so that we can treat the process as cached for purposes of 18841 // memory trimming (determing current memory level, trim command to 18842 // send to process) since there can be an arbitrary number of stopping 18843 // processes and they should soon all go into the cached state. 18844 if (!r.finishing) { 18845 if (procState > ActivityManager.PROCESS_STATE_LAST_ACTIVITY) { 18846 procState = ActivityManager.PROCESS_STATE_LAST_ACTIVITY; 18847 } 18848 } 18849 app.cached = false; 18850 app.empty = false; 18851 foregroundActivities = true; 18852 } else { 18853 if (procState > ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 18854 procState = ActivityManager.PROCESS_STATE_CACHED_ACTIVITY; 18855 app.adjType = "cch-act"; 18856 } 18857 } 18858 } 18859 if (adj == ProcessList.VISIBLE_APP_ADJ) { 18860 adj += minLayer; 18861 } 18862 } 18863 18864 if (adj > ProcessList.PERCEPTIBLE_APP_ADJ 18865 || procState > ActivityManager.PROCESS_STATE_FOREGROUND_SERVICE) { 18866 if (app.foregroundServices) { 18867 // The user is aware of this app, so make it visible. 18868 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 18869 procState = ActivityManager.PROCESS_STATE_FOREGROUND_SERVICE; 18870 app.cached = false; 18871 app.adjType = "fg-service"; 18872 schedGroup = ProcessList.SCHED_GROUP_DEFAULT; 18873 } else if (app.forcingToForeground != null) { 18874 // The user is aware of this app, so make it visible. 18875 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 18876 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 18877 app.cached = false; 18878 app.adjType = "force-fg"; 18879 app.adjSource = app.forcingToForeground; 18880 schedGroup = ProcessList.SCHED_GROUP_DEFAULT; 18881 } 18882 } 18883 18884 if (app == mHeavyWeightProcess) { 18885 if (adj > ProcessList.HEAVY_WEIGHT_APP_ADJ) { 18886 // We don't want to kill the current heavy-weight process. 18887 adj = ProcessList.HEAVY_WEIGHT_APP_ADJ; 18888 schedGroup = ProcessList.SCHED_GROUP_BACKGROUND; 18889 app.cached = false; 18890 app.adjType = "heavy"; 18891 } 18892 if (procState > ActivityManager.PROCESS_STATE_HEAVY_WEIGHT) { 18893 procState = ActivityManager.PROCESS_STATE_HEAVY_WEIGHT; 18894 } 18895 } 18896 18897 if (app == mHomeProcess) { 18898 if (adj > ProcessList.HOME_APP_ADJ) { 18899 // This process is hosting what we currently consider to be the 18900 // home app, so we don't want to let it go into the background. 18901 adj = ProcessList.HOME_APP_ADJ; 18902 schedGroup = ProcessList.SCHED_GROUP_BACKGROUND; 18903 app.cached = false; 18904 app.adjType = "home"; 18905 } 18906 if (procState > ActivityManager.PROCESS_STATE_HOME) { 18907 procState = ActivityManager.PROCESS_STATE_HOME; 18908 } 18909 } 18910 18911 if (app == mPreviousProcess && app.activities.size() > 0) { 18912 if (adj > ProcessList.PREVIOUS_APP_ADJ) { 18913 // This was the previous process that showed UI to the user. 18914 // We want to try to keep it around more aggressively, to give 18915 // a good experience around switching between two apps. 18916 adj = ProcessList.PREVIOUS_APP_ADJ; 18917 schedGroup = ProcessList.SCHED_GROUP_BACKGROUND; 18918 app.cached = false; 18919 app.adjType = "previous"; 18920 } 18921 if (procState > ActivityManager.PROCESS_STATE_LAST_ACTIVITY) { 18922 procState = ActivityManager.PROCESS_STATE_LAST_ACTIVITY; 18923 } 18924 } 18925 18926 if (false) Slog.i(TAG, "OOM " + app + ": initial adj=" + adj 18927 + " reason=" + app.adjType); 18928 18929 // By default, we use the computed adjustment. It may be changed if 18930 // there are applications dependent on our services or providers, but 18931 // this gives us a baseline and makes sure we don't get into an 18932 // infinite recursion. 18933 app.adjSeq = mAdjSeq; 18934 app.curRawAdj = adj; 18935 app.hasStartedServices = false; 18936 18937 if (mBackupTarget != null && app == mBackupTarget.app) { 18938 // If possible we want to avoid killing apps while they're being backed up 18939 if (adj > ProcessList.BACKUP_APP_ADJ) { 18940 if (DEBUG_BACKUP) Slog.v(TAG_BACKUP, "oom BACKUP_APP_ADJ for " + app); 18941 adj = ProcessList.BACKUP_APP_ADJ; 18942 if (procState > ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND) { 18943 procState = ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND; 18944 } 18945 app.adjType = "backup"; 18946 app.cached = false; 18947 } 18948 if (procState > ActivityManager.PROCESS_STATE_BACKUP) { 18949 procState = ActivityManager.PROCESS_STATE_BACKUP; 18950 } 18951 } 18952 18953 boolean mayBeTop = false; 18954 18955 for (int is = app.services.size()-1; 18956 is >= 0 && (adj > ProcessList.FOREGROUND_APP_ADJ 18957 || schedGroup == ProcessList.SCHED_GROUP_BACKGROUND 18958 || procState > ActivityManager.PROCESS_STATE_TOP); 18959 is--) { 18960 ServiceRecord s = app.services.valueAt(is); 18961 if (s.startRequested) { 18962 app.hasStartedServices = true; 18963 if (procState > ActivityManager.PROCESS_STATE_SERVICE) { 18964 procState = ActivityManager.PROCESS_STATE_SERVICE; 18965 } 18966 if (app.hasShownUi && app != mHomeProcess) { 18967 // If this process has shown some UI, let it immediately 18968 // go to the LRU list because it may be pretty heavy with 18969 // UI stuff. We'll tag it with a label just to help 18970 // debug and understand what is going on. 18971 if (adj > ProcessList.SERVICE_ADJ) { 18972 app.adjType = "cch-started-ui-services"; 18973 } 18974 } else { 18975 if (now < (s.lastActivity + ActiveServices.MAX_SERVICE_INACTIVITY)) { 18976 // This service has seen some activity within 18977 // recent memory, so we will keep its process ahead 18978 // of the background processes. 18979 if (adj > ProcessList.SERVICE_ADJ) { 18980 adj = ProcessList.SERVICE_ADJ; 18981 app.adjType = "started-services"; 18982 app.cached = false; 18983 } 18984 } 18985 // If we have let the service slide into the background 18986 // state, still have some text describing what it is doing 18987 // even though the service no longer has an impact. 18988 if (adj > ProcessList.SERVICE_ADJ) { 18989 app.adjType = "cch-started-services"; 18990 } 18991 } 18992 } 18993 for (int conni = s.connections.size()-1; 18994 conni >= 0 && (adj > ProcessList.FOREGROUND_APP_ADJ 18995 || schedGroup == ProcessList.SCHED_GROUP_BACKGROUND 18996 || procState > ActivityManager.PROCESS_STATE_TOP); 18997 conni--) { 18998 ArrayList<ConnectionRecord> clist = s.connections.valueAt(conni); 18999 for (int i = 0; 19000 i < clist.size() && (adj > ProcessList.FOREGROUND_APP_ADJ 19001 || schedGroup == ProcessList.SCHED_GROUP_BACKGROUND 19002 || procState > ActivityManager.PROCESS_STATE_TOP); 19003 i++) { 19004 // XXX should compute this based on the max of 19005 // all connected clients. 19006 ConnectionRecord cr = clist.get(i); 19007 if (cr.binding.client == app) { 19008 // Binding to ourself is not interesting. 19009 continue; 19010 } 19011 if ((cr.flags&Context.BIND_WAIVE_PRIORITY) == 0) { 19012 ProcessRecord client = cr.binding.client; 19013 int clientAdj = computeOomAdjLocked(client, cachedAdj, 19014 TOP_APP, doingAll, now); 19015 int clientProcState = client.curProcState; 19016 if (clientProcState >= ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 19017 // If the other app is cached for any reason, for purposes here 19018 // we are going to consider it empty. The specific cached state 19019 // doesn't propagate except under certain conditions. 19020 clientProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 19021 } 19022 String adjType = null; 19023 if ((cr.flags&Context.BIND_ALLOW_OOM_MANAGEMENT) != 0) { 19024 // Not doing bind OOM management, so treat 19025 // this guy more like a started service. 19026 if (app.hasShownUi && app != mHomeProcess) { 19027 // If this process has shown some UI, let it immediately 19028 // go to the LRU list because it may be pretty heavy with 19029 // UI stuff. We'll tag it with a label just to help 19030 // debug and understand what is going on. 19031 if (adj > clientAdj) { 19032 adjType = "cch-bound-ui-services"; 19033 } 19034 app.cached = false; 19035 clientAdj = adj; 19036 clientProcState = procState; 19037 } else { 19038 if (now >= (s.lastActivity 19039 + ActiveServices.MAX_SERVICE_INACTIVITY)) { 19040 // This service has not seen activity within 19041 // recent memory, so allow it to drop to the 19042 // LRU list if there is no other reason to keep 19043 // it around. We'll also tag it with a label just 19044 // to help debug and undertand what is going on. 19045 if (adj > clientAdj) { 19046 adjType = "cch-bound-services"; 19047 } 19048 clientAdj = adj; 19049 } 19050 } 19051 } 19052 if (adj > clientAdj) { 19053 // If this process has recently shown UI, and 19054 // the process that is binding to it is less 19055 // important than being visible, then we don't 19056 // care about the binding as much as we care 19057 // about letting this process get into the LRU 19058 // list to be killed and restarted if needed for 19059 // memory. 19060 if (app.hasShownUi && app != mHomeProcess 19061 && clientAdj > ProcessList.PERCEPTIBLE_APP_ADJ) { 19062 adjType = "cch-bound-ui-services"; 19063 } else { 19064 if ((cr.flags&(Context.BIND_ABOVE_CLIENT 19065 |Context.BIND_IMPORTANT)) != 0) { 19066 adj = clientAdj >= ProcessList.PERSISTENT_SERVICE_ADJ 19067 ? clientAdj : ProcessList.PERSISTENT_SERVICE_ADJ; 19068 } else if ((cr.flags&Context.BIND_NOT_VISIBLE) != 0 19069 && clientAdj < ProcessList.PERCEPTIBLE_APP_ADJ 19070 && adj > ProcessList.PERCEPTIBLE_APP_ADJ) { 19071 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 19072 } else if (clientAdj >= ProcessList.PERCEPTIBLE_APP_ADJ) { 19073 adj = clientAdj; 19074 } else { 19075 if (adj > ProcessList.VISIBLE_APP_ADJ) { 19076 adj = Math.max(clientAdj, ProcessList.VISIBLE_APP_ADJ); 19077 } 19078 } 19079 if (!client.cached) { 19080 app.cached = false; 19081 } 19082 adjType = "service"; 19083 } 19084 } 19085 if ((cr.flags&Context.BIND_NOT_FOREGROUND) == 0) { 19086 // This will treat important bound services identically to 19087 // the top app, which may behave differently than generic 19088 // foreground work. 19089 if (client.curSchedGroup > schedGroup) { 19090 if ((cr.flags&Context.BIND_IMPORTANT) != 0) { 19091 schedGroup = client.curSchedGroup; 19092 } else { 19093 schedGroup = ProcessList.SCHED_GROUP_DEFAULT; 19094 } 19095 } 19096 if (clientProcState <= ActivityManager.PROCESS_STATE_TOP) { 19097 if (clientProcState == ActivityManager.PROCESS_STATE_TOP) { 19098 // Special handling of clients who are in the top state. 19099 // We *may* want to consider this process to be in the 19100 // top state as well, but only if there is not another 19101 // reason for it to be running. Being on the top is a 19102 // special state, meaning you are specifically running 19103 // for the current top app. If the process is already 19104 // running in the background for some other reason, it 19105 // is more important to continue considering it to be 19106 // in the background state. 19107 mayBeTop = true; 19108 clientProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 19109 } else { 19110 // Special handling for above-top states (persistent 19111 // processes). These should not bring the current process 19112 // into the top state, since they are not on top. Instead 19113 // give them the best state after that. 19114 if ((cr.flags&Context.BIND_FOREGROUND_SERVICE) != 0) { 19115 clientProcState = 19116 ActivityManager.PROCESS_STATE_BOUND_FOREGROUND_SERVICE; 19117 } else if (mWakefulness 19118 == PowerManagerInternal.WAKEFULNESS_AWAKE && 19119 (cr.flags&Context.BIND_FOREGROUND_SERVICE_WHILE_AWAKE) 19120 != 0) { 19121 clientProcState = 19122 ActivityManager.PROCESS_STATE_BOUND_FOREGROUND_SERVICE; 19123 } else { 19124 clientProcState = 19125 ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 19126 } 19127 } 19128 } 19129 } else { 19130 if (clientProcState < 19131 ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND) { 19132 clientProcState = 19133 ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND; 19134 } 19135 } 19136 if (procState > clientProcState) { 19137 procState = clientProcState; 19138 } 19139 if (procState < ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND 19140 && (cr.flags&Context.BIND_SHOWING_UI) != 0) { 19141 app.pendingUiClean = true; 19142 } 19143 if (adjType != null) { 19144 app.adjType = adjType; 19145 app.adjTypeCode = ActivityManager.RunningAppProcessInfo 19146 .REASON_SERVICE_IN_USE; 19147 app.adjSource = cr.binding.client; 19148 app.adjSourceProcState = clientProcState; 19149 app.adjTarget = s.name; 19150 } 19151 } 19152 if ((cr.flags&Context.BIND_TREAT_LIKE_ACTIVITY) != 0) { 19153 app.treatLikeActivity = true; 19154 } 19155 final ActivityRecord a = cr.activity; 19156 if ((cr.flags&Context.BIND_ADJUST_WITH_ACTIVITY) != 0) { 19157 if (a != null && adj > ProcessList.FOREGROUND_APP_ADJ && 19158 (a.visible || a.state == ActivityState.RESUMED || 19159 a.state == ActivityState.PAUSING)) { 19160 adj = ProcessList.FOREGROUND_APP_ADJ; 19161 if ((cr.flags&Context.BIND_NOT_FOREGROUND) == 0) { 19162 if ((cr.flags&Context.BIND_IMPORTANT) != 0) { 19163 schedGroup = ProcessList.SCHED_GROUP_TOP_APP; 19164 } else { 19165 schedGroup = ProcessList.SCHED_GROUP_DEFAULT; 19166 } 19167 } 19168 app.cached = false; 19169 app.adjType = "service"; 19170 app.adjTypeCode = ActivityManager.RunningAppProcessInfo 19171 .REASON_SERVICE_IN_USE; 19172 app.adjSource = a; 19173 app.adjSourceProcState = procState; 19174 app.adjTarget = s.name; 19175 } 19176 } 19177 } 19178 } 19179 } 19180 19181 for (int provi = app.pubProviders.size()-1; 19182 provi >= 0 && (adj > ProcessList.FOREGROUND_APP_ADJ 19183 || schedGroup == ProcessList.SCHED_GROUP_BACKGROUND 19184 || procState > ActivityManager.PROCESS_STATE_TOP); 19185 provi--) { 19186 ContentProviderRecord cpr = app.pubProviders.valueAt(provi); 19187 for (int i = cpr.connections.size()-1; 19188 i >= 0 && (adj > ProcessList.FOREGROUND_APP_ADJ 19189 || schedGroup == ProcessList.SCHED_GROUP_BACKGROUND 19190 || procState > ActivityManager.PROCESS_STATE_TOP); 19191 i--) { 19192 ContentProviderConnection conn = cpr.connections.get(i); 19193 ProcessRecord client = conn.client; 19194 if (client == app) { 19195 // Being our own client is not interesting. 19196 continue; 19197 } 19198 int clientAdj = computeOomAdjLocked(client, cachedAdj, TOP_APP, doingAll, now); 19199 int clientProcState = client.curProcState; 19200 if (clientProcState >= ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 19201 // If the other app is cached for any reason, for purposes here 19202 // we are going to consider it empty. 19203 clientProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 19204 } 19205 if (adj > clientAdj) { 19206 if (app.hasShownUi && app != mHomeProcess 19207 && clientAdj > ProcessList.PERCEPTIBLE_APP_ADJ) { 19208 app.adjType = "cch-ui-provider"; 19209 } else { 19210 adj = clientAdj > ProcessList.FOREGROUND_APP_ADJ 19211 ? clientAdj : ProcessList.FOREGROUND_APP_ADJ; 19212 app.adjType = "provider"; 19213 } 19214 app.cached &= client.cached; 19215 app.adjTypeCode = ActivityManager.RunningAppProcessInfo 19216 .REASON_PROVIDER_IN_USE; 19217 app.adjSource = client; 19218 app.adjSourceProcState = clientProcState; 19219 app.adjTarget = cpr.name; 19220 } 19221 if (clientProcState <= ActivityManager.PROCESS_STATE_TOP) { 19222 if (clientProcState == ActivityManager.PROCESS_STATE_TOP) { 19223 // Special handling of clients who are in the top state. 19224 // We *may* want to consider this process to be in the 19225 // top state as well, but only if there is not another 19226 // reason for it to be running. Being on the top is a 19227 // special state, meaning you are specifically running 19228 // for the current top app. If the process is already 19229 // running in the background for some other reason, it 19230 // is more important to continue considering it to be 19231 // in the background state. 19232 mayBeTop = true; 19233 clientProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 19234 } else { 19235 // Special handling for above-top states (persistent 19236 // processes). These should not bring the current process 19237 // into the top state, since they are not on top. Instead 19238 // give them the best state after that. 19239 clientProcState = 19240 ActivityManager.PROCESS_STATE_BOUND_FOREGROUND_SERVICE; 19241 } 19242 } 19243 if (procState > clientProcState) { 19244 procState = clientProcState; 19245 } 19246 if (client.curSchedGroup > schedGroup) { 19247 schedGroup = ProcessList.SCHED_GROUP_DEFAULT; 19248 } 19249 } 19250 // If the provider has external (non-framework) process 19251 // dependencies, ensure that its adjustment is at least 19252 // FOREGROUND_APP_ADJ. 19253 if (cpr.hasExternalProcessHandles()) { 19254 if (adj > ProcessList.FOREGROUND_APP_ADJ) { 19255 adj = ProcessList.FOREGROUND_APP_ADJ; 19256 schedGroup = ProcessList.SCHED_GROUP_DEFAULT; 19257 app.cached = false; 19258 app.adjType = "provider"; 19259 app.adjTarget = cpr.name; 19260 } 19261 if (procState > ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND) { 19262 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 19263 } 19264 } 19265 } 19266 19267 if (app.lastProviderTime > 0 && (app.lastProviderTime+CONTENT_PROVIDER_RETAIN_TIME) > now) { 19268 if (adj > ProcessList.PREVIOUS_APP_ADJ) { 19269 adj = ProcessList.PREVIOUS_APP_ADJ; 19270 schedGroup = ProcessList.SCHED_GROUP_BACKGROUND; 19271 app.cached = false; 19272 app.adjType = "provider"; 19273 } 19274 if (procState > ActivityManager.PROCESS_STATE_LAST_ACTIVITY) { 19275 procState = ActivityManager.PROCESS_STATE_LAST_ACTIVITY; 19276 } 19277 } 19278 19279 if (mayBeTop && procState > ActivityManager.PROCESS_STATE_TOP) { 19280 // A client of one of our services or providers is in the top state. We 19281 // *may* want to be in the top state, but not if we are already running in 19282 // the background for some other reason. For the decision here, we are going 19283 // to pick out a few specific states that we want to remain in when a client 19284 // is top (states that tend to be longer-term) and otherwise allow it to go 19285 // to the top state. 19286 switch (procState) { 19287 case ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND: 19288 case ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND: 19289 case ActivityManager.PROCESS_STATE_SERVICE: 19290 // These all are longer-term states, so pull them up to the top 19291 // of the background states, but not all the way to the top state. 19292 procState = ActivityManager.PROCESS_STATE_BOUND_FOREGROUND_SERVICE; 19293 break; 19294 default: 19295 // Otherwise, top is a better choice, so take it. 19296 procState = ActivityManager.PROCESS_STATE_TOP; 19297 break; 19298 } 19299 } 19300 19301 if (procState >= ActivityManager.PROCESS_STATE_CACHED_EMPTY) { 19302 if (app.hasClientActivities) { 19303 // This is a cached process, but with client activities. Mark it so. 19304 procState = ActivityManager.PROCESS_STATE_CACHED_ACTIVITY_CLIENT; 19305 app.adjType = "cch-client-act"; 19306 } else if (app.treatLikeActivity) { 19307 // This is a cached process, but somebody wants us to treat it like it has 19308 // an activity, okay! 19309 procState = ActivityManager.PROCESS_STATE_CACHED_ACTIVITY; 19310 app.adjType = "cch-as-act"; 19311 } 19312 } 19313 19314 if (adj == ProcessList.SERVICE_ADJ) { 19315 if (doingAll) { 19316 app.serviceb = mNewNumAServiceProcs > (mNumServiceProcs/3); 19317 mNewNumServiceProcs++; 19318 //Slog.i(TAG, "ADJ " + app + " serviceb=" + app.serviceb); 19319 if (!app.serviceb) { 19320 // This service isn't far enough down on the LRU list to 19321 // normally be a B service, but if we are low on RAM and it 19322 // is large we want to force it down since we would prefer to 19323 // keep launcher over it. 19324 if (mLastMemoryLevel > ProcessStats.ADJ_MEM_FACTOR_NORMAL 19325 && app.lastPss >= mProcessList.getCachedRestoreThresholdKb()) { 19326 app.serviceHighRam = true; 19327 app.serviceb = true; 19328 //Slog.i(TAG, "ADJ " + app + " high ram!"); 19329 } else { 19330 mNewNumAServiceProcs++; 19331 //Slog.i(TAG, "ADJ " + app + " not high ram!"); 19332 } 19333 } else { 19334 app.serviceHighRam = false; 19335 } 19336 } 19337 if (app.serviceb) { 19338 adj = ProcessList.SERVICE_B_ADJ; 19339 } 19340 } 19341 19342 app.curRawAdj = adj; 19343 19344 //Slog.i(TAG, "OOM ADJ " + app + ": pid=" + app.pid + 19345 // " adj=" + adj + " curAdj=" + app.curAdj + " maxAdj=" + app.maxAdj); 19346 if (adj > app.maxAdj) { 19347 adj = app.maxAdj; 19348 if (app.maxAdj <= ProcessList.PERCEPTIBLE_APP_ADJ) { 19349 schedGroup = ProcessList.SCHED_GROUP_DEFAULT; 19350 } 19351 } 19352 19353 // Do final modification to adj. Everything we do between here and applying 19354 // the final setAdj must be done in this function, because we will also use 19355 // it when computing the final cached adj later. Note that we don't need to 19356 // worry about this for max adj above, since max adj will always be used to 19357 // keep it out of the cached vaues. 19358 app.curAdj = app.modifyRawOomAdj(adj); 19359 app.curSchedGroup = schedGroup; 19360 app.curProcState = procState; 19361 app.foregroundActivities = foregroundActivities; 19362 19363 return app.curRawAdj; 19364 } 19365 19366 /** 19367 * Record new PSS sample for a process. 19368 */ 19369 void recordPssSampleLocked(ProcessRecord proc, int procState, long pss, long uss, long swapPss, 19370 long now) { 19371 EventLogTags.writeAmPss(proc.pid, proc.uid, proc.processName, pss * 1024, uss * 1024, 19372 swapPss * 1024); 19373 proc.lastPssTime = now; 19374 proc.baseProcessTracker.addPss(pss, uss, true, proc.pkgList); 19375 if (DEBUG_PSS) Slog.d(TAG_PSS, 19376 "PSS of " + proc.toShortString() + ": " + pss + " lastPss=" + proc.lastPss 19377 + " state=" + ProcessList.makeProcStateString(procState)); 19378 if (proc.initialIdlePss == 0) { 19379 proc.initialIdlePss = pss; 19380 } 19381 proc.lastPss = pss; 19382 proc.lastSwapPss = swapPss; 19383 if (procState >= ActivityManager.PROCESS_STATE_HOME) { 19384 proc.lastCachedPss = pss; 19385 proc.lastCachedSwapPss = swapPss; 19386 } 19387 19388 final SparseArray<Pair<Long, String>> watchUids 19389 = mMemWatchProcesses.getMap().get(proc.processName); 19390 Long check = null; 19391 if (watchUids != null) { 19392 Pair<Long, String> val = watchUids.get(proc.uid); 19393 if (val == null) { 19394 val = watchUids.get(0); 19395 } 19396 if (val != null) { 19397 check = val.first; 19398 } 19399 } 19400 if (check != null) { 19401 if ((pss * 1024) >= check && proc.thread != null && mMemWatchDumpProcName == null) { 19402 boolean isDebuggable = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 19403 if (!isDebuggable) { 19404 if ((proc.info.flags&ApplicationInfo.FLAG_DEBUGGABLE) != 0) { 19405 isDebuggable = true; 19406 } 19407 } 19408 if (isDebuggable) { 19409 Slog.w(TAG, "Process " + proc + " exceeded pss limit " + check + "; reporting"); 19410 final ProcessRecord myProc = proc; 19411 final File heapdumpFile = DumpHeapProvider.getJavaFile(); 19412 mMemWatchDumpProcName = proc.processName; 19413 mMemWatchDumpFile = heapdumpFile.toString(); 19414 mMemWatchDumpPid = proc.pid; 19415 mMemWatchDumpUid = proc.uid; 19416 BackgroundThread.getHandler().post(new Runnable() { 19417 @Override 19418 public void run() { 19419 revokeUriPermission(ActivityThread.currentActivityThread() 19420 .getApplicationThread(), 19421 DumpHeapActivity.JAVA_URI, 19422 Intent.FLAG_GRANT_READ_URI_PERMISSION 19423 | Intent.FLAG_GRANT_WRITE_URI_PERMISSION, 19424 UserHandle.myUserId()); 19425 ParcelFileDescriptor fd = null; 19426 try { 19427 heapdumpFile.delete(); 19428 fd = ParcelFileDescriptor.open(heapdumpFile, 19429 ParcelFileDescriptor.MODE_CREATE | 19430 ParcelFileDescriptor.MODE_TRUNCATE | 19431 ParcelFileDescriptor.MODE_WRITE_ONLY | 19432 ParcelFileDescriptor.MODE_APPEND); 19433 IApplicationThread thread = myProc.thread; 19434 if (thread != null) { 19435 try { 19436 if (DEBUG_PSS) Slog.d(TAG_PSS, 19437 "Requesting dump heap from " 19438 + myProc + " to " + heapdumpFile); 19439 thread.dumpHeap(true, heapdumpFile.toString(), fd); 19440 } catch (RemoteException e) { 19441 } 19442 } 19443 } catch (FileNotFoundException e) { 19444 e.printStackTrace(); 19445 } finally { 19446 if (fd != null) { 19447 try { 19448 fd.close(); 19449 } catch (IOException e) { 19450 } 19451 } 19452 } 19453 } 19454 }); 19455 } else { 19456 Slog.w(TAG, "Process " + proc + " exceeded pss limit " + check 19457 + ", but debugging not enabled"); 19458 } 19459 } 19460 } 19461 } 19462 19463 /** 19464 * Schedule PSS collection of a process. 19465 */ 19466 void requestPssLocked(ProcessRecord proc, int procState) { 19467 if (mPendingPssProcesses.contains(proc)) { 19468 return; 19469 } 19470 if (mPendingPssProcesses.size() == 0) { 19471 mBgHandler.sendEmptyMessage(COLLECT_PSS_BG_MSG); 19472 } 19473 if (DEBUG_PSS) Slog.d(TAG_PSS, "Requesting PSS of: " + proc); 19474 proc.pssProcState = procState; 19475 mPendingPssProcesses.add(proc); 19476 } 19477 19478 /** 19479 * Schedule PSS collection of all processes. 19480 */ 19481 void requestPssAllProcsLocked(long now, boolean always, boolean memLowered) { 19482 if (!always) { 19483 if (now < (mLastFullPssTime + 19484 (memLowered ? FULL_PSS_LOWERED_INTERVAL : FULL_PSS_MIN_INTERVAL))) { 19485 return; 19486 } 19487 } 19488 if (DEBUG_PSS) Slog.d(TAG_PSS, "Requesting PSS of all procs! memLowered=" + memLowered); 19489 mLastFullPssTime = now; 19490 mFullPssPending = true; 19491 mPendingPssProcesses.ensureCapacity(mLruProcesses.size()); 19492 mPendingPssProcesses.clear(); 19493 for (int i = mLruProcesses.size() - 1; i >= 0; i--) { 19494 ProcessRecord app = mLruProcesses.get(i); 19495 if (app.thread == null 19496 || app.curProcState == ActivityManager.PROCESS_STATE_NONEXISTENT) { 19497 continue; 19498 } 19499 if (memLowered || now > (app.lastStateTime+ProcessList.PSS_ALL_INTERVAL)) { 19500 app.pssProcState = app.setProcState; 19501 app.nextPssTime = ProcessList.computeNextPssTime(app.curProcState, true, 19502 mTestPssMode, isSleeping(), now); 19503 mPendingPssProcesses.add(app); 19504 } 19505 } 19506 mBgHandler.sendEmptyMessage(COLLECT_PSS_BG_MSG); 19507 } 19508 19509 public void setTestPssMode(boolean enabled) { 19510 synchronized (this) { 19511 mTestPssMode = enabled; 19512 if (enabled) { 19513 // Whenever we enable the mode, we want to take a snapshot all of current 19514 // process mem use. 19515 requestPssAllProcsLocked(SystemClock.uptimeMillis(), true, true); 19516 } 19517 } 19518 } 19519 19520 /** 19521 * Ask a given process to GC right now. 19522 */ 19523 final void performAppGcLocked(ProcessRecord app) { 19524 try { 19525 app.lastRequestedGc = SystemClock.uptimeMillis(); 19526 if (app.thread != null) { 19527 if (app.reportLowMemory) { 19528 app.reportLowMemory = false; 19529 app.thread.scheduleLowMemory(); 19530 } else { 19531 app.thread.processInBackground(); 19532 } 19533 } 19534 } catch (Exception e) { 19535 // whatever. 19536 } 19537 } 19538 19539 /** 19540 * Returns true if things are idle enough to perform GCs. 19541 */ 19542 private final boolean canGcNowLocked() { 19543 boolean processingBroadcasts = false; 19544 for (BroadcastQueue q : mBroadcastQueues) { 19545 if (q.mParallelBroadcasts.size() != 0 || q.mOrderedBroadcasts.size() != 0) { 19546 processingBroadcasts = true; 19547 } 19548 } 19549 return !processingBroadcasts 19550 && (isSleeping() || mStackSupervisor.allResumedActivitiesIdle()); 19551 } 19552 19553 /** 19554 * Perform GCs on all processes that are waiting for it, but only 19555 * if things are idle. 19556 */ 19557 final void performAppGcsLocked() { 19558 final int N = mProcessesToGc.size(); 19559 if (N <= 0) { 19560 return; 19561 } 19562 if (canGcNowLocked()) { 19563 while (mProcessesToGc.size() > 0) { 19564 ProcessRecord proc = mProcessesToGc.remove(0); 19565 if (proc.curRawAdj > ProcessList.PERCEPTIBLE_APP_ADJ || proc.reportLowMemory) { 19566 if ((proc.lastRequestedGc+GC_MIN_INTERVAL) 19567 <= SystemClock.uptimeMillis()) { 19568 // To avoid spamming the system, we will GC processes one 19569 // at a time, waiting a few seconds between each. 19570 performAppGcLocked(proc); 19571 scheduleAppGcsLocked(); 19572 return; 19573 } else { 19574 // It hasn't been long enough since we last GCed this 19575 // process... put it in the list to wait for its time. 19576 addProcessToGcListLocked(proc); 19577 break; 19578 } 19579 } 19580 } 19581 19582 scheduleAppGcsLocked(); 19583 } 19584 } 19585 19586 /** 19587 * If all looks good, perform GCs on all processes waiting for them. 19588 */ 19589 final void performAppGcsIfAppropriateLocked() { 19590 if (canGcNowLocked()) { 19591 performAppGcsLocked(); 19592 return; 19593 } 19594 // Still not idle, wait some more. 19595 scheduleAppGcsLocked(); 19596 } 19597 19598 /** 19599 * Schedule the execution of all pending app GCs. 19600 */ 19601 final void scheduleAppGcsLocked() { 19602 mHandler.removeMessages(GC_BACKGROUND_PROCESSES_MSG); 19603 19604 if (mProcessesToGc.size() > 0) { 19605 // Schedule a GC for the time to the next process. 19606 ProcessRecord proc = mProcessesToGc.get(0); 19607 Message msg = mHandler.obtainMessage(GC_BACKGROUND_PROCESSES_MSG); 19608 19609 long when = proc.lastRequestedGc + GC_MIN_INTERVAL; 19610 long now = SystemClock.uptimeMillis(); 19611 if (when < (now+GC_TIMEOUT)) { 19612 when = now + GC_TIMEOUT; 19613 } 19614 mHandler.sendMessageAtTime(msg, when); 19615 } 19616 } 19617 19618 /** 19619 * Add a process to the array of processes waiting to be GCed. Keeps the 19620 * list in sorted order by the last GC time. The process can't already be 19621 * on the list. 19622 */ 19623 final void addProcessToGcListLocked(ProcessRecord proc) { 19624 boolean added = false; 19625 for (int i=mProcessesToGc.size()-1; i>=0; i--) { 19626 if (mProcessesToGc.get(i).lastRequestedGc < 19627 proc.lastRequestedGc) { 19628 added = true; 19629 mProcessesToGc.add(i+1, proc); 19630 break; 19631 } 19632 } 19633 if (!added) { 19634 mProcessesToGc.add(0, proc); 19635 } 19636 } 19637 19638 /** 19639 * Set up to ask a process to GC itself. This will either do it 19640 * immediately, or put it on the list of processes to gc the next 19641 * time things are idle. 19642 */ 19643 final void scheduleAppGcLocked(ProcessRecord app) { 19644 long now = SystemClock.uptimeMillis(); 19645 if ((app.lastRequestedGc+GC_MIN_INTERVAL) > now) { 19646 return; 19647 } 19648 if (!mProcessesToGc.contains(app)) { 19649 addProcessToGcListLocked(app); 19650 scheduleAppGcsLocked(); 19651 } 19652 } 19653 19654 final void checkExcessivePowerUsageLocked(boolean doKills) { 19655 updateCpuStatsNow(); 19656 19657 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 19658 boolean doWakeKills = doKills; 19659 boolean doCpuKills = doKills; 19660 if (mLastPowerCheckRealtime == 0) { 19661 doWakeKills = false; 19662 } 19663 if (mLastPowerCheckUptime == 0) { 19664 doCpuKills = false; 19665 } 19666 if (stats.isScreenOn()) { 19667 doWakeKills = false; 19668 } 19669 final long curRealtime = SystemClock.elapsedRealtime(); 19670 final long realtimeSince = curRealtime - mLastPowerCheckRealtime; 19671 final long curUptime = SystemClock.uptimeMillis(); 19672 final long uptimeSince = curUptime - mLastPowerCheckUptime; 19673 mLastPowerCheckRealtime = curRealtime; 19674 mLastPowerCheckUptime = curUptime; 19675 if (realtimeSince < WAKE_LOCK_MIN_CHECK_DURATION) { 19676 doWakeKills = false; 19677 } 19678 if (uptimeSince < CPU_MIN_CHECK_DURATION) { 19679 doCpuKills = false; 19680 } 19681 int i = mLruProcesses.size(); 19682 while (i > 0) { 19683 i--; 19684 ProcessRecord app = mLruProcesses.get(i); 19685 if (app.setProcState >= ActivityManager.PROCESS_STATE_HOME) { 19686 long wtime; 19687 synchronized (stats) { 19688 wtime = stats.getProcessWakeTime(app.info.uid, 19689 app.pid, curRealtime); 19690 } 19691 long wtimeUsed = wtime - app.lastWakeTime; 19692 long cputimeUsed = app.curCpuTime - app.lastCpuTime; 19693 if (DEBUG_POWER) { 19694 StringBuilder sb = new StringBuilder(128); 19695 sb.append("Wake for "); 19696 app.toShortString(sb); 19697 sb.append(": over "); 19698 TimeUtils.formatDuration(realtimeSince, sb); 19699 sb.append(" used "); 19700 TimeUtils.formatDuration(wtimeUsed, sb); 19701 sb.append(" ("); 19702 sb.append((wtimeUsed*100)/realtimeSince); 19703 sb.append("%)"); 19704 Slog.i(TAG_POWER, sb.toString()); 19705 sb.setLength(0); 19706 sb.append("CPU for "); 19707 app.toShortString(sb); 19708 sb.append(": over "); 19709 TimeUtils.formatDuration(uptimeSince, sb); 19710 sb.append(" used "); 19711 TimeUtils.formatDuration(cputimeUsed, sb); 19712 sb.append(" ("); 19713 sb.append((cputimeUsed*100)/uptimeSince); 19714 sb.append("%)"); 19715 Slog.i(TAG_POWER, sb.toString()); 19716 } 19717 // If a process has held a wake lock for more 19718 // than 50% of the time during this period, 19719 // that sounds bad. Kill! 19720 if (doWakeKills && realtimeSince > 0 19721 && ((wtimeUsed*100)/realtimeSince) >= 50) { 19722 synchronized (stats) { 19723 stats.reportExcessiveWakeLocked(app.info.uid, app.processName, 19724 realtimeSince, wtimeUsed); 19725 } 19726 app.kill("excessive wake held " + wtimeUsed + " during " + realtimeSince, true); 19727 app.baseProcessTracker.reportExcessiveWake(app.pkgList); 19728 } else if (doCpuKills && uptimeSince > 0 19729 && ((cputimeUsed*100)/uptimeSince) >= 25) { 19730 synchronized (stats) { 19731 stats.reportExcessiveCpuLocked(app.info.uid, app.processName, 19732 uptimeSince, cputimeUsed); 19733 } 19734 app.kill("excessive cpu " + cputimeUsed + " during " + uptimeSince, true); 19735 app.baseProcessTracker.reportExcessiveCpu(app.pkgList); 19736 } else { 19737 app.lastWakeTime = wtime; 19738 app.lastCpuTime = app.curCpuTime; 19739 } 19740 } 19741 } 19742 } 19743 19744 private final boolean applyOomAdjLocked(ProcessRecord app, boolean doingAll, long now, 19745 long nowElapsed) { 19746 boolean success = true; 19747 19748 if (app.curRawAdj != app.setRawAdj) { 19749 app.setRawAdj = app.curRawAdj; 19750 } 19751 19752 int changes = 0; 19753 19754 if (app.curAdj != app.setAdj) { 19755 ProcessList.setOomAdj(app.pid, app.info.uid, app.curAdj); 19756 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG_OOM_ADJ, 19757 "Set " + app.pid + " " + app.processName + " adj " + app.curAdj + ": " 19758 + app.adjType); 19759 app.setAdj = app.curAdj; 19760 } 19761 19762 if (app.setSchedGroup != app.curSchedGroup) { 19763 app.setSchedGroup = app.curSchedGroup; 19764 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG_OOM_ADJ, 19765 "Setting sched group of " + app.processName 19766 + " to " + app.curSchedGroup); 19767 if (app.waitingToKill != null && app.curReceiver == null 19768 && app.setSchedGroup == ProcessList.SCHED_GROUP_BACKGROUND) { 19769 app.kill(app.waitingToKill, true); 19770 success = false; 19771 } else { 19772 int processGroup; 19773 switch (app.curSchedGroup) { 19774 case ProcessList.SCHED_GROUP_BACKGROUND: 19775 processGroup = Process.THREAD_GROUP_BG_NONINTERACTIVE; 19776 break; 19777 case ProcessList.SCHED_GROUP_TOP_APP: 19778 processGroup = Process.THREAD_GROUP_TOP_APP; 19779 break; 19780 default: 19781 processGroup = Process.THREAD_GROUP_DEFAULT; 19782 break; 19783 } 19784 if (true) { 19785 long oldId = Binder.clearCallingIdentity(); 19786 try { 19787 Process.setProcessGroup(app.pid, processGroup); 19788 } catch (Exception e) { 19789 Slog.w(TAG, "Failed setting process group of " + app.pid 19790 + " to " + app.curSchedGroup); 19791 e.printStackTrace(); 19792 } finally { 19793 Binder.restoreCallingIdentity(oldId); 19794 } 19795 } else { 19796 if (app.thread != null) { 19797 try { 19798 app.thread.setSchedulingGroup(processGroup); 19799 } catch (RemoteException e) { 19800 } 19801 } 19802 } 19803 } 19804 } 19805 if (app.repForegroundActivities != app.foregroundActivities) { 19806 app.repForegroundActivities = app.foregroundActivities; 19807 changes |= ProcessChangeItem.CHANGE_ACTIVITIES; 19808 } 19809 if (app.repProcState != app.curProcState) { 19810 app.repProcState = app.curProcState; 19811 changes |= ProcessChangeItem.CHANGE_PROCESS_STATE; 19812 if (app.thread != null) { 19813 try { 19814 if (false) { 19815 //RuntimeException h = new RuntimeException("here"); 19816 Slog.i(TAG, "Sending new process state " + app.repProcState 19817 + " to " + app /*, h*/); 19818 } 19819 app.thread.setProcessState(app.repProcState); 19820 } catch (RemoteException e) { 19821 } 19822 } 19823 } 19824 if (app.setProcState == ActivityManager.PROCESS_STATE_NONEXISTENT 19825 || ProcessList.procStatesDifferForMem(app.curProcState, app.setProcState)) { 19826 if (false && mTestPssMode && app.setProcState >= 0 && app.lastStateTime <= (now-200)) { 19827 // Experimental code to more aggressively collect pss while 19828 // running test... the problem is that this tends to collect 19829 // the data right when a process is transitioning between process 19830 // states, which well tend to give noisy data. 19831 long start = SystemClock.uptimeMillis(); 19832 long pss = Debug.getPss(app.pid, mTmpLong, null); 19833 recordPssSampleLocked(app, app.curProcState, pss, mTmpLong[0], mTmpLong[1], now); 19834 mPendingPssProcesses.remove(app); 19835 Slog.i(TAG, "Recorded pss for " + app + " state " + app.setProcState 19836 + " to " + app.curProcState + ": " 19837 + (SystemClock.uptimeMillis()-start) + "ms"); 19838 } 19839 app.lastStateTime = now; 19840 app.nextPssTime = ProcessList.computeNextPssTime(app.curProcState, true, 19841 mTestPssMode, isSleeping(), now); 19842 if (DEBUG_PSS) Slog.d(TAG_PSS, "Process state change from " 19843 + ProcessList.makeProcStateString(app.setProcState) + " to " 19844 + ProcessList.makeProcStateString(app.curProcState) + " next pss in " 19845 + (app.nextPssTime-now) + ": " + app); 19846 } else { 19847 if (now > app.nextPssTime || (now > (app.lastPssTime+ProcessList.PSS_MAX_INTERVAL) 19848 && now > (app.lastStateTime+ProcessList.minTimeFromStateChange( 19849 mTestPssMode)))) { 19850 requestPssLocked(app, app.setProcState); 19851 app.nextPssTime = ProcessList.computeNextPssTime(app.curProcState, false, 19852 mTestPssMode, isSleeping(), now); 19853 } else if (false && DEBUG_PSS) Slog.d(TAG_PSS, 19854 "Not requesting PSS of " + app + ": next=" + (app.nextPssTime-now)); 19855 } 19856 if (app.setProcState != app.curProcState) { 19857 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG_OOM_ADJ, 19858 "Proc state change of " + app.processName 19859 + " to " + app.curProcState); 19860 boolean setImportant = app.setProcState < ActivityManager.PROCESS_STATE_SERVICE; 19861 boolean curImportant = app.curProcState < ActivityManager.PROCESS_STATE_SERVICE; 19862 if (setImportant && !curImportant) { 19863 // This app is no longer something we consider important enough to allow to 19864 // use arbitrary amounts of battery power. Note 19865 // its current wake lock time to later know to kill it if 19866 // it is not behaving well. 19867 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 19868 synchronized (stats) { 19869 app.lastWakeTime = stats.getProcessWakeTime(app.info.uid, 19870 app.pid, nowElapsed); 19871 } 19872 app.lastCpuTime = app.curCpuTime; 19873 19874 } 19875 // Inform UsageStats of important process state change 19876 // Must be called before updating setProcState 19877 maybeUpdateUsageStatsLocked(app, nowElapsed); 19878 19879 app.setProcState = app.curProcState; 19880 if (app.setProcState >= ActivityManager.PROCESS_STATE_HOME) { 19881 app.notCachedSinceIdle = false; 19882 } 19883 if (!doingAll) { 19884 setProcessTrackerStateLocked(app, mProcessStats.getMemFactorLocked(), now); 19885 } else { 19886 app.procStateChanged = true; 19887 } 19888 } else if (app.reportedInteraction && (nowElapsed-app.interactionEventTime) 19889 > USAGE_STATS_INTERACTION_INTERVAL) { 19890 // For apps that sit around for a long time in the interactive state, we need 19891 // to report this at least once a day so they don't go idle. 19892 maybeUpdateUsageStatsLocked(app, nowElapsed); 19893 } 19894 19895 if (changes != 0) { 19896 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG_PROCESS_OBSERVERS, 19897 "Changes in " + app + ": " + changes); 19898 int i = mPendingProcessChanges.size()-1; 19899 ProcessChangeItem item = null; 19900 while (i >= 0) { 19901 item = mPendingProcessChanges.get(i); 19902 if (item.pid == app.pid) { 19903 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG_PROCESS_OBSERVERS, 19904 "Re-using existing item: " + item); 19905 break; 19906 } 19907 i--; 19908 } 19909 if (i < 0) { 19910 // No existing item in pending changes; need a new one. 19911 final int NA = mAvailProcessChanges.size(); 19912 if (NA > 0) { 19913 item = mAvailProcessChanges.remove(NA-1); 19914 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG_PROCESS_OBSERVERS, 19915 "Retrieving available item: " + item); 19916 } else { 19917 item = new ProcessChangeItem(); 19918 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG_PROCESS_OBSERVERS, 19919 "Allocating new item: " + item); 19920 } 19921 item.changes = 0; 19922 item.pid = app.pid; 19923 item.uid = app.info.uid; 19924 if (mPendingProcessChanges.size() == 0) { 19925 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG_PROCESS_OBSERVERS, 19926 "*** Enqueueing dispatch processes changed!"); 19927 mUiHandler.obtainMessage(DISPATCH_PROCESSES_CHANGED_UI_MSG).sendToTarget(); 19928 } 19929 mPendingProcessChanges.add(item); 19930 } 19931 item.changes |= changes; 19932 item.processState = app.repProcState; 19933 item.foregroundActivities = app.repForegroundActivities; 19934 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG_PROCESS_OBSERVERS, 19935 "Item " + Integer.toHexString(System.identityHashCode(item)) 19936 + " " + app.toShortString() + ": changes=" + item.changes 19937 + " procState=" + item.processState 19938 + " foreground=" + item.foregroundActivities 19939 + " type=" + app.adjType + " source=" + app.adjSource 19940 + " target=" + app.adjTarget); 19941 } 19942 19943 return success; 19944 } 19945 19946 private final void enqueueUidChangeLocked(UidRecord uidRec, int uid, int change) { 19947 final UidRecord.ChangeItem pendingChange; 19948 if (uidRec == null || uidRec.pendingChange == null) { 19949 if (mPendingUidChanges.size() == 0) { 19950 if (DEBUG_UID_OBSERVERS) Slog.i(TAG_UID_OBSERVERS, 19951 "*** Enqueueing dispatch uid changed!"); 19952 mUiHandler.obtainMessage(DISPATCH_UIDS_CHANGED_UI_MSG).sendToTarget(); 19953 } 19954 final int NA = mAvailUidChanges.size(); 19955 if (NA > 0) { 19956 pendingChange = mAvailUidChanges.remove(NA-1); 19957 if (DEBUG_UID_OBSERVERS) Slog.i(TAG_UID_OBSERVERS, 19958 "Retrieving available item: " + pendingChange); 19959 } else { 19960 pendingChange = new UidRecord.ChangeItem(); 19961 if (DEBUG_UID_OBSERVERS) Slog.i(TAG_UID_OBSERVERS, 19962 "Allocating new item: " + pendingChange); 19963 } 19964 if (uidRec != null) { 19965 uidRec.pendingChange = pendingChange; 19966 if (change == UidRecord.CHANGE_GONE && !uidRec.idle) { 19967 // If this uid is going away, and we haven't yet reported it is gone, 19968 // then do so now. 19969 change = UidRecord.CHANGE_GONE_IDLE; 19970 } 19971 } else if (uid < 0) { 19972 throw new IllegalArgumentException("No UidRecord or uid"); 19973 } 19974 pendingChange.uidRecord = uidRec; 19975 pendingChange.uid = uidRec != null ? uidRec.uid : uid; 19976 mPendingUidChanges.add(pendingChange); 19977 } else { 19978 pendingChange = uidRec.pendingChange; 19979 if (change == UidRecord.CHANGE_GONE && pendingChange.change == UidRecord.CHANGE_IDLE) { 19980 change = UidRecord.CHANGE_GONE_IDLE; 19981 } 19982 } 19983 pendingChange.change = change; 19984 pendingChange.processState = uidRec != null 19985 ? uidRec.setProcState : ActivityManager.PROCESS_STATE_NONEXISTENT; 19986 } 19987 19988 private void maybeUpdateProviderUsageStatsLocked(ProcessRecord app, String providerPkgName, 19989 String authority) { 19990 if (app == null) return; 19991 if (app.curProcState <= ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND) { 19992 UserState userState = mUserController.getStartedUserStateLocked(app.userId); 19993 if (userState == null) return; 19994 final long now = SystemClock.elapsedRealtime(); 19995 Long lastReported = userState.mProviderLastReportedFg.get(authority); 19996 if (lastReported == null || lastReported < now - 60 * 1000L) { 19997 mUsageStatsService.reportContentProviderUsage( 19998 authority, providerPkgName, app.userId); 19999 userState.mProviderLastReportedFg.put(authority, now); 20000 } 20001 } 20002 } 20003 20004 private void maybeUpdateUsageStatsLocked(ProcessRecord app, long nowElapsed) { 20005 if (DEBUG_USAGE_STATS) { 20006 Slog.d(TAG, "Checking proc [" + Arrays.toString(app.getPackageList()) 20007 + "] state changes: old = " + app.setProcState + ", new = " 20008 + app.curProcState); 20009 } 20010 if (mUsageStatsService == null) { 20011 return; 20012 } 20013 boolean isInteraction; 20014 // To avoid some abuse patterns, we are going to be careful about what we consider 20015 // to be an app interaction. Being the top activity doesn't count while the display 20016 // is sleeping, nor do short foreground services. 20017 if (app.curProcState <= ActivityManager.PROCESS_STATE_BOUND_FOREGROUND_SERVICE) { 20018 isInteraction = true; 20019 app.fgInteractionTime = 0; 20020 } else if (app.curProcState <= ActivityManager.PROCESS_STATE_TOP_SLEEPING) { 20021 if (app.fgInteractionTime == 0) { 20022 app.fgInteractionTime = nowElapsed; 20023 isInteraction = false; 20024 } else { 20025 isInteraction = nowElapsed > app.fgInteractionTime + SERVICE_USAGE_INTERACTION_TIME; 20026 } 20027 } else { 20028 isInteraction = app.curProcState 20029 <= ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 20030 app.fgInteractionTime = 0; 20031 } 20032 if (isInteraction && (!app.reportedInteraction 20033 || (nowElapsed-app.interactionEventTime) > USAGE_STATS_INTERACTION_INTERVAL)) { 20034 app.interactionEventTime = nowElapsed; 20035 String[] packages = app.getPackageList(); 20036 if (packages != null) { 20037 for (int i = 0; i < packages.length; i++) { 20038 mUsageStatsService.reportEvent(packages[i], app.userId, 20039 UsageEvents.Event.SYSTEM_INTERACTION); 20040 } 20041 } 20042 } 20043 app.reportedInteraction = isInteraction; 20044 if (!isInteraction) { 20045 app.interactionEventTime = 0; 20046 } 20047 } 20048 20049 private final void setProcessTrackerStateLocked(ProcessRecord proc, int memFactor, long now) { 20050 if (proc.thread != null) { 20051 if (proc.baseProcessTracker != null) { 20052 proc.baseProcessTracker.setState(proc.repProcState, memFactor, now, proc.pkgList); 20053 } 20054 } 20055 } 20056 20057 private final boolean updateOomAdjLocked(ProcessRecord app, int cachedAdj, 20058 ProcessRecord TOP_APP, boolean doingAll, long now) { 20059 if (app.thread == null) { 20060 return false; 20061 } 20062 20063 computeOomAdjLocked(app, cachedAdj, TOP_APP, doingAll, now); 20064 20065 return applyOomAdjLocked(app, doingAll, now, SystemClock.elapsedRealtime()); 20066 } 20067 20068 final void updateProcessForegroundLocked(ProcessRecord proc, boolean isForeground, 20069 boolean oomAdj) { 20070 if (isForeground != proc.foregroundServices) { 20071 proc.foregroundServices = isForeground; 20072 ArrayList<ProcessRecord> curProcs = mForegroundPackages.get(proc.info.packageName, 20073 proc.info.uid); 20074 if (isForeground) { 20075 if (curProcs == null) { 20076 curProcs = new ArrayList<ProcessRecord>(); 20077 mForegroundPackages.put(proc.info.packageName, proc.info.uid, curProcs); 20078 } 20079 if (!curProcs.contains(proc)) { 20080 curProcs.add(proc); 20081 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_FOREGROUND_START, 20082 proc.info.packageName, proc.info.uid); 20083 } 20084 } else { 20085 if (curProcs != null) { 20086 if (curProcs.remove(proc)) { 20087 mBatteryStatsService.noteEvent( 20088 BatteryStats.HistoryItem.EVENT_FOREGROUND_FINISH, 20089 proc.info.packageName, proc.info.uid); 20090 if (curProcs.size() <= 0) { 20091 mForegroundPackages.remove(proc.info.packageName, proc.info.uid); 20092 } 20093 } 20094 } 20095 } 20096 if (oomAdj) { 20097 updateOomAdjLocked(); 20098 } 20099 } 20100 } 20101 20102 private final ActivityRecord resumedAppLocked() { 20103 ActivityRecord act = mStackSupervisor.resumedAppLocked(); 20104 String pkg; 20105 int uid; 20106 if (act != null) { 20107 pkg = act.packageName; 20108 uid = act.info.applicationInfo.uid; 20109 } else { 20110 pkg = null; 20111 uid = -1; 20112 } 20113 // Has the UID or resumed package name changed? 20114 if (uid != mCurResumedUid || (pkg != mCurResumedPackage 20115 && (pkg == null || !pkg.equals(mCurResumedPackage)))) { 20116 if (mCurResumedPackage != null) { 20117 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_TOP_FINISH, 20118 mCurResumedPackage, mCurResumedUid); 20119 } 20120 mCurResumedPackage = pkg; 20121 mCurResumedUid = uid; 20122 if (mCurResumedPackage != null) { 20123 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_TOP_START, 20124 mCurResumedPackage, mCurResumedUid); 20125 } 20126 } 20127 return act; 20128 } 20129 20130 final boolean updateOomAdjLocked(ProcessRecord app) { 20131 final ActivityRecord TOP_ACT = resumedAppLocked(); 20132 final ProcessRecord TOP_APP = TOP_ACT != null ? TOP_ACT.app : null; 20133 final boolean wasCached = app.cached; 20134 20135 mAdjSeq++; 20136 20137 // This is the desired cached adjusment we want to tell it to use. 20138 // If our app is currently cached, we know it, and that is it. Otherwise, 20139 // we don't know it yet, and it needs to now be cached we will then 20140 // need to do a complete oom adj. 20141 final int cachedAdj = app.curRawAdj >= ProcessList.CACHED_APP_MIN_ADJ 20142 ? app.curRawAdj : ProcessList.UNKNOWN_ADJ; 20143 boolean success = updateOomAdjLocked(app, cachedAdj, TOP_APP, false, 20144 SystemClock.uptimeMillis()); 20145 if (wasCached != app.cached || app.curRawAdj == ProcessList.UNKNOWN_ADJ) { 20146 // Changed to/from cached state, so apps after it in the LRU 20147 // list may also be changed. 20148 updateOomAdjLocked(); 20149 } 20150 return success; 20151 } 20152 20153 final void updateOomAdjLocked() { 20154 final ActivityRecord TOP_ACT = resumedAppLocked(); 20155 final ProcessRecord TOP_APP = TOP_ACT != null ? TOP_ACT.app : null; 20156 final long now = SystemClock.uptimeMillis(); 20157 final long nowElapsed = SystemClock.elapsedRealtime(); 20158 final long oldTime = now - ProcessList.MAX_EMPTY_TIME; 20159 final int N = mLruProcesses.size(); 20160 20161 if (false) { 20162 RuntimeException e = new RuntimeException(); 20163 e.fillInStackTrace(); 20164 Slog.i(TAG, "updateOomAdj: top=" + TOP_ACT, e); 20165 } 20166 20167 // Reset state in all uid records. 20168 for (int i=mActiveUids.size()-1; i>=0; i--) { 20169 final UidRecord uidRec = mActiveUids.valueAt(i); 20170 if (false && DEBUG_UID_OBSERVERS) Slog.i(TAG_UID_OBSERVERS, 20171 "Starting update of " + uidRec); 20172 uidRec.reset(); 20173 } 20174 20175 mStackSupervisor.rankTaskLayersIfNeeded(); 20176 20177 mAdjSeq++; 20178 mNewNumServiceProcs = 0; 20179 mNewNumAServiceProcs = 0; 20180 20181 final int emptyProcessLimit; 20182 final int cachedProcessLimit; 20183 if (mProcessLimit <= 0) { 20184 emptyProcessLimit = cachedProcessLimit = 0; 20185 } else if (mProcessLimit == 1) { 20186 emptyProcessLimit = 1; 20187 cachedProcessLimit = 0; 20188 } else { 20189 emptyProcessLimit = ProcessList.computeEmptyProcessLimit(mProcessLimit); 20190 cachedProcessLimit = mProcessLimit - emptyProcessLimit; 20191 } 20192 20193 // Let's determine how many processes we have running vs. 20194 // how many slots we have for background processes; we may want 20195 // to put multiple processes in a slot of there are enough of 20196 // them. 20197 int numSlots = (ProcessList.CACHED_APP_MAX_ADJ 20198 - ProcessList.CACHED_APP_MIN_ADJ + 1) / 2; 20199 int numEmptyProcs = N - mNumNonCachedProcs - mNumCachedHiddenProcs; 20200 if (numEmptyProcs > cachedProcessLimit) { 20201 // If there are more empty processes than our limit on cached 20202 // processes, then use the cached process limit for the factor. 20203 // This ensures that the really old empty processes get pushed 20204 // down to the bottom, so if we are running low on memory we will 20205 // have a better chance at keeping around more cached processes 20206 // instead of a gazillion empty processes. 20207 numEmptyProcs = cachedProcessLimit; 20208 } 20209 int emptyFactor = numEmptyProcs/numSlots; 20210 if (emptyFactor < 1) emptyFactor = 1; 20211 int cachedFactor = (mNumCachedHiddenProcs > 0 ? mNumCachedHiddenProcs : 1)/numSlots; 20212 if (cachedFactor < 1) cachedFactor = 1; 20213 int stepCached = 0; 20214 int stepEmpty = 0; 20215 int numCached = 0; 20216 int numEmpty = 0; 20217 int numTrimming = 0; 20218 20219 mNumNonCachedProcs = 0; 20220 mNumCachedHiddenProcs = 0; 20221 20222 // First update the OOM adjustment for each of the 20223 // application processes based on their current state. 20224 int curCachedAdj = ProcessList.CACHED_APP_MIN_ADJ; 20225 int nextCachedAdj = curCachedAdj+1; 20226 int curEmptyAdj = ProcessList.CACHED_APP_MIN_ADJ; 20227 int nextEmptyAdj = curEmptyAdj+2; 20228 for (int i=N-1; i>=0; i--) { 20229 ProcessRecord app = mLruProcesses.get(i); 20230 if (!app.killedByAm && app.thread != null) { 20231 app.procStateChanged = false; 20232 computeOomAdjLocked(app, ProcessList.UNKNOWN_ADJ, TOP_APP, true, now); 20233 20234 // If we haven't yet assigned the final cached adj 20235 // to the process, do that now. 20236 if (app.curAdj >= ProcessList.UNKNOWN_ADJ) { 20237 switch (app.curProcState) { 20238 case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY: 20239 case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY_CLIENT: 20240 // This process is a cached process holding activities... 20241 // assign it the next cached value for that type, and then 20242 // step that cached level. 20243 app.curRawAdj = curCachedAdj; 20244 app.curAdj = app.modifyRawOomAdj(curCachedAdj); 20245 if (DEBUG_LRU && false) Slog.d(TAG_LRU, "Assigning activity LRU #" + i 20246 + " adj: " + app.curAdj + " (curCachedAdj=" + curCachedAdj 20247 + ")"); 20248 if (curCachedAdj != nextCachedAdj) { 20249 stepCached++; 20250 if (stepCached >= cachedFactor) { 20251 stepCached = 0; 20252 curCachedAdj = nextCachedAdj; 20253 nextCachedAdj += 2; 20254 if (nextCachedAdj > ProcessList.CACHED_APP_MAX_ADJ) { 20255 nextCachedAdj = ProcessList.CACHED_APP_MAX_ADJ; 20256 } 20257 } 20258 } 20259 break; 20260 default: 20261 // For everything else, assign next empty cached process 20262 // level and bump that up. Note that this means that 20263 // long-running services that have dropped down to the 20264 // cached level will be treated as empty (since their process 20265 // state is still as a service), which is what we want. 20266 app.curRawAdj = curEmptyAdj; 20267 app.curAdj = app.modifyRawOomAdj(curEmptyAdj); 20268 if (DEBUG_LRU && false) Slog.d(TAG_LRU, "Assigning empty LRU #" + i 20269 + " adj: " + app.curAdj + " (curEmptyAdj=" + curEmptyAdj 20270 + ")"); 20271 if (curEmptyAdj != nextEmptyAdj) { 20272 stepEmpty++; 20273 if (stepEmpty >= emptyFactor) { 20274 stepEmpty = 0; 20275 curEmptyAdj = nextEmptyAdj; 20276 nextEmptyAdj += 2; 20277 if (nextEmptyAdj > ProcessList.CACHED_APP_MAX_ADJ) { 20278 nextEmptyAdj = ProcessList.CACHED_APP_MAX_ADJ; 20279 } 20280 } 20281 } 20282 break; 20283 } 20284 } 20285 20286 applyOomAdjLocked(app, true, now, nowElapsed); 20287 20288 // Count the number of process types. 20289 switch (app.curProcState) { 20290 case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY: 20291 case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY_CLIENT: 20292 mNumCachedHiddenProcs++; 20293 numCached++; 20294 if (numCached > cachedProcessLimit) { 20295 app.kill("cached #" + numCached, true); 20296 } 20297 break; 20298 case ActivityManager.PROCESS_STATE_CACHED_EMPTY: 20299 if (numEmpty > ProcessList.TRIM_EMPTY_APPS 20300 && app.lastActivityTime < oldTime) { 20301 app.kill("empty for " 20302 + ((oldTime + ProcessList.MAX_EMPTY_TIME - app.lastActivityTime) 20303 / 1000) + "s", true); 20304 } else { 20305 numEmpty++; 20306 if (numEmpty > emptyProcessLimit) { 20307 app.kill("empty #" + numEmpty, true); 20308 } 20309 } 20310 break; 20311 default: 20312 mNumNonCachedProcs++; 20313 break; 20314 } 20315 20316 if (app.isolated && app.services.size() <= 0) { 20317 // If this is an isolated process, and there are no 20318 // services running in it, then the process is no longer 20319 // needed. We agressively kill these because we can by 20320 // definition not re-use the same process again, and it is 20321 // good to avoid having whatever code was running in them 20322 // left sitting around after no longer needed. 20323 app.kill("isolated not needed", true); 20324 } else { 20325 // Keeping this process, update its uid. 20326 final UidRecord uidRec = app.uidRecord; 20327 if (uidRec != null && uidRec.curProcState > app.curProcState) { 20328 uidRec.curProcState = app.curProcState; 20329 } 20330 } 20331 20332 if (app.curProcState >= ActivityManager.PROCESS_STATE_HOME 20333 && !app.killedByAm) { 20334 numTrimming++; 20335 } 20336 } 20337 } 20338 20339 mNumServiceProcs = mNewNumServiceProcs; 20340 20341 // Now determine the memory trimming level of background processes. 20342 // Unfortunately we need to start at the back of the list to do this 20343 // properly. We only do this if the number of background apps we 20344 // are managing to keep around is less than half the maximum we desire; 20345 // if we are keeping a good number around, we'll let them use whatever 20346 // memory they want. 20347 final int numCachedAndEmpty = numCached + numEmpty; 20348 int memFactor; 20349 if (numCached <= ProcessList.TRIM_CACHED_APPS 20350 && numEmpty <= ProcessList.TRIM_EMPTY_APPS) { 20351 if (numCachedAndEmpty <= ProcessList.TRIM_CRITICAL_THRESHOLD) { 20352 memFactor = ProcessStats.ADJ_MEM_FACTOR_CRITICAL; 20353 } else if (numCachedAndEmpty <= ProcessList.TRIM_LOW_THRESHOLD) { 20354 memFactor = ProcessStats.ADJ_MEM_FACTOR_LOW; 20355 } else { 20356 memFactor = ProcessStats.ADJ_MEM_FACTOR_MODERATE; 20357 } 20358 } else { 20359 memFactor = ProcessStats.ADJ_MEM_FACTOR_NORMAL; 20360 } 20361 // We always allow the memory level to go up (better). We only allow it to go 20362 // down if we are in a state where that is allowed, *and* the total number of processes 20363 // has gone down since last time. 20364 if (DEBUG_OOM_ADJ) Slog.d(TAG_OOM_ADJ, "oom: memFactor=" + memFactor 20365 + " last=" + mLastMemoryLevel + " allowLow=" + mAllowLowerMemLevel 20366 + " numProcs=" + mLruProcesses.size() + " last=" + mLastNumProcesses); 20367 if (memFactor > mLastMemoryLevel) { 20368 if (!mAllowLowerMemLevel || mLruProcesses.size() >= mLastNumProcesses) { 20369 memFactor = mLastMemoryLevel; 20370 if (DEBUG_OOM_ADJ) Slog.d(TAG_OOM_ADJ, "Keeping last mem factor!"); 20371 } 20372 } 20373 if (memFactor != mLastMemoryLevel) { 20374 EventLogTags.writeAmMemFactor(memFactor, mLastMemoryLevel); 20375 } 20376 mLastMemoryLevel = memFactor; 20377 mLastNumProcesses = mLruProcesses.size(); 20378 boolean allChanged = mProcessStats.setMemFactorLocked(memFactor, !isSleeping(), now); 20379 final int trackerMemFactor = mProcessStats.getMemFactorLocked(); 20380 if (memFactor != ProcessStats.ADJ_MEM_FACTOR_NORMAL) { 20381 if (mLowRamStartTime == 0) { 20382 mLowRamStartTime = now; 20383 } 20384 int step = 0; 20385 int fgTrimLevel; 20386 switch (memFactor) { 20387 case ProcessStats.ADJ_MEM_FACTOR_CRITICAL: 20388 fgTrimLevel = ComponentCallbacks2.TRIM_MEMORY_RUNNING_CRITICAL; 20389 break; 20390 case ProcessStats.ADJ_MEM_FACTOR_LOW: 20391 fgTrimLevel = ComponentCallbacks2.TRIM_MEMORY_RUNNING_LOW; 20392 break; 20393 default: 20394 fgTrimLevel = ComponentCallbacks2.TRIM_MEMORY_RUNNING_MODERATE; 20395 break; 20396 } 20397 int factor = numTrimming/3; 20398 int minFactor = 2; 20399 if (mHomeProcess != null) minFactor++; 20400 if (mPreviousProcess != null) minFactor++; 20401 if (factor < minFactor) factor = minFactor; 20402 int curLevel = ComponentCallbacks2.TRIM_MEMORY_COMPLETE; 20403 for (int i=N-1; i>=0; i--) { 20404 ProcessRecord app = mLruProcesses.get(i); 20405 if (allChanged || app.procStateChanged) { 20406 setProcessTrackerStateLocked(app, trackerMemFactor, now); 20407 app.procStateChanged = false; 20408 } 20409 if (app.curProcState >= ActivityManager.PROCESS_STATE_HOME 20410 && !app.killedByAm) { 20411 if (app.trimMemoryLevel < curLevel && app.thread != null) { 20412 try { 20413 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG_OOM_ADJ, 20414 "Trimming memory of " + app.processName + " to " + curLevel); 20415 app.thread.scheduleTrimMemory(curLevel); 20416 } catch (RemoteException e) { 20417 } 20418 if (false) { 20419 // For now we won't do this; our memory trimming seems 20420 // to be good enough at this point that destroying 20421 // activities causes more harm than good. 20422 if (curLevel >= ComponentCallbacks2.TRIM_MEMORY_COMPLETE 20423 && app != mHomeProcess && app != mPreviousProcess) { 20424 // Need to do this on its own message because the stack may not 20425 // be in a consistent state at this point. 20426 // For these apps we will also finish their activities 20427 // to help them free memory. 20428 mStackSupervisor.scheduleDestroyAllActivities(app, "trim"); 20429 } 20430 } 20431 } 20432 app.trimMemoryLevel = curLevel; 20433 step++; 20434 if (step >= factor) { 20435 step = 0; 20436 switch (curLevel) { 20437 case ComponentCallbacks2.TRIM_MEMORY_COMPLETE: 20438 curLevel = ComponentCallbacks2.TRIM_MEMORY_MODERATE; 20439 break; 20440 case ComponentCallbacks2.TRIM_MEMORY_MODERATE: 20441 curLevel = ComponentCallbacks2.TRIM_MEMORY_BACKGROUND; 20442 break; 20443 } 20444 } 20445 } else if (app.curProcState == ActivityManager.PROCESS_STATE_HEAVY_WEIGHT) { 20446 if (app.trimMemoryLevel < ComponentCallbacks2.TRIM_MEMORY_BACKGROUND 20447 && app.thread != null) { 20448 try { 20449 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG_OOM_ADJ, 20450 "Trimming memory of heavy-weight " + app.processName 20451 + " to " + ComponentCallbacks2.TRIM_MEMORY_BACKGROUND); 20452 app.thread.scheduleTrimMemory( 20453 ComponentCallbacks2.TRIM_MEMORY_BACKGROUND); 20454 } catch (RemoteException e) { 20455 } 20456 } 20457 app.trimMemoryLevel = ComponentCallbacks2.TRIM_MEMORY_BACKGROUND; 20458 } else { 20459 if ((app.curProcState >= ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND 20460 || app.systemNoUi) && app.pendingUiClean) { 20461 // If this application is now in the background and it 20462 // had done UI, then give it the special trim level to 20463 // have it free UI resources. 20464 final int level = ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN; 20465 if (app.trimMemoryLevel < level && app.thread != null) { 20466 try { 20467 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG_OOM_ADJ, 20468 "Trimming memory of bg-ui " + app.processName 20469 + " to " + level); 20470 app.thread.scheduleTrimMemory(level); 20471 } catch (RemoteException e) { 20472 } 20473 } 20474 app.pendingUiClean = false; 20475 } 20476 if (app.trimMemoryLevel < fgTrimLevel && app.thread != null) { 20477 try { 20478 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG_OOM_ADJ, 20479 "Trimming memory of fg " + app.processName 20480 + " to " + fgTrimLevel); 20481 app.thread.scheduleTrimMemory(fgTrimLevel); 20482 } catch (RemoteException e) { 20483 } 20484 } 20485 app.trimMemoryLevel = fgTrimLevel; 20486 } 20487 } 20488 } else { 20489 if (mLowRamStartTime != 0) { 20490 mLowRamTimeSinceLastIdle += now - mLowRamStartTime; 20491 mLowRamStartTime = 0; 20492 } 20493 for (int i=N-1; i>=0; i--) { 20494 ProcessRecord app = mLruProcesses.get(i); 20495 if (allChanged || app.procStateChanged) { 20496 setProcessTrackerStateLocked(app, trackerMemFactor, now); 20497 app.procStateChanged = false; 20498 } 20499 if ((app.curProcState >= ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND 20500 || app.systemNoUi) && app.pendingUiClean) { 20501 if (app.trimMemoryLevel < ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN 20502 && app.thread != null) { 20503 try { 20504 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG_OOM_ADJ, 20505 "Trimming memory of ui hidden " + app.processName 20506 + " to " + ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN); 20507 app.thread.scheduleTrimMemory( 20508 ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN); 20509 } catch (RemoteException e) { 20510 } 20511 } 20512 app.pendingUiClean = false; 20513 } 20514 app.trimMemoryLevel = 0; 20515 } 20516 } 20517 20518 if (mAlwaysFinishActivities) { 20519 // Need to do this on its own message because the stack may not 20520 // be in a consistent state at this point. 20521 mStackSupervisor.scheduleDestroyAllActivities(null, "always-finish"); 20522 } 20523 20524 if (allChanged) { 20525 requestPssAllProcsLocked(now, false, mProcessStats.isMemFactorLowered()); 20526 } 20527 20528 // Update from any uid changes. 20529 for (int i=mActiveUids.size()-1; i>=0; i--) { 20530 final UidRecord uidRec = mActiveUids.valueAt(i); 20531 int uidChange = UidRecord.CHANGE_PROCSTATE; 20532 if (uidRec.setProcState != uidRec.curProcState) { 20533 if (DEBUG_UID_OBSERVERS) Slog.i(TAG_UID_OBSERVERS, 20534 "Changes in " + uidRec + ": proc state from " + uidRec.setProcState 20535 + " to " + uidRec.curProcState); 20536 if (ActivityManager.isProcStateBackground(uidRec.curProcState)) { 20537 if (!ActivityManager.isProcStateBackground(uidRec.setProcState)) { 20538 uidRec.lastBackgroundTime = nowElapsed; 20539 if (!mHandler.hasMessages(IDLE_UIDS_MSG)) { 20540 // Note: the background settle time is in elapsed realtime, while 20541 // the handler time base is uptime. All this means is that we may 20542 // stop background uids later than we had intended, but that only 20543 // happens because the device was sleeping so we are okay anyway. 20544 mHandler.sendEmptyMessageDelayed(IDLE_UIDS_MSG, BACKGROUND_SETTLE_TIME); 20545 } 20546 } 20547 } else { 20548 if (uidRec.idle) { 20549 uidChange = UidRecord.CHANGE_ACTIVE; 20550 uidRec.idle = false; 20551 } 20552 uidRec.lastBackgroundTime = 0; 20553 } 20554 uidRec.setProcState = uidRec.curProcState; 20555 enqueueUidChangeLocked(uidRec, -1, uidChange); 20556 noteUidProcessState(uidRec.uid, uidRec.curProcState); 20557 } 20558 } 20559 20560 if (mProcessStats.shouldWriteNowLocked(now)) { 20561 mHandler.post(new Runnable() { 20562 @Override public void run() { 20563 synchronized (ActivityManagerService.this) { 20564 mProcessStats.writeStateAsyncLocked(); 20565 } 20566 } 20567 }); 20568 } 20569 20570 if (DEBUG_OOM_ADJ) { 20571 final long duration = SystemClock.uptimeMillis() - now; 20572 if (false) { 20573 Slog.d(TAG_OOM_ADJ, "Did OOM ADJ in " + duration + "ms", 20574 new RuntimeException("here").fillInStackTrace()); 20575 } else { 20576 Slog.d(TAG_OOM_ADJ, "Did OOM ADJ in " + duration + "ms"); 20577 } 20578 } 20579 } 20580 20581 final void idleUids() { 20582 synchronized (this) { 20583 final long nowElapsed = SystemClock.elapsedRealtime(); 20584 final long maxBgTime = nowElapsed - BACKGROUND_SETTLE_TIME; 20585 long nextTime = 0; 20586 for (int i=mActiveUids.size()-1; i>=0; i--) { 20587 final UidRecord uidRec = mActiveUids.valueAt(i); 20588 final long bgTime = uidRec.lastBackgroundTime; 20589 if (bgTime > 0 && !uidRec.idle) { 20590 if (bgTime <= maxBgTime) { 20591 uidRec.idle = true; 20592 doStopUidLocked(uidRec.uid, uidRec); 20593 } else { 20594 if (nextTime == 0 || nextTime > bgTime) { 20595 nextTime = bgTime; 20596 } 20597 } 20598 } 20599 } 20600 if (nextTime > 0) { 20601 mHandler.removeMessages(IDLE_UIDS_MSG); 20602 mHandler.sendEmptyMessageDelayed(IDLE_UIDS_MSG, 20603 nextTime + BACKGROUND_SETTLE_TIME - nowElapsed); 20604 } 20605 } 20606 } 20607 20608 final void runInBackgroundDisabled(int uid) { 20609 synchronized (this) { 20610 UidRecord uidRec = mActiveUids.get(uid); 20611 if (uidRec != null) { 20612 // This uid is actually running... should it be considered background now? 20613 if (uidRec.idle) { 20614 doStopUidLocked(uidRec.uid, uidRec); 20615 } 20616 } else { 20617 // This uid isn't actually running... still send a report about it being "stopped". 20618 doStopUidLocked(uid, null); 20619 } 20620 } 20621 } 20622 20623 final void doStopUidLocked(int uid, final UidRecord uidRec) { 20624 mServices.stopInBackgroundLocked(uid); 20625 enqueueUidChangeLocked(uidRec, uid, UidRecord.CHANGE_IDLE); 20626 } 20627 20628 final void trimApplications() { 20629 synchronized (this) { 20630 int i; 20631 20632 // First remove any unused application processes whose package 20633 // has been removed. 20634 for (i=mRemovedProcesses.size()-1; i>=0; i--) { 20635 final ProcessRecord app = mRemovedProcesses.get(i); 20636 if (app.activities.size() == 0 20637 && app.curReceiver == null && app.services.size() == 0) { 20638 Slog.i( 20639 TAG, "Exiting empty application process " 20640 + app.toShortString() + " (" 20641 + (app.thread != null ? app.thread.asBinder() : null) 20642 + ")\n"); 20643 if (app.pid > 0 && app.pid != MY_PID) { 20644 app.kill("empty", false); 20645 } else { 20646 try { 20647 app.thread.scheduleExit(); 20648 } catch (Exception e) { 20649 // Ignore exceptions. 20650 } 20651 } 20652 cleanUpApplicationRecordLocked(app, false, true, -1); 20653 mRemovedProcesses.remove(i); 20654 20655 if (app.persistent) { 20656 addAppLocked(app.info, false, null /* ABI override */); 20657 } 20658 } 20659 } 20660 20661 // Now update the oom adj for all processes. 20662 updateOomAdjLocked(); 20663 } 20664 } 20665 20666 /** This method sends the specified signal to each of the persistent apps */ 20667 public void signalPersistentProcesses(int sig) throws RemoteException { 20668 if (sig != Process.SIGNAL_USR1) { 20669 throw new SecurityException("Only SIGNAL_USR1 is allowed"); 20670 } 20671 20672 synchronized (this) { 20673 if (checkCallingPermission(android.Manifest.permission.SIGNAL_PERSISTENT_PROCESSES) 20674 != PackageManager.PERMISSION_GRANTED) { 20675 throw new SecurityException("Requires permission " 20676 + android.Manifest.permission.SIGNAL_PERSISTENT_PROCESSES); 20677 } 20678 20679 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 20680 ProcessRecord r = mLruProcesses.get(i); 20681 if (r.thread != null && r.persistent) { 20682 Process.sendSignal(r.pid, sig); 20683 } 20684 } 20685 } 20686 } 20687 20688 private void stopProfilerLocked(ProcessRecord proc, int profileType) { 20689 if (proc == null || proc == mProfileProc) { 20690 proc = mProfileProc; 20691 profileType = mProfileType; 20692 clearProfilerLocked(); 20693 } 20694 if (proc == null) { 20695 return; 20696 } 20697 try { 20698 proc.thread.profilerControl(false, null, profileType); 20699 } catch (RemoteException e) { 20700 throw new IllegalStateException("Process disappeared"); 20701 } 20702 } 20703 20704 private void clearProfilerLocked() { 20705 if (mProfileFd != null) { 20706 try { 20707 mProfileFd.close(); 20708 } catch (IOException e) { 20709 } 20710 } 20711 mProfileApp = null; 20712 mProfileProc = null; 20713 mProfileFile = null; 20714 mProfileType = 0; 20715 mAutoStopProfiler = false; 20716 mSamplingInterval = 0; 20717 } 20718 20719 public boolean profileControl(String process, int userId, boolean start, 20720 ProfilerInfo profilerInfo, int profileType) throws RemoteException { 20721 20722 try { 20723 synchronized (this) { 20724 // note: hijacking SET_ACTIVITY_WATCHER, but should be changed to 20725 // its own permission. 20726 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 20727 != PackageManager.PERMISSION_GRANTED) { 20728 throw new SecurityException("Requires permission " 20729 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 20730 } 20731 20732 if (start && (profilerInfo == null || profilerInfo.profileFd == null)) { 20733 throw new IllegalArgumentException("null profile info or fd"); 20734 } 20735 20736 ProcessRecord proc = null; 20737 if (process != null) { 20738 proc = findProcessLocked(process, userId, "profileControl"); 20739 } 20740 20741 if (start && (proc == null || proc.thread == null)) { 20742 throw new IllegalArgumentException("Unknown process: " + process); 20743 } 20744 20745 if (start) { 20746 stopProfilerLocked(null, 0); 20747 setProfileApp(proc.info, proc.processName, profilerInfo); 20748 mProfileProc = proc; 20749 mProfileType = profileType; 20750 ParcelFileDescriptor fd = profilerInfo.profileFd; 20751 try { 20752 fd = fd.dup(); 20753 } catch (IOException e) { 20754 fd = null; 20755 } 20756 profilerInfo.profileFd = fd; 20757 proc.thread.profilerControl(start, profilerInfo, profileType); 20758 fd = null; 20759 mProfileFd = null; 20760 } else { 20761 stopProfilerLocked(proc, profileType); 20762 if (profilerInfo != null && profilerInfo.profileFd != null) { 20763 try { 20764 profilerInfo.profileFd.close(); 20765 } catch (IOException e) { 20766 } 20767 } 20768 } 20769 20770 return true; 20771 } 20772 } catch (RemoteException e) { 20773 throw new IllegalStateException("Process disappeared"); 20774 } finally { 20775 if (profilerInfo != null && profilerInfo.profileFd != null) { 20776 try { 20777 profilerInfo.profileFd.close(); 20778 } catch (IOException e) { 20779 } 20780 } 20781 } 20782 } 20783 20784 private ProcessRecord findProcessLocked(String process, int userId, String callName) { 20785 userId = mUserController.handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 20786 userId, true, ALLOW_FULL_ONLY, callName, null); 20787 ProcessRecord proc = null; 20788 try { 20789 int pid = Integer.parseInt(process); 20790 synchronized (mPidsSelfLocked) { 20791 proc = mPidsSelfLocked.get(pid); 20792 } 20793 } catch (NumberFormatException e) { 20794 } 20795 20796 if (proc == null) { 20797 ArrayMap<String, SparseArray<ProcessRecord>> all 20798 = mProcessNames.getMap(); 20799 SparseArray<ProcessRecord> procs = all.get(process); 20800 if (procs != null && procs.size() > 0) { 20801 proc = procs.valueAt(0); 20802 if (userId != UserHandle.USER_ALL && proc.userId != userId) { 20803 for (int i=1; i<procs.size(); i++) { 20804 ProcessRecord thisProc = procs.valueAt(i); 20805 if (thisProc.userId == userId) { 20806 proc = thisProc; 20807 break; 20808 } 20809 } 20810 } 20811 } 20812 } 20813 20814 return proc; 20815 } 20816 20817 public boolean dumpHeap(String process, int userId, boolean managed, 20818 String path, ParcelFileDescriptor fd) throws RemoteException { 20819 20820 try { 20821 synchronized (this) { 20822 // note: hijacking SET_ACTIVITY_WATCHER, but should be changed to 20823 // its own permission (same as profileControl). 20824 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 20825 != PackageManager.PERMISSION_GRANTED) { 20826 throw new SecurityException("Requires permission " 20827 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 20828 } 20829 20830 if (fd == null) { 20831 throw new IllegalArgumentException("null fd"); 20832 } 20833 20834 ProcessRecord proc = findProcessLocked(process, userId, "dumpHeap"); 20835 if (proc == null || proc.thread == null) { 20836 throw new IllegalArgumentException("Unknown process: " + process); 20837 } 20838 20839 boolean isDebuggable = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 20840 if (!isDebuggable) { 20841 if ((proc.info.flags&ApplicationInfo.FLAG_DEBUGGABLE) == 0) { 20842 throw new SecurityException("Process not debuggable: " + proc); 20843 } 20844 } 20845 20846 proc.thread.dumpHeap(managed, path, fd); 20847 fd = null; 20848 return true; 20849 } 20850 } catch (RemoteException e) { 20851 throw new IllegalStateException("Process disappeared"); 20852 } finally { 20853 if (fd != null) { 20854 try { 20855 fd.close(); 20856 } catch (IOException e) { 20857 } 20858 } 20859 } 20860 } 20861 20862 @Override 20863 public void setDumpHeapDebugLimit(String processName, int uid, long maxMemSize, 20864 String reportPackage) { 20865 if (processName != null) { 20866 enforceCallingPermission(android.Manifest.permission.SET_DEBUG_APP, 20867 "setDumpHeapDebugLimit()"); 20868 } else { 20869 synchronized (mPidsSelfLocked) { 20870 ProcessRecord proc = mPidsSelfLocked.get(Binder.getCallingPid()); 20871 if (proc == null) { 20872 throw new SecurityException("No process found for calling pid " 20873 + Binder.getCallingPid()); 20874 } 20875 if (!Build.IS_DEBUGGABLE 20876 && (proc.info.flags&ApplicationInfo.FLAG_DEBUGGABLE) == 0) { 20877 throw new SecurityException("Not running a debuggable build"); 20878 } 20879 processName = proc.processName; 20880 uid = proc.uid; 20881 if (reportPackage != null && !proc.pkgList.containsKey(reportPackage)) { 20882 throw new SecurityException("Package " + reportPackage + " is not running in " 20883 + proc); 20884 } 20885 } 20886 } 20887 synchronized (this) { 20888 if (maxMemSize > 0) { 20889 mMemWatchProcesses.put(processName, uid, new Pair(maxMemSize, reportPackage)); 20890 } else { 20891 if (uid != 0) { 20892 mMemWatchProcesses.remove(processName, uid); 20893 } else { 20894 mMemWatchProcesses.getMap().remove(processName); 20895 } 20896 } 20897 } 20898 } 20899 20900 @Override 20901 public void dumpHeapFinished(String path) { 20902 synchronized (this) { 20903 if (Binder.getCallingPid() != mMemWatchDumpPid) { 20904 Slog.w(TAG, "dumpHeapFinished: Calling pid " + Binder.getCallingPid() 20905 + " does not match last pid " + mMemWatchDumpPid); 20906 return; 20907 } 20908 if (mMemWatchDumpFile == null || !mMemWatchDumpFile.equals(path)) { 20909 Slog.w(TAG, "dumpHeapFinished: Calling path " + path 20910 + " does not match last path " + mMemWatchDumpFile); 20911 return; 20912 } 20913 if (DEBUG_PSS) Slog.d(TAG_PSS, "Dump heap finished for " + path); 20914 mHandler.sendEmptyMessage(POST_DUMP_HEAP_NOTIFICATION_MSG); 20915 } 20916 } 20917 20918 /** In this method we try to acquire our lock to make sure that we have not deadlocked */ 20919 public void monitor() { 20920 synchronized (this) { } 20921 } 20922 20923 void onCoreSettingsChange(Bundle settings) { 20924 for (int i = mLruProcesses.size() - 1; i >= 0; i--) { 20925 ProcessRecord processRecord = mLruProcesses.get(i); 20926 try { 20927 if (processRecord.thread != null) { 20928 processRecord.thread.setCoreSettings(settings); 20929 } 20930 } catch (RemoteException re) { 20931 /* ignore */ 20932 } 20933 } 20934 } 20935 20936 // Multi-user methods 20937 20938 /** 20939 * Start user, if its not already running, but don't bring it to foreground. 20940 */ 20941 @Override 20942 public boolean startUserInBackground(final int userId) { 20943 return mUserController.startUser(userId, /* foreground */ false); 20944 } 20945 20946 @Override 20947 public boolean unlockUser(int userId, byte[] token, byte[] secret, IProgressListener listener) { 20948 return mUserController.unlockUser(userId, token, secret, listener); 20949 } 20950 20951 @Override 20952 public boolean switchUser(final int targetUserId) { 20953 enforceShellRestriction(UserManager.DISALLOW_DEBUGGING_FEATURES, targetUserId); 20954 UserInfo currentUserInfo; 20955 UserInfo targetUserInfo; 20956 synchronized (this) { 20957 int currentUserId = mUserController.getCurrentUserIdLocked(); 20958 currentUserInfo = mUserController.getUserInfo(currentUserId); 20959 targetUserInfo = mUserController.getUserInfo(targetUserId); 20960 if (targetUserInfo == null) { 20961 Slog.w(TAG, "No user info for user #" + targetUserId); 20962 return false; 20963 } 20964 if (!targetUserInfo.supportsSwitchTo()) { 20965 Slog.w(TAG, "Cannot switch to User #" + targetUserId + ": not supported"); 20966 return false; 20967 } 20968 if (targetUserInfo.isManagedProfile()) { 20969 Slog.w(TAG, "Cannot switch to User #" + targetUserId + ": not a full user"); 20970 return false; 20971 } 20972 mUserController.setTargetUserIdLocked(targetUserId); 20973 } 20974 Pair<UserInfo, UserInfo> userNames = new Pair<>(currentUserInfo, targetUserInfo); 20975 mUiHandler.removeMessages(START_USER_SWITCH_UI_MSG); 20976 mUiHandler.sendMessage(mUiHandler.obtainMessage(START_USER_SWITCH_UI_MSG, userNames)); 20977 return true; 20978 } 20979 20980 void scheduleStartProfilesLocked() { 20981 if (!mHandler.hasMessages(START_PROFILES_MSG)) { 20982 mHandler.sendMessageDelayed(mHandler.obtainMessage(START_PROFILES_MSG), 20983 DateUtils.SECOND_IN_MILLIS); 20984 } 20985 } 20986 20987 @Override 20988 public int stopUser(final int userId, boolean force, final IStopUserCallback callback) { 20989 return mUserController.stopUser(userId, force, callback); 20990 } 20991 20992 @Override 20993 public UserInfo getCurrentUser() { 20994 return mUserController.getCurrentUser(); 20995 } 20996 20997 @Override 20998 public boolean isUserRunning(int userId, int flags) { 20999 if (userId != UserHandle.getCallingUserId() && checkCallingPermission( 21000 INTERACT_ACROSS_USERS) != PackageManager.PERMISSION_GRANTED) { 21001 String msg = "Permission Denial: isUserRunning() from pid=" 21002 + Binder.getCallingPid() 21003 + ", uid=" + Binder.getCallingUid() 21004 + " requires " + INTERACT_ACROSS_USERS; 21005 Slog.w(TAG, msg); 21006 throw new SecurityException(msg); 21007 } 21008 synchronized (this) { 21009 return mUserController.isUserRunningLocked(userId, flags); 21010 } 21011 } 21012 21013 @Override 21014 public int[] getRunningUserIds() { 21015 if (checkCallingPermission(INTERACT_ACROSS_USERS) 21016 != PackageManager.PERMISSION_GRANTED) { 21017 String msg = "Permission Denial: isUserRunning() from pid=" 21018 + Binder.getCallingPid() 21019 + ", uid=" + Binder.getCallingUid() 21020 + " requires " + INTERACT_ACROSS_USERS; 21021 Slog.w(TAG, msg); 21022 throw new SecurityException(msg); 21023 } 21024 synchronized (this) { 21025 return mUserController.getStartedUserArrayLocked(); 21026 } 21027 } 21028 21029 @Override 21030 public void registerUserSwitchObserver(IUserSwitchObserver observer) { 21031 mUserController.registerUserSwitchObserver(observer); 21032 } 21033 21034 @Override 21035 public void unregisterUserSwitchObserver(IUserSwitchObserver observer) { 21036 mUserController.unregisterUserSwitchObserver(observer); 21037 } 21038 21039 ApplicationInfo getAppInfoForUser(ApplicationInfo info, int userId) { 21040 if (info == null) return null; 21041 ApplicationInfo newInfo = new ApplicationInfo(info); 21042 newInfo.initForUser(userId); 21043 return newInfo; 21044 } 21045 21046 public boolean isUserStopped(int userId) { 21047 synchronized (this) { 21048 return mUserController.getStartedUserStateLocked(userId) == null; 21049 } 21050 } 21051 21052 ActivityInfo getActivityInfoForUser(ActivityInfo aInfo, int userId) { 21053 if (aInfo == null 21054 || (userId < 1 && aInfo.applicationInfo.uid < UserHandle.PER_USER_RANGE)) { 21055 return aInfo; 21056 } 21057 21058 ActivityInfo info = new ActivityInfo(aInfo); 21059 info.applicationInfo = getAppInfoForUser(info.applicationInfo, userId); 21060 return info; 21061 } 21062 21063 private boolean processSanityChecksLocked(ProcessRecord process) { 21064 if (process == null || process.thread == null) { 21065 return false; 21066 } 21067 21068 boolean isDebuggable = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 21069 if (!isDebuggable) { 21070 if ((process.info.flags&ApplicationInfo.FLAG_DEBUGGABLE) == 0) { 21071 return false; 21072 } 21073 } 21074 21075 return true; 21076 } 21077 21078 public boolean startBinderTracking() throws RemoteException { 21079 synchronized (this) { 21080 mBinderTransactionTrackingEnabled = true; 21081 // TODO: hijacking SET_ACTIVITY_WATCHER, but should be changed to its own 21082 // permission (same as profileControl). 21083 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 21084 != PackageManager.PERMISSION_GRANTED) { 21085 throw new SecurityException("Requires permission " 21086 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 21087 } 21088 21089 for (int i = 0; i < mLruProcesses.size(); i++) { 21090 ProcessRecord process = mLruProcesses.get(i); 21091 if (!processSanityChecksLocked(process)) { 21092 continue; 21093 } 21094 try { 21095 process.thread.startBinderTracking(); 21096 } catch (RemoteException e) { 21097 Log.v(TAG, "Process disappared"); 21098 } 21099 } 21100 return true; 21101 } 21102 } 21103 21104 public boolean stopBinderTrackingAndDump(ParcelFileDescriptor fd) throws RemoteException { 21105 try { 21106 synchronized (this) { 21107 mBinderTransactionTrackingEnabled = false; 21108 // TODO: hijacking SET_ACTIVITY_WATCHER, but should be changed to its own 21109 // permission (same as profileControl). 21110 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 21111 != PackageManager.PERMISSION_GRANTED) { 21112 throw new SecurityException("Requires permission " 21113 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 21114 } 21115 21116 if (fd == null) { 21117 throw new IllegalArgumentException("null fd"); 21118 } 21119 21120 PrintWriter pw = new FastPrintWriter(new FileOutputStream(fd.getFileDescriptor())); 21121 pw.println("Binder transaction traces for all processes.\n"); 21122 for (ProcessRecord process : mLruProcesses) { 21123 if (!processSanityChecksLocked(process)) { 21124 continue; 21125 } 21126 21127 pw.println("Traces for process: " + process.processName); 21128 pw.flush(); 21129 try { 21130 TransferPipe tp = new TransferPipe(); 21131 try { 21132 process.thread.stopBinderTrackingAndDump( 21133 tp.getWriteFd().getFileDescriptor()); 21134 tp.go(fd.getFileDescriptor()); 21135 } finally { 21136 tp.kill(); 21137 } 21138 } catch (IOException e) { 21139 pw.println("Failure while dumping IPC traces from " + process + 21140 ". Exception: " + e); 21141 pw.flush(); 21142 } catch (RemoteException e) { 21143 pw.println("Got a RemoteException while dumping IPC traces from " + 21144 process + ". Exception: " + e); 21145 pw.flush(); 21146 } 21147 } 21148 fd = null; 21149 return true; 21150 } 21151 } finally { 21152 if (fd != null) { 21153 try { 21154 fd.close(); 21155 } catch (IOException e) { 21156 } 21157 } 21158 } 21159 } 21160 21161 private final class LocalService extends ActivityManagerInternal { 21162 @Override 21163 public void onWakefulnessChanged(int wakefulness) { 21164 ActivityManagerService.this.onWakefulnessChanged(wakefulness); 21165 } 21166 21167 @Override 21168 public int startIsolatedProcess(String entryPoint, String[] entryPointArgs, 21169 String processName, String abiOverride, int uid, Runnable crashHandler) { 21170 return ActivityManagerService.this.startIsolatedProcess(entryPoint, entryPointArgs, 21171 processName, abiOverride, uid, crashHandler); 21172 } 21173 21174 @Override 21175 public SleepToken acquireSleepToken(String tag) { 21176 Preconditions.checkNotNull(tag); 21177 21178 synchronized (ActivityManagerService.this) { 21179 SleepTokenImpl token = new SleepTokenImpl(tag); 21180 mSleepTokens.add(token); 21181 updateSleepIfNeededLocked(); 21182 applyVrModeIfNeededLocked(mFocusedActivity, false); 21183 return token; 21184 } 21185 } 21186 21187 @Override 21188 public ComponentName getHomeActivityForUser(int userId) { 21189 synchronized (ActivityManagerService.this) { 21190 ActivityRecord homeActivity = mStackSupervisor.getHomeActivityForUser(userId); 21191 return homeActivity == null ? null : homeActivity.realActivity; 21192 } 21193 } 21194 21195 @Override 21196 public void onUserRemoved(int userId) { 21197 synchronized (ActivityManagerService.this) { 21198 ActivityManagerService.this.onUserStoppedLocked(userId); 21199 } 21200 } 21201 21202 @Override 21203 public void onLocalVoiceInteractionStarted(IBinder activity, 21204 IVoiceInteractionSession voiceSession, IVoiceInteractor voiceInteractor) { 21205 synchronized (ActivityManagerService.this) { 21206 ActivityManagerService.this.onLocalVoiceInteractionStartedLocked(activity, 21207 voiceSession, voiceInteractor); 21208 } 21209 } 21210 21211 @Override 21212 public void notifyStartingWindowDrawn() { 21213 synchronized (ActivityManagerService.this) { 21214 mStackSupervisor.mActivityMetricsLogger.notifyStartingWindowDrawn(); 21215 } 21216 } 21217 21218 @Override 21219 public void notifyAppTransitionStarting(int reason) { 21220 synchronized (ActivityManagerService.this) { 21221 mStackSupervisor.mActivityMetricsLogger.notifyTransitionStarting(reason); 21222 } 21223 } 21224 21225 @Override 21226 public void notifyAppTransitionFinished() { 21227 synchronized (ActivityManagerService.this) { 21228 mStackSupervisor.notifyAppTransitionDone(); 21229 } 21230 } 21231 21232 @Override 21233 public void notifyAppTransitionCancelled() { 21234 synchronized (ActivityManagerService.this) { 21235 mStackSupervisor.notifyAppTransitionDone(); 21236 } 21237 } 21238 21239 @Override 21240 public List<IBinder> getTopVisibleActivities() { 21241 synchronized (ActivityManagerService.this) { 21242 return mStackSupervisor.getTopVisibleActivities(); 21243 } 21244 } 21245 21246 @Override 21247 public void notifyDockedStackMinimizedChanged(boolean minimized) { 21248 synchronized (ActivityManagerService.this) { 21249 mStackSupervisor.setDockedStackMinimized(minimized); 21250 } 21251 } 21252 21253 @Override 21254 public void killForegroundAppsForUser(int userHandle) { 21255 synchronized (ActivityManagerService.this) { 21256 final ArrayList<ProcessRecord> procs = new ArrayList<>(); 21257 final int NP = mProcessNames.getMap().size(); 21258 for (int ip = 0; ip < NP; ip++) { 21259 final SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 21260 final int NA = apps.size(); 21261 for (int ia = 0; ia < NA; ia++) { 21262 final ProcessRecord app = apps.valueAt(ia); 21263 if (app.persistent) { 21264 // We don't kill persistent processes. 21265 continue; 21266 } 21267 if (app.removed) { 21268 procs.add(app); 21269 } else if (app.userId == userHandle && app.foregroundActivities) { 21270 app.removed = true; 21271 procs.add(app); 21272 } 21273 } 21274 } 21275 21276 final int N = procs.size(); 21277 for (int i = 0; i < N; i++) { 21278 removeProcessLocked(procs.get(i), false, true, "kill all fg"); 21279 } 21280 } 21281 } 21282 } 21283 21284 private final class SleepTokenImpl extends SleepToken { 21285 private final String mTag; 21286 private final long mAcquireTime; 21287 21288 public SleepTokenImpl(String tag) { 21289 mTag = tag; 21290 mAcquireTime = SystemClock.uptimeMillis(); 21291 } 21292 21293 @Override 21294 public void release() { 21295 synchronized (ActivityManagerService.this) { 21296 if (mSleepTokens.remove(this)) { 21297 updateSleepIfNeededLocked(); 21298 } 21299 } 21300 } 21301 21302 @Override 21303 public String toString() { 21304 return "{\"" + mTag + "\", acquire at " + TimeUtils.formatUptime(mAcquireTime) + "}"; 21305 } 21306 } 21307 21308 /** 21309 * An implementation of IAppTask, that allows an app to manage its own tasks via 21310 * {@link android.app.ActivityManager.AppTask}. We keep track of the callingUid to ensure that 21311 * only the process that calls getAppTasks() can call the AppTask methods. 21312 */ 21313 class AppTaskImpl extends IAppTask.Stub { 21314 private int mTaskId; 21315 private int mCallingUid; 21316 21317 public AppTaskImpl(int taskId, int callingUid) { 21318 mTaskId = taskId; 21319 mCallingUid = callingUid; 21320 } 21321 21322 private void checkCaller() { 21323 if (mCallingUid != Binder.getCallingUid()) { 21324 throw new SecurityException("Caller " + mCallingUid 21325 + " does not match caller of getAppTasks(): " + Binder.getCallingUid()); 21326 } 21327 } 21328 21329 @Override 21330 public void finishAndRemoveTask() { 21331 checkCaller(); 21332 21333 synchronized (ActivityManagerService.this) { 21334 long origId = Binder.clearCallingIdentity(); 21335 try { 21336 // We remove the task from recents to preserve backwards 21337 if (!removeTaskByIdLocked(mTaskId, false, REMOVE_FROM_RECENTS)) { 21338 throw new IllegalArgumentException("Unable to find task ID " + mTaskId); 21339 } 21340 } finally { 21341 Binder.restoreCallingIdentity(origId); 21342 } 21343 } 21344 } 21345 21346 @Override 21347 public ActivityManager.RecentTaskInfo getTaskInfo() { 21348 checkCaller(); 21349 21350 synchronized (ActivityManagerService.this) { 21351 long origId = Binder.clearCallingIdentity(); 21352 try { 21353 TaskRecord tr = mStackSupervisor.anyTaskForIdLocked(mTaskId); 21354 if (tr == null) { 21355 throw new IllegalArgumentException("Unable to find task ID " + mTaskId); 21356 } 21357 return createRecentTaskInfoFromTaskRecord(tr); 21358 } finally { 21359 Binder.restoreCallingIdentity(origId); 21360 } 21361 } 21362 } 21363 21364 @Override 21365 public void moveToFront() { 21366 checkCaller(); 21367 // Will bring task to front if it already has a root activity. 21368 final long origId = Binder.clearCallingIdentity(); 21369 try { 21370 synchronized (this) { 21371 mStackSupervisor.startActivityFromRecentsInner(mTaskId, null); 21372 } 21373 } finally { 21374 Binder.restoreCallingIdentity(origId); 21375 } 21376 } 21377 21378 @Override 21379 public int startActivity(IBinder whoThread, String callingPackage, 21380 Intent intent, String resolvedType, Bundle bOptions) { 21381 checkCaller(); 21382 21383 int callingUser = UserHandle.getCallingUserId(); 21384 TaskRecord tr; 21385 IApplicationThread appThread; 21386 synchronized (ActivityManagerService.this) { 21387 tr = mStackSupervisor.anyTaskForIdLocked(mTaskId); 21388 if (tr == null) { 21389 throw new IllegalArgumentException("Unable to find task ID " + mTaskId); 21390 } 21391 appThread = ApplicationThreadNative.asInterface(whoThread); 21392 if (appThread == null) { 21393 throw new IllegalArgumentException("Bad app thread " + appThread); 21394 } 21395 } 21396 return mActivityStarter.startActivityMayWait(appThread, -1, callingPackage, intent, 21397 resolvedType, null, null, null, null, 0, 0, null, null, 21398 null, bOptions, false, callingUser, null, tr); 21399 } 21400 21401 @Override 21402 public void setExcludeFromRecents(boolean exclude) { 21403 checkCaller(); 21404 21405 synchronized (ActivityManagerService.this) { 21406 long origId = Binder.clearCallingIdentity(); 21407 try { 21408 TaskRecord tr = mStackSupervisor.anyTaskForIdLocked(mTaskId); 21409 if (tr == null) { 21410 throw new IllegalArgumentException("Unable to find task ID " + mTaskId); 21411 } 21412 Intent intent = tr.getBaseIntent(); 21413 if (exclude) { 21414 intent.addFlags(Intent.FLAG_ACTIVITY_EXCLUDE_FROM_RECENTS); 21415 } else { 21416 intent.setFlags(intent.getFlags() 21417 & ~Intent.FLAG_ACTIVITY_EXCLUDE_FROM_RECENTS); 21418 } 21419 } finally { 21420 Binder.restoreCallingIdentity(origId); 21421 } 21422 } 21423 } 21424 } 21425 21426 /** 21427 * Kill processes for the user with id userId and that depend on the package named packageName 21428 */ 21429 @Override 21430 public void killPackageDependents(String packageName, int userId) { 21431 enforceCallingPermission(android.Manifest.permission.KILL_UID, "killPackageDependents()"); 21432 if (packageName == null) { 21433 throw new NullPointerException( 21434 "Cannot kill the dependents of a package without its name."); 21435 } 21436 21437 long callingId = Binder.clearCallingIdentity(); 21438 IPackageManager pm = AppGlobals.getPackageManager(); 21439 int pkgUid = -1; 21440 try { 21441 pkgUid = pm.getPackageUid(packageName, MATCH_DEBUG_TRIAGED_MISSING, userId); 21442 } catch (RemoteException e) { 21443 } 21444 if (userId != UserHandle.USER_ALL && pkgUid == -1) { 21445 throw new IllegalArgumentException( 21446 "Cannot kill dependents of non-existing package " + packageName); 21447 } 21448 try { 21449 synchronized(this) { 21450 killPackageProcessesLocked(packageName, UserHandle.getAppId(pkgUid), userId, 21451 ProcessList.FOREGROUND_APP_ADJ, false, true, true, false, 21452 "dep: " + packageName); 21453 } 21454 } finally { 21455 Binder.restoreCallingIdentity(callingId); 21456 } 21457 } 21458} 21459