ActivityManagerService.java revision e69c93181f1f313dcedd07f677af1cea953fdf16
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 android.annotation.Nullable; 20import android.app.ApplicationThreadConstants; 21import android.app.ContentProviderHolder; 22import android.app.IActivityManager; 23import android.app.WaitResult; 24import android.os.IDeviceIdentifiersPolicyService; 25import android.util.Size; 26import android.util.TypedValue; 27import android.view.DisplayInfo; 28import com.android.internal.telephony.TelephonyIntents; 29import com.google.android.collect.Lists; 30import com.google.android.collect.Maps; 31import com.android.internal.R; 32import com.android.internal.annotations.GuardedBy; 33import com.android.internal.app.AssistUtils; 34import com.android.internal.app.DumpHeapActivity; 35import com.android.internal.app.IAppOpsCallback; 36import com.android.internal.app.IAppOpsService; 37import com.android.internal.app.IVoiceInteractor; 38import com.android.internal.app.ProcessMap; 39import com.android.internal.app.SystemUserHomeActivity; 40import com.android.internal.app.procstats.ProcessStats; 41import com.android.internal.os.BackgroundThread; 42import com.android.internal.os.BatteryStatsImpl; 43import com.android.internal.os.IResultReceiver; 44import com.android.internal.os.ProcessCpuTracker; 45import com.android.internal.os.TransferPipe; 46import com.android.internal.os.Zygote; 47import com.android.internal.os.InstallerConnection.InstallerException; 48import com.android.internal.util.ArrayUtils; 49import com.android.internal.util.FastPrintWriter; 50import com.android.internal.util.FastXmlSerializer; 51import com.android.internal.util.MemInfoReader; 52import com.android.internal.util.Preconditions; 53import com.android.server.AppOpsService; 54import com.android.server.AttributeCache; 55import com.android.server.DeviceIdleController; 56import com.android.server.IntentResolver; 57import com.android.server.LocalServices; 58import com.android.server.LockGuard; 59import com.android.server.ServiceThread; 60import com.android.server.SystemService; 61import com.android.server.SystemServiceManager; 62import com.android.server.Watchdog; 63import com.android.server.am.ActivityStack.ActivityState; 64import com.android.server.firewall.IntentFirewall; 65import com.android.server.pm.Installer; 66import com.android.server.statusbar.StatusBarManagerInternal; 67import com.android.server.vr.VrManagerInternal; 68import com.android.server.wm.WindowManagerService; 69 70import org.xmlpull.v1.XmlPullParser; 71import org.xmlpull.v1.XmlPullParserException; 72import org.xmlpull.v1.XmlSerializer; 73 74import android.Manifest; 75import android.Manifest.permission; 76import android.annotation.NonNull; 77import android.annotation.UserIdInt; 78import android.app.Activity; 79import android.app.ActivityManager; 80import android.app.ActivityManager.RunningTaskInfo; 81import android.app.ActivityManager.StackId; 82import android.app.ActivityManager.StackInfo; 83import android.app.ActivityManager.TaskDescription; 84import android.app.ActivityManager.TaskThumbnailInfo; 85import android.app.ActivityManagerInternal; 86import android.app.ActivityManagerInternal.SleepToken; 87import android.app.ActivityOptions; 88import android.app.ActivityThread; 89import android.app.AlertDialog; 90import android.app.AppGlobals; 91import android.app.AppOpsManager; 92import android.app.ApplicationErrorReport; 93import android.app.BroadcastOptions; 94import android.app.Dialog; 95import android.app.IActivityContainer; 96import android.app.IActivityContainerCallback; 97import android.app.IActivityController; 98import android.app.IAppTask; 99import android.app.IApplicationThread; 100import android.app.IInstrumentationWatcher; 101import android.app.INotificationManager; 102import android.app.IProcessObserver; 103import android.app.IServiceConnection; 104import android.app.IStopUserCallback; 105import android.app.ITaskStackListener; 106import android.app.IUiAutomationConnection; 107import android.app.IUidObserver; 108import android.app.IUserSwitchObserver; 109import android.app.Instrumentation; 110import android.app.Notification; 111import android.app.NotificationManager; 112import android.app.PendingIntent; 113import android.app.ProfilerInfo; 114import android.app.admin.DevicePolicyManager; 115import android.app.assist.AssistContent; 116import android.app.assist.AssistStructure; 117import android.app.backup.IBackupManager; 118import android.app.usage.UsageEvents; 119import android.app.usage.UsageStatsManagerInternal; 120import android.appwidget.AppWidgetManager; 121import android.content.ActivityNotFoundException; 122import android.content.BroadcastReceiver; 123import android.content.ClipData; 124import android.content.ComponentCallbacks2; 125import android.content.ComponentName; 126import android.content.ContentProvider; 127import android.content.ContentResolver; 128import android.content.Context; 129import android.content.DialogInterface; 130import android.content.IContentProvider; 131import android.content.IIntentReceiver; 132import android.content.IIntentSender; 133import android.content.Intent; 134import android.content.IntentFilter; 135import android.content.IntentSender; 136import android.content.pm.ActivityInfo; 137import android.content.pm.ApplicationInfo; 138import android.content.pm.ConfigurationInfo; 139import android.content.pm.IPackageDataObserver; 140import android.content.pm.IPackageManager; 141import android.content.pm.InstrumentationInfo; 142import android.content.pm.PackageInfo; 143import android.content.pm.PackageManager; 144import android.content.pm.PackageManager.NameNotFoundException; 145import android.content.pm.PackageManagerInternal; 146import android.content.pm.ParceledListSlice; 147import android.content.pm.PathPermission; 148import android.content.pm.PermissionInfo; 149import android.content.pm.ProviderInfo; 150import android.content.pm.ResolveInfo; 151import android.content.pm.ServiceInfo; 152import android.content.pm.UserInfo; 153import android.content.res.CompatibilityInfo; 154import android.content.res.Configuration; 155import android.content.res.Resources; 156import android.database.ContentObserver; 157import android.graphics.Bitmap; 158import android.graphics.Point; 159import android.graphics.Rect; 160import android.location.LocationManager; 161import android.net.Proxy; 162import android.net.ProxyInfo; 163import android.net.Uri; 164import android.os.BatteryStats; 165import android.os.Binder; 166import android.os.Build; 167import android.os.Bundle; 168import android.os.Debug; 169import android.os.DropBoxManager; 170import android.os.Environment; 171import android.os.FactoryTest; 172import android.os.FileObserver; 173import android.os.FileUtils; 174import android.os.Handler; 175import android.os.IBinder; 176import android.os.IPermissionController; 177import android.os.IProcessInfoService; 178import android.os.IProgressListener; 179import android.os.LocaleList; 180import android.os.Looper; 181import android.os.Message; 182import android.os.Parcel; 183import android.os.ParcelFileDescriptor; 184import android.os.PersistableBundle; 185import android.os.PowerManager; 186import android.os.PowerManagerInternal; 187import android.os.Process; 188import android.os.RemoteCallbackList; 189import android.os.RemoteException; 190import android.os.ResultReceiver; 191import android.os.ServiceManager; 192import android.os.ShellCallback; 193import android.os.StrictMode; 194import android.os.SystemClock; 195import android.os.SystemProperties; 196import android.os.Trace; 197import android.os.TransactionTooLargeException; 198import android.os.UpdateLock; 199import android.os.UserHandle; 200import android.os.UserManager; 201import android.os.WorkSource; 202import android.os.storage.IMountService; 203import android.os.storage.MountServiceInternal; 204import android.os.storage.StorageManager; 205import android.provider.Settings; 206import android.service.voice.IVoiceInteractionSession; 207import android.service.voice.VoiceInteractionManagerInternal; 208import android.service.voice.VoiceInteractionSession; 209import android.telecom.TelecomManager; 210import android.text.format.DateUtils; 211import android.text.format.Time; 212import android.text.style.SuggestionSpan; 213import android.util.ArrayMap; 214import android.util.ArraySet; 215import android.util.AtomicFile; 216import android.util.DebugUtils; 217import android.util.DisplayMetrics; 218import android.util.EventLog; 219import android.util.Log; 220import android.util.Pair; 221import android.util.PrintWriterPrinter; 222import android.util.Slog; 223import android.util.SparseArray; 224import android.util.TimeUtils; 225import android.util.Xml; 226import android.view.Gravity; 227import android.view.LayoutInflater; 228import android.view.View; 229import android.view.WindowManager; 230 231import java.io.File; 232import java.io.FileDescriptor; 233import java.io.FileInputStream; 234import java.io.FileNotFoundException; 235import java.io.FileOutputStream; 236import java.io.IOException; 237import java.io.InputStreamReader; 238import java.io.PrintWriter; 239import java.io.StringWriter; 240import java.lang.ref.WeakReference; 241import java.nio.charset.StandardCharsets; 242import java.util.ArrayList; 243import java.util.Arrays; 244import java.util.Collections; 245import java.util.Comparator; 246import java.util.HashMap; 247import java.util.HashSet; 248import java.util.Iterator; 249import java.util.List; 250import java.util.Locale; 251import java.util.Map; 252import java.util.Objects; 253import java.util.Set; 254import java.util.concurrent.atomic.AtomicBoolean; 255import java.util.concurrent.atomic.AtomicLong; 256 257import dalvik.system.VMRuntime; 258 259import libcore.io.IoUtils; 260import libcore.util.EmptyArray; 261 262import static android.Manifest.permission.CHANGE_CONFIGURATION; 263import static android.Manifest.permission.INTERACT_ACROSS_USERS; 264import static android.Manifest.permission.INTERACT_ACROSS_USERS_FULL; 265import static android.Manifest.permission.MANAGE_ACTIVITY_STACKS; 266import static android.Manifest.permission.START_TASKS_FROM_RECENTS; 267import static android.app.ActivityManager.DOCKED_STACK_CREATE_MODE_TOP_OR_LEFT; 268import static android.app.ActivityManager.RESIZE_MODE_PRESERVE_WINDOW; 269import static android.app.ActivityManager.StackId.DOCKED_STACK_ID; 270import static android.app.ActivityManager.StackId.FREEFORM_WORKSPACE_STACK_ID; 271import static android.app.ActivityManager.StackId.FULLSCREEN_WORKSPACE_STACK_ID; 272import static android.app.ActivityManager.StackId.HOME_STACK_ID; 273import static android.app.ActivityManager.StackId.INVALID_STACK_ID; 274import static android.app.ActivityManager.StackId.PINNED_STACK_ID; 275import static android.content.pm.PackageManager.FEATURE_FREEFORM_WINDOW_MANAGEMENT; 276import static android.content.pm.PackageManager.FEATURE_LEANBACK_ONLY; 277import static android.content.pm.PackageManager.FEATURE_PICTURE_IN_PICTURE; 278import static android.content.pm.PackageManager.GET_PROVIDERS; 279import static android.content.pm.PackageManager.MATCH_DEBUG_TRIAGED_MISSING; 280import static android.content.pm.PackageManager.MATCH_DIRECT_BOOT_AWARE; 281import static android.content.pm.PackageManager.MATCH_DIRECT_BOOT_UNAWARE; 282import static android.content.pm.PackageManager.MATCH_SYSTEM_ONLY; 283import static android.content.pm.PackageManager.MATCH_UNINSTALLED_PACKAGES; 284import static android.content.pm.PackageManager.PERMISSION_GRANTED; 285import static android.content.res.Configuration.UI_MODE_TYPE_TELEVISION; 286import static android.os.Build.VERSION_CODES.N; 287import static android.os.Process.PROC_CHAR; 288import static android.os.Process.PROC_OUT_LONG; 289import static android.os.Process.PROC_PARENS; 290import static android.os.Process.PROC_SPACE_TERM; 291import static android.provider.Settings.Global.ALWAYS_FINISH_ACTIVITIES; 292import static android.provider.Settings.Global.DEBUG_APP; 293import static android.provider.Settings.Global.DEVELOPMENT_ENABLE_FREEFORM_WINDOWS_SUPPORT; 294import static android.provider.Settings.Global.DEVELOPMENT_FORCE_RESIZABLE_ACTIVITIES; 295import static android.provider.Settings.Global.DEVELOPMENT_FORCE_RTL; 296import static android.provider.Settings.Global.LENIENT_BACKGROUND_CHECK; 297import static android.provider.Settings.Global.WAIT_FOR_DEBUGGER; 298import static android.provider.Settings.System.FONT_SCALE; 299import static android.util.TypedValue.COMPLEX_UNIT_DIP; 300import static android.view.Display.DEFAULT_DISPLAY; 301 302import static com.android.internal.util.XmlUtils.readBooleanAttribute; 303import static com.android.internal.util.XmlUtils.readIntAttribute; 304import static com.android.internal.util.XmlUtils.readLongAttribute; 305import static com.android.internal.util.XmlUtils.writeBooleanAttribute; 306import static com.android.internal.util.XmlUtils.writeIntAttribute; 307import static com.android.internal.util.XmlUtils.writeLongAttribute; 308import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_ALL; 309import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_ANR; 310import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_BACKUP; 311import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_BROADCAST; 312import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_BROADCAST_BACKGROUND; 313import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_BROADCAST_LIGHT; 314import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_CLEANUP; 315import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_CONFIGURATION; 316import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_FOCUS; 317import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_IMMERSIVE; 318import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_LOCKTASK; 319import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_LRU; 320import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_MU; 321import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_OOM_ADJ; 322import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_PERMISSIONS_REVIEW; 323import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_POWER; 324import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_POWER_QUICK; 325import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_PROCESSES; 326import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_PROCESS_OBSERVERS; 327import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_PROVIDER; 328import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_PSS; 329import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_RECENTS; 330import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_SERVICE; 331import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_STACK; 332import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_SWITCH; 333import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_TASKS; 334import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_UID_OBSERVERS; 335import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_URI_PERMISSION; 336import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_USAGE_STATS; 337import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_VISIBILITY; 338import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_VISIBLE_BEHIND; 339import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_WHITELISTS; 340import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_BACKUP; 341import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_BROADCAST; 342import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_CLEANUP; 343import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_CONFIGURATION; 344import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_FOCUS; 345import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_IMMERSIVE; 346import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_LOCKSCREEN; 347import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_LOCKTASK; 348import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_LRU; 349import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_MU; 350import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_OOM_ADJ; 351import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_POWER; 352import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_PROCESSES; 353import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_PROCESS_OBSERVERS; 354import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_PROVIDER; 355import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_PSS; 356import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_RECENTS; 357import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_SERVICE; 358import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_STACK; 359import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_SWITCH; 360import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_UID_OBSERVERS; 361import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_URI_PERMISSION; 362import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_VISIBILITY; 363import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_VISIBLE_BEHIND; 364import static com.android.server.am.ActivityManagerDebugConfig.TAG_AM; 365import static com.android.server.am.ActivityManagerDebugConfig.TAG_WITH_CLASS_NAME; 366import static com.android.server.am.ActivityRecord.RECENTS_ACTIVITY_TYPE; 367import static com.android.server.am.ActivityStackSupervisor.ActivityContainer.FORCE_NEW_TASK_FLAGS; 368import static com.android.server.am.ActivityStackSupervisor.DEFER_RESUME; 369import static com.android.server.am.ActivityStackSupervisor.FORCE_FOCUS; 370import static com.android.server.am.ActivityStackSupervisor.ON_TOP; 371import static com.android.server.am.ActivityStackSupervisor.PRESERVE_WINDOWS; 372import static com.android.server.am.ActivityStackSupervisor.RESTORE_FROM_RECENTS; 373import static com.android.server.am.TaskRecord.INVALID_TASK_ID; 374import static com.android.server.am.TaskRecord.LOCK_TASK_AUTH_DONT_LOCK; 375import static com.android.server.am.TaskRecord.LOCK_TASK_AUTH_LAUNCHABLE_PRIV; 376import static com.android.server.am.TaskRecord.LOCK_TASK_AUTH_PINNABLE; 377import static com.android.server.wm.AppTransition.TRANSIT_ACTIVITY_OPEN; 378import static com.android.server.wm.AppTransition.TRANSIT_ACTIVITY_RELAUNCH; 379import static com.android.server.wm.AppTransition.TRANSIT_NONE; 380import static com.android.server.wm.AppTransition.TRANSIT_TASK_IN_PLACE; 381import static com.android.server.wm.AppTransition.TRANSIT_TASK_OPEN; 382import static com.android.server.wm.AppTransition.TRANSIT_TASK_TO_FRONT; 383import static org.xmlpull.v1.XmlPullParser.END_DOCUMENT; 384import static org.xmlpull.v1.XmlPullParser.START_TAG; 385 386public class ActivityManagerService extends IActivityManager.Stub 387 implements Watchdog.Monitor, BatteryStatsImpl.BatteryCallback { 388 389 private static final String TAG = TAG_WITH_CLASS_NAME ? "ActivityManagerService" : TAG_AM; 390 private static final String TAG_BACKUP = TAG + POSTFIX_BACKUP; 391 private static final String TAG_BROADCAST = TAG + POSTFIX_BROADCAST; 392 private static final String TAG_CLEANUP = TAG + POSTFIX_CLEANUP; 393 private static final String TAG_CONFIGURATION = TAG + POSTFIX_CONFIGURATION; 394 private static final String TAG_FOCUS = TAG + POSTFIX_FOCUS; 395 private static final String TAG_IMMERSIVE = TAG + POSTFIX_IMMERSIVE; 396 private static final String TAG_LOCKSCREEN = TAG + POSTFIX_LOCKSCREEN; 397 private static final String TAG_LOCKTASK = TAG + POSTFIX_LOCKTASK; 398 private static final String TAG_LRU = TAG + POSTFIX_LRU; 399 private static final String TAG_MU = TAG + POSTFIX_MU; 400 private static final String TAG_OOM_ADJ = TAG + POSTFIX_OOM_ADJ; 401 private static final String TAG_POWER = TAG + POSTFIX_POWER; 402 private static final String TAG_PROCESS_OBSERVERS = TAG + POSTFIX_PROCESS_OBSERVERS; 403 private static final String TAG_PROCESSES = TAG + POSTFIX_PROCESSES; 404 private static final String TAG_PROVIDER = TAG + POSTFIX_PROVIDER; 405 private static final String TAG_PSS = TAG + POSTFIX_PSS; 406 private static final String TAG_RECENTS = TAG + POSTFIX_RECENTS; 407 private static final String TAG_SERVICE = TAG + POSTFIX_SERVICE; 408 private static final String TAG_STACK = TAG + POSTFIX_STACK; 409 private static final String TAG_SWITCH = TAG + POSTFIX_SWITCH; 410 private static final String TAG_UID_OBSERVERS = TAG + POSTFIX_UID_OBSERVERS; 411 private static final String TAG_URI_PERMISSION = TAG + POSTFIX_URI_PERMISSION; 412 private static final String TAG_VISIBILITY = TAG + POSTFIX_VISIBILITY; 413 private static final String TAG_VISIBLE_BEHIND = TAG + POSTFIX_VISIBLE_BEHIND; 414 415 // Mock "pretend we're idle now" broadcast action to the job scheduler; declared 416 // here so that while the job scheduler can depend on AMS, the other way around 417 // need not be the case. 418 public static final String ACTION_TRIGGER_IDLE = "com.android.server.ACTION_TRIGGER_IDLE"; 419 420 /** Control over CPU and battery monitoring */ 421 // write battery stats every 30 minutes. 422 static final long BATTERY_STATS_TIME = 30 * 60 * 1000; 423 static final boolean MONITOR_CPU_USAGE = true; 424 // don't sample cpu less than every 5 seconds. 425 static final long MONITOR_CPU_MIN_TIME = 5 * 1000; 426 // wait possibly forever for next cpu sample. 427 static final long MONITOR_CPU_MAX_TIME = 0x0fffffff; 428 static final boolean MONITOR_THREAD_CPU_USAGE = false; 429 430 // The flags that are set for all calls we make to the package manager. 431 static final int STOCK_PM_FLAGS = PackageManager.GET_SHARED_LIBRARY_FILES; 432 433 static final String SYSTEM_DEBUGGABLE = "ro.debuggable"; 434 435 static final boolean IS_USER_BUILD = "user".equals(Build.TYPE); 436 437 // Amount of time after a call to stopAppSwitches() during which we will 438 // prevent further untrusted switches from happening. 439 static final long APP_SWITCH_DELAY_TIME = 5*1000; 440 441 // How long we wait for a launched process to attach to the activity manager 442 // before we decide it's never going to come up for real. 443 static final int PROC_START_TIMEOUT = 10*1000; 444 // How long we wait for an attached process to publish its content providers 445 // before we decide it must be hung. 446 static final int CONTENT_PROVIDER_PUBLISH_TIMEOUT = 10*1000; 447 448 // How long we will retain processes hosting content providers in the "last activity" 449 // state before allowing them to drop down to the regular cached LRU list. This is 450 // to avoid thrashing of provider processes under low memory situations. 451 static final int CONTENT_PROVIDER_RETAIN_TIME = 20*1000; 452 453 // How long we wait for a launched process to attach to the activity manager 454 // before we decide it's never going to come up for real, when the process was 455 // started with a wrapper for instrumentation (such as Valgrind) because it 456 // could take much longer than usual. 457 static final int PROC_START_TIMEOUT_WITH_WRAPPER = 1200*1000; 458 459 // How long to wait after going idle before forcing apps to GC. 460 static final int GC_TIMEOUT = 5*1000; 461 462 // The minimum amount of time between successive GC requests for a process. 463 static final int GC_MIN_INTERVAL = 60*1000; 464 465 // The minimum amount of time between successive PSS requests for a process. 466 static final int FULL_PSS_MIN_INTERVAL = 10*60*1000; 467 468 // The minimum amount of time between successive PSS requests for a process 469 // when the request is due to the memory state being lowered. 470 static final int FULL_PSS_LOWERED_INTERVAL = 2*60*1000; 471 472 // The rate at which we check for apps using excessive power -- 15 mins. 473 static final int POWER_CHECK_DELAY = (DEBUG_POWER_QUICK ? 2 : 15) * 60*1000; 474 475 // The minimum sample duration we will allow before deciding we have 476 // enough data on wake locks to start killing things. 477 static final int WAKE_LOCK_MIN_CHECK_DURATION = (DEBUG_POWER_QUICK ? 1 : 5) * 60*1000; 478 479 // The minimum sample duration we will allow before deciding we have 480 // enough data on CPU usage to start killing things. 481 static final int CPU_MIN_CHECK_DURATION = (DEBUG_POWER_QUICK ? 1 : 5) * 60*1000; 482 483 // How long we allow a receiver to run before giving up on it. 484 static final int BROADCAST_FG_TIMEOUT = 10*1000; 485 static final int BROADCAST_BG_TIMEOUT = 60*1000; 486 487 // How long we wait until we timeout on key dispatching. 488 static final int KEY_DISPATCHING_TIMEOUT = 5*1000; 489 490 // How long we wait until we timeout on key dispatching during instrumentation. 491 static final int INSTRUMENTATION_KEY_DISPATCHING_TIMEOUT = 60*1000; 492 493 // This is the amount of time an app needs to be running a foreground service before 494 // we will consider it to be doing interaction for usage stats. 495 static final int SERVICE_USAGE_INTERACTION_TIME = 30*60*1000; 496 497 // Maximum amount of time we will allow to elapse before re-reporting usage stats 498 // interaction with foreground processes. 499 static final long USAGE_STATS_INTERACTION_INTERVAL = 24*60*60*1000L; 500 501 // This is the amount of time we allow an app to settle after it goes into the background, 502 // before we start restricting what it can do. 503 static final int BACKGROUND_SETTLE_TIME = 1*60*1000; 504 505 // How long to wait in getAssistContextExtras for the activity and foreground services 506 // to respond with the result. 507 static final int PENDING_ASSIST_EXTRAS_TIMEOUT = 500; 508 509 // How long top wait when going through the modern assist (which doesn't need to block 510 // on getting this result before starting to launch its UI). 511 static final int PENDING_ASSIST_EXTRAS_LONG_TIMEOUT = 2000; 512 513 // Maximum number of persisted Uri grants a package is allowed 514 static final int MAX_PERSISTED_URI_GRANTS = 128; 515 516 static final int MY_PID = Process.myPid(); 517 518 static final String[] EMPTY_STRING_ARRAY = new String[0]; 519 520 // How many bytes to write into the dropbox log before truncating 521 static final int DROPBOX_MAX_SIZE = 192 * 1024; 522 // Assumes logcat entries average around 100 bytes; that's not perfect stack traces count 523 // as one line, but close enough for now. 524 static final int RESERVED_BYTES_PER_LOGCAT_LINE = 100; 525 526 // Access modes for handleIncomingUser. 527 static final int ALLOW_NON_FULL = 0; 528 static final int ALLOW_NON_FULL_IN_PROFILE = 1; 529 static final int ALLOW_FULL_ONLY = 2; 530 531 // Necessary ApplicationInfo flags to mark an app as persistent 532 private static final int PERSISTENT_MASK = 533 ApplicationInfo.FLAG_SYSTEM|ApplicationInfo.FLAG_PERSISTENT; 534 535 // Intent sent when remote bugreport collection has been completed 536 private static final String INTENT_REMOTE_BUGREPORT_FINISHED = 537 "android.intent.action.REMOTE_BUGREPORT_FINISHED"; 538 539 // Used to indicate that a task is removed it should also be removed from recents. 540 private static final boolean REMOVE_FROM_RECENTS = true; 541 // Used to indicate that an app transition should be animated. 542 static final boolean ANIMATE = true; 543 544 // Determines whether to take full screen screenshots 545 static final boolean TAKE_FULLSCREEN_SCREENSHOTS = true; 546 public static final float FULLSCREEN_SCREENSHOT_SCALE = 0.6f; 547 548 /** All system services */ 549 SystemServiceManager mSystemServiceManager; 550 551 private Installer mInstaller; 552 553 /** Run all ActivityStacks through this */ 554 final ActivityStackSupervisor mStackSupervisor; 555 private final KeyguardController mKeyguardController; 556 557 final ActivityStarter mActivityStarter; 558 559 final TaskChangeNotificationController mTaskChangeNotificationController; 560 561 final InstrumentationReporter mInstrumentationReporter = new InstrumentationReporter(); 562 563 public IntentFirewall mIntentFirewall; 564 565 // Whether we should show our dialogs (ANR, crash, etc) or just perform their 566 // default action automatically. Important for devices without direct input 567 // devices. 568 private boolean mShowDialogs = true; 569 private boolean mInVrMode = false; 570 571 // Whether we should use SCHED_FIFO for UI and RenderThreads. 572 private boolean mUseFifoUiScheduling = false; 573 574 BroadcastQueue mFgBroadcastQueue; 575 BroadcastQueue mBgBroadcastQueue; 576 // Convenient for easy iteration over the queues. Foreground is first 577 // so that dispatch of foreground broadcasts gets precedence. 578 final BroadcastQueue[] mBroadcastQueues = new BroadcastQueue[2]; 579 580 BroadcastStats mLastBroadcastStats; 581 BroadcastStats mCurBroadcastStats; 582 583 BroadcastQueue broadcastQueueForIntent(Intent intent) { 584 final boolean isFg = (intent.getFlags() & Intent.FLAG_RECEIVER_FOREGROUND) != 0; 585 if (DEBUG_BROADCAST_BACKGROUND) Slog.i(TAG_BROADCAST, 586 "Broadcast intent " + intent + " on " 587 + (isFg ? "foreground" : "background") + " queue"); 588 return (isFg) ? mFgBroadcastQueue : mBgBroadcastQueue; 589 } 590 591 /** 592 * The last resumed activity. This is identical to the current resumed activity most 593 * of the time but could be different when we're pausing one activity before we resume 594 * another activity. 595 */ 596 private ActivityRecord mLastResumedActivity; 597 598 /** 599 * If non-null, we are tracking the time the user spends in the currently focused app. 600 */ 601 private AppTimeTracker mCurAppTimeTracker; 602 603 /** 604 * List of intents that were used to start the most recent tasks. 605 */ 606 final RecentTasks mRecentTasks; 607 608 /** 609 * For addAppTask: cached of the last activity component that was added. 610 */ 611 ComponentName mLastAddedTaskComponent; 612 613 /** 614 * For addAppTask: cached of the last activity uid that was added. 615 */ 616 int mLastAddedTaskUid; 617 618 /** 619 * For addAppTask: cached of the last ActivityInfo that was added. 620 */ 621 ActivityInfo mLastAddedTaskActivity; 622 623 /** 624 * List of packages whitelisted by DevicePolicyManager for locktask. Indexed by userId. 625 */ 626 SparseArray<String[]> mLockTaskPackages = new SparseArray<>(); 627 628 /** 629 * The package name of the DeviceOwner. This package is not permitted to have its data cleared. 630 */ 631 String mDeviceOwnerName; 632 633 final UserController mUserController; 634 635 final AppErrors mAppErrors; 636 637 public boolean canShowErrorDialogs() { 638 return mShowDialogs && !mSleeping && !mShuttingDown 639 && !mKeyguardController.isKeyguardShowing(); 640 } 641 642 private static final class PriorityState { 643 // Acts as counter for number of synchronized region that needs to acquire 'this' as a lock 644 // the current thread is currently in. When it drops down to zero, we will no longer boost 645 // the thread's priority. 646 private int regionCounter = 0; 647 648 // The thread's previous priority before boosting. 649 private int prevPriority = Integer.MIN_VALUE; 650 } 651 652 static ThreadLocal<PriorityState> sThreadPriorityState = new ThreadLocal<PriorityState>() { 653 @Override protected PriorityState initialValue() { 654 return new PriorityState(); 655 } 656 }; 657 658 static void boostPriorityForLockedSection() { 659 int tid = Process.myTid(); 660 int prevPriority = Process.getThreadPriority(tid); 661 PriorityState state = sThreadPriorityState.get(); 662 if (state.regionCounter == 0 && prevPriority > -2) { 663 state.prevPriority = prevPriority; 664 Process.setThreadPriority(tid, -2); 665 } 666 state.regionCounter++; 667 } 668 669 static void resetPriorityAfterLockedSection() { 670 PriorityState state = sThreadPriorityState.get(); 671 state.regionCounter--; 672 if (state.regionCounter == 0 && state.prevPriority > -2) { 673 Process.setThreadPriority(Process.myTid(), state.prevPriority); 674 } 675 } 676 677 public class PendingAssistExtras extends Binder implements Runnable { 678 public final ActivityRecord activity; 679 public final Bundle extras; 680 public final Intent intent; 681 public final String hint; 682 public final IResultReceiver receiver; 683 public final int userHandle; 684 public boolean haveResult = false; 685 public Bundle result = null; 686 public AssistStructure structure = null; 687 public AssistContent content = null; 688 public Bundle receiverExtras; 689 690 public PendingAssistExtras(ActivityRecord _activity, Bundle _extras, Intent _intent, 691 String _hint, IResultReceiver _receiver, Bundle _receiverExtras, int _userHandle) { 692 activity = _activity; 693 extras = _extras; 694 intent = _intent; 695 hint = _hint; 696 receiver = _receiver; 697 receiverExtras = _receiverExtras; 698 userHandle = _userHandle; 699 } 700 @Override 701 public void run() { 702 Slog.w(TAG, "getAssistContextExtras failed: timeout retrieving from " + activity); 703 synchronized (this) { 704 haveResult = true; 705 notifyAll(); 706 } 707 pendingAssistExtrasTimedOut(this); 708 } 709 } 710 711 final ArrayList<PendingAssistExtras> mPendingAssistExtras 712 = new ArrayList<PendingAssistExtras>(); 713 714 /** 715 * Process management. 716 */ 717 final ProcessList mProcessList = new ProcessList(); 718 719 /** 720 * All of the applications we currently have running organized by name. 721 * The keys are strings of the application package name (as 722 * returned by the package manager), and the keys are ApplicationRecord 723 * objects. 724 */ 725 final ProcessMap<ProcessRecord> mProcessNames = new ProcessMap<ProcessRecord>(); 726 727 /** 728 * Tracking long-term execution of processes to look for abuse and other 729 * bad app behavior. 730 */ 731 final ProcessStatsService mProcessStats; 732 733 /** 734 * The currently running isolated processes. 735 */ 736 final SparseArray<ProcessRecord> mIsolatedProcesses = new SparseArray<ProcessRecord>(); 737 738 /** 739 * Counter for assigning isolated process uids, to avoid frequently reusing the 740 * same ones. 741 */ 742 int mNextIsolatedProcessUid = 0; 743 744 /** 745 * The currently running heavy-weight process, if any. 746 */ 747 ProcessRecord mHeavyWeightProcess = null; 748 749 /** 750 * All of the processes we currently have running organized by pid. 751 * The keys are the pid running the application. 752 * 753 * <p>NOTE: This object is protected by its own lock, NOT the global 754 * activity manager lock! 755 */ 756 final SparseArray<ProcessRecord> mPidsSelfLocked = new SparseArray<ProcessRecord>(); 757 758 /** 759 * All of the processes that have been forced to be foreground. The key 760 * is the pid of the caller who requested it (we hold a death 761 * link on it). 762 */ 763 abstract class ForegroundToken implements IBinder.DeathRecipient { 764 int pid; 765 IBinder token; 766 } 767 final SparseArray<ForegroundToken> mForegroundProcesses = new SparseArray<ForegroundToken>(); 768 769 /** 770 * List of records for processes that someone had tried to start before the 771 * system was ready. We don't start them at that point, but ensure they 772 * are started by the time booting is complete. 773 */ 774 final ArrayList<ProcessRecord> mProcessesOnHold = new ArrayList<ProcessRecord>(); 775 776 /** 777 * List of persistent applications that are in the process 778 * of being started. 779 */ 780 final ArrayList<ProcessRecord> mPersistentStartingProcesses = new ArrayList<ProcessRecord>(); 781 782 /** 783 * Processes that are being forcibly torn down. 784 */ 785 final ArrayList<ProcessRecord> mRemovedProcesses = new ArrayList<ProcessRecord>(); 786 787 /** 788 * List of running applications, sorted by recent usage. 789 * The first entry in the list is the least recently used. 790 */ 791 final ArrayList<ProcessRecord> mLruProcesses = new ArrayList<ProcessRecord>(); 792 793 /** 794 * Where in mLruProcesses that the processes hosting activities start. 795 */ 796 int mLruProcessActivityStart = 0; 797 798 /** 799 * Where in mLruProcesses that the processes hosting services start. 800 * This is after (lower index) than mLruProcessesActivityStart. 801 */ 802 int mLruProcessServiceStart = 0; 803 804 /** 805 * List of processes that should gc as soon as things are idle. 806 */ 807 final ArrayList<ProcessRecord> mProcessesToGc = new ArrayList<ProcessRecord>(); 808 809 /** 810 * Processes we want to collect PSS data from. 811 */ 812 final ArrayList<ProcessRecord> mPendingPssProcesses = new ArrayList<ProcessRecord>(); 813 814 private boolean mBinderTransactionTrackingEnabled = false; 815 816 /** 817 * Last time we requested PSS data of all processes. 818 */ 819 long mLastFullPssTime = SystemClock.uptimeMillis(); 820 821 /** 822 * If set, the next time we collect PSS data we should do a full collection 823 * with data from native processes and the kernel. 824 */ 825 boolean mFullPssPending = false; 826 827 /** 828 * This is the process holding what we currently consider to be 829 * the "home" activity. 830 */ 831 ProcessRecord mHomeProcess; 832 833 /** 834 * This is the process holding the activity the user last visited that 835 * is in a different process from the one they are currently in. 836 */ 837 ProcessRecord mPreviousProcess; 838 839 /** 840 * The time at which the previous process was last visible. 841 */ 842 long mPreviousProcessVisibleTime; 843 844 /** 845 * Track all uids that have actively running processes. 846 */ 847 final SparseArray<UidRecord> mActiveUids = new SparseArray<>(); 848 849 /** 850 * This is for verifying the UID report flow. 851 */ 852 static final boolean VALIDATE_UID_STATES = true; 853 final SparseArray<UidRecord> mValidateUids = new SparseArray<>(); 854 855 /** 856 * Packages that the user has asked to have run in screen size 857 * compatibility mode instead of filling the screen. 858 */ 859 final CompatModePackages mCompatModePackages; 860 861 /** 862 * Set of IntentSenderRecord objects that are currently active. 863 */ 864 final HashMap<PendingIntentRecord.Key, WeakReference<PendingIntentRecord>> mIntentSenderRecords 865 = new HashMap<PendingIntentRecord.Key, WeakReference<PendingIntentRecord>>(); 866 867 /** 868 * Fingerprints (hashCode()) of stack traces that we've 869 * already logged DropBox entries for. Guarded by itself. If 870 * something (rogue user app) forces this over 871 * MAX_DUP_SUPPRESSED_STACKS entries, the contents are cleared. 872 */ 873 private final HashSet<Integer> mAlreadyLoggedViolatedStacks = new HashSet<Integer>(); 874 private static final int MAX_DUP_SUPPRESSED_STACKS = 5000; 875 876 /** 877 * Strict Mode background batched logging state. 878 * 879 * The string buffer is guarded by itself, and its lock is also 880 * used to determine if another batched write is already 881 * in-flight. 882 */ 883 private final StringBuilder mStrictModeBuffer = new StringBuilder(); 884 885 /** 886 * Keeps track of all IIntentReceivers that have been registered for broadcasts. 887 * Hash keys are the receiver IBinder, hash value is a ReceiverList. 888 */ 889 final HashMap<IBinder, ReceiverList> mRegisteredReceivers = new HashMap<>(); 890 891 /** 892 * Resolver for broadcast intents to registered receivers. 893 * Holds BroadcastFilter (subclass of IntentFilter). 894 */ 895 final IntentResolver<BroadcastFilter, BroadcastFilter> mReceiverResolver 896 = new IntentResolver<BroadcastFilter, BroadcastFilter>() { 897 @Override 898 protected boolean allowFilterResult( 899 BroadcastFilter filter, List<BroadcastFilter> dest) { 900 IBinder target = filter.receiverList.receiver.asBinder(); 901 for (int i = dest.size() - 1; i >= 0; i--) { 902 if (dest.get(i).receiverList.receiver.asBinder() == target) { 903 return false; 904 } 905 } 906 return true; 907 } 908 909 @Override 910 protected BroadcastFilter newResult(BroadcastFilter filter, int match, int userId) { 911 if (userId == UserHandle.USER_ALL || filter.owningUserId == UserHandle.USER_ALL 912 || userId == filter.owningUserId) { 913 return super.newResult(filter, match, userId); 914 } 915 return null; 916 } 917 918 @Override 919 protected BroadcastFilter[] newArray(int size) { 920 return new BroadcastFilter[size]; 921 } 922 923 @Override 924 protected boolean isPackageForFilter(String packageName, BroadcastFilter filter) { 925 return packageName.equals(filter.packageName); 926 } 927 }; 928 929 /** 930 * State of all active sticky broadcasts per user. Keys are the action of the 931 * sticky Intent, values are an ArrayList of all broadcasted intents with 932 * that action (which should usually be one). The SparseArray is keyed 933 * by the user ID the sticky is for, and can include UserHandle.USER_ALL 934 * for stickies that are sent to all users. 935 */ 936 final SparseArray<ArrayMap<String, ArrayList<Intent>>> mStickyBroadcasts = 937 new SparseArray<ArrayMap<String, ArrayList<Intent>>>(); 938 939 final ActiveServices mServices; 940 941 final static class Association { 942 final int mSourceUid; 943 final String mSourceProcess; 944 final int mTargetUid; 945 final ComponentName mTargetComponent; 946 final String mTargetProcess; 947 948 int mCount; 949 long mTime; 950 951 int mNesting; 952 long mStartTime; 953 954 // states of the source process when the bind occurred. 955 int mLastState = ActivityManager.MAX_PROCESS_STATE + 1; 956 long mLastStateUptime; 957 long[] mStateTimes = new long[ActivityManager.MAX_PROCESS_STATE 958 - ActivityManager.MIN_PROCESS_STATE+1]; 959 960 Association(int sourceUid, String sourceProcess, int targetUid, 961 ComponentName targetComponent, String targetProcess) { 962 mSourceUid = sourceUid; 963 mSourceProcess = sourceProcess; 964 mTargetUid = targetUid; 965 mTargetComponent = targetComponent; 966 mTargetProcess = targetProcess; 967 } 968 } 969 970 /** 971 * When service association tracking is enabled, this is all of the associations we 972 * have seen. Mapping is target uid -> target component -> source uid -> source process name 973 * -> association data. 974 */ 975 final SparseArray<ArrayMap<ComponentName, SparseArray<ArrayMap<String, Association>>>> 976 mAssociations = new SparseArray<>(); 977 boolean mTrackingAssociations; 978 979 /** 980 * Backup/restore process management 981 */ 982 String mBackupAppName = null; 983 BackupRecord mBackupTarget = null; 984 985 final ProviderMap mProviderMap; 986 987 /** 988 * List of content providers who have clients waiting for them. The 989 * application is currently being launched and the provider will be 990 * removed from this list once it is published. 991 */ 992 final ArrayList<ContentProviderRecord> mLaunchingProviders 993 = new ArrayList<ContentProviderRecord>(); 994 995 /** 996 * File storing persisted {@link #mGrantedUriPermissions}. 997 */ 998 private final AtomicFile mGrantFile; 999 1000 /** XML constants used in {@link #mGrantFile} */ 1001 private static final String TAG_URI_GRANTS = "uri-grants"; 1002 private static final String TAG_URI_GRANT = "uri-grant"; 1003 private static final String ATTR_USER_HANDLE = "userHandle"; 1004 private static final String ATTR_SOURCE_USER_ID = "sourceUserId"; 1005 private static final String ATTR_TARGET_USER_ID = "targetUserId"; 1006 private static final String ATTR_SOURCE_PKG = "sourcePkg"; 1007 private static final String ATTR_TARGET_PKG = "targetPkg"; 1008 private static final String ATTR_URI = "uri"; 1009 private static final String ATTR_MODE_FLAGS = "modeFlags"; 1010 private static final String ATTR_CREATED_TIME = "createdTime"; 1011 private static final String ATTR_PREFIX = "prefix"; 1012 1013 /** 1014 * Global set of specific {@link Uri} permissions that have been granted. 1015 * This optimized lookup structure maps from {@link UriPermission#targetUid} 1016 * to {@link UriPermission#uri} to {@link UriPermission}. 1017 */ 1018 @GuardedBy("this") 1019 private final SparseArray<ArrayMap<GrantUri, UriPermission>> 1020 mGrantedUriPermissions = new SparseArray<ArrayMap<GrantUri, UriPermission>>(); 1021 1022 public static class GrantUri { 1023 public final int sourceUserId; 1024 public final Uri uri; 1025 public boolean prefix; 1026 1027 public GrantUri(int sourceUserId, Uri uri, boolean prefix) { 1028 this.sourceUserId = sourceUserId; 1029 this.uri = uri; 1030 this.prefix = prefix; 1031 } 1032 1033 @Override 1034 public int hashCode() { 1035 int hashCode = 1; 1036 hashCode = 31 * hashCode + sourceUserId; 1037 hashCode = 31 * hashCode + uri.hashCode(); 1038 hashCode = 31 * hashCode + (prefix ? 1231 : 1237); 1039 return hashCode; 1040 } 1041 1042 @Override 1043 public boolean equals(Object o) { 1044 if (o instanceof GrantUri) { 1045 GrantUri other = (GrantUri) o; 1046 return uri.equals(other.uri) && (sourceUserId == other.sourceUserId) 1047 && prefix == other.prefix; 1048 } 1049 return false; 1050 } 1051 1052 @Override 1053 public String toString() { 1054 String result = Integer.toString(sourceUserId) + " @ " + uri.toString(); 1055 if (prefix) result += " [prefix]"; 1056 return result; 1057 } 1058 1059 public String toSafeString() { 1060 String result = Integer.toString(sourceUserId) + " @ " + uri.toSafeString(); 1061 if (prefix) result += " [prefix]"; 1062 return result; 1063 } 1064 1065 public static GrantUri resolve(int defaultSourceUserHandle, Uri uri) { 1066 return new GrantUri(ContentProvider.getUserIdFromUri(uri, defaultSourceUserHandle), 1067 ContentProvider.getUriWithoutUserId(uri), false); 1068 } 1069 } 1070 1071 CoreSettingsObserver mCoreSettingsObserver; 1072 1073 FontScaleSettingObserver mFontScaleSettingObserver; 1074 1075 private final class FontScaleSettingObserver extends ContentObserver { 1076 private final Uri mFontScaleUri = Settings.System.getUriFor(FONT_SCALE); 1077 1078 public FontScaleSettingObserver() { 1079 super(mHandler); 1080 ContentResolver resolver = mContext.getContentResolver(); 1081 resolver.registerContentObserver(mFontScaleUri, false, this, UserHandle.USER_ALL); 1082 } 1083 1084 @Override 1085 public void onChange(boolean selfChange, Uri uri, @UserIdInt int userId) { 1086 if (mFontScaleUri.equals(uri)) { 1087 updateFontScaleIfNeeded(userId); 1088 } 1089 } 1090 } 1091 1092 /** 1093 * Thread-local storage used to carry caller permissions over through 1094 * indirect content-provider access. 1095 */ 1096 private class Identity { 1097 public final IBinder token; 1098 public final int pid; 1099 public final int uid; 1100 1101 Identity(IBinder _token, int _pid, int _uid) { 1102 token = _token; 1103 pid = _pid; 1104 uid = _uid; 1105 } 1106 } 1107 1108 private static final ThreadLocal<Identity> sCallerIdentity = new ThreadLocal<Identity>(); 1109 1110 /** 1111 * All information we have collected about the runtime performance of 1112 * any user id that can impact battery performance. 1113 */ 1114 final BatteryStatsService mBatteryStatsService; 1115 1116 /** 1117 * Information about component usage 1118 */ 1119 UsageStatsManagerInternal mUsageStatsService; 1120 1121 /** 1122 * Access to DeviceIdleController service. 1123 */ 1124 DeviceIdleController.LocalService mLocalDeviceIdleController; 1125 1126 /** 1127 * Information about and control over application operations 1128 */ 1129 final AppOpsService mAppOpsService; 1130 1131 /** Current sequencing integer of the configuration, for skipping old configurations. */ 1132 private int mConfigurationSeq; 1133 1134 /** 1135 * Temp object used when global and/or display override configuration is updated. It is also 1136 * sent to outer world instead of {@link #getGlobalConfiguration} because we don't trust 1137 * anyone... 1138 */ 1139 private Configuration mTempConfig = new Configuration(); 1140 1141 private final UpdateConfigurationResult mTmpUpdateConfigurationResult = 1142 new UpdateConfigurationResult(); 1143 private static final class UpdateConfigurationResult { 1144 // Configuration changes that were updated. 1145 int changes; 1146 // If the activity was relaunched to match the new configuration. 1147 boolean activityRelaunched; 1148 1149 void reset() { 1150 changes = 0; 1151 activityRelaunched = false; 1152 } 1153 } 1154 1155 boolean mSuppressResizeConfigChanges; 1156 1157 /** 1158 * Hardware-reported OpenGLES version. 1159 */ 1160 final int GL_ES_VERSION; 1161 1162 /** 1163 * List of initialization arguments to pass to all processes when binding applications to them. 1164 * For example, references to the commonly used services. 1165 */ 1166 HashMap<String, IBinder> mAppBindArgs; 1167 HashMap<String, IBinder> mIsolatedAppBindArgs; 1168 1169 /** 1170 * Temporary to avoid allocations. Protected by main lock. 1171 */ 1172 final StringBuilder mStringBuilder = new StringBuilder(256); 1173 1174 /** 1175 * Used to control how we initialize the service. 1176 */ 1177 ComponentName mTopComponent; 1178 String mTopAction = Intent.ACTION_MAIN; 1179 String mTopData; 1180 1181 volatile boolean mProcessesReady = false; 1182 volatile boolean mSystemReady = false; 1183 volatile boolean mOnBattery = false; 1184 volatile int mFactoryTest; 1185 1186 @GuardedBy("this") boolean mBooting = false; 1187 @GuardedBy("this") boolean mCallFinishBooting = false; 1188 @GuardedBy("this") boolean mBootAnimationComplete = false; 1189 @GuardedBy("this") boolean mLaunchWarningShown = false; 1190 @GuardedBy("this") boolean mCheckedForSetup = false; 1191 1192 Context mContext; 1193 1194 /** 1195 * The time at which we will allow normal application switches again, 1196 * after a call to {@link #stopAppSwitches()}. 1197 */ 1198 long mAppSwitchesAllowedTime; 1199 1200 /** 1201 * This is set to true after the first switch after mAppSwitchesAllowedTime 1202 * is set; any switches after that will clear the time. 1203 */ 1204 boolean mDidAppSwitch; 1205 1206 /** 1207 * Last time (in realtime) at which we checked for power usage. 1208 */ 1209 long mLastPowerCheckRealtime; 1210 1211 /** 1212 * Last time (in uptime) at which we checked for power usage. 1213 */ 1214 long mLastPowerCheckUptime; 1215 1216 /** 1217 * Set while we are wanting to sleep, to prevent any 1218 * activities from being started/resumed. 1219 */ 1220 private boolean mSleeping = false; 1221 1222 /** 1223 * The process state used for processes that are running the top activities. 1224 * This changes between TOP and TOP_SLEEPING to following mSleeping. 1225 */ 1226 int mTopProcessState = ActivityManager.PROCESS_STATE_TOP; 1227 1228 /** 1229 * Set while we are running a voice interaction. This overrides 1230 * sleeping while it is active. 1231 */ 1232 private IVoiceInteractionSession mRunningVoice; 1233 1234 /** 1235 * For some direct access we need to power manager. 1236 */ 1237 PowerManagerInternal mLocalPowerManager; 1238 1239 /** 1240 * We want to hold a wake lock while running a voice interaction session, since 1241 * this may happen with the screen off and we need to keep the CPU running to 1242 * be able to continue to interact with the user. 1243 */ 1244 PowerManager.WakeLock mVoiceWakeLock; 1245 1246 /** 1247 * State of external calls telling us if the device is awake or asleep. 1248 */ 1249 private int mWakefulness = PowerManagerInternal.WAKEFULNESS_AWAKE; 1250 1251 /** 1252 * A list of tokens that cause the top activity to be put to sleep. 1253 * They are used by components that may hide and block interaction with underlying 1254 * activities. 1255 */ 1256 final ArrayList<SleepToken> mSleepTokens = new ArrayList<SleepToken>(); 1257 1258 /** 1259 * Set if we are shutting down the system, similar to sleeping. 1260 */ 1261 boolean mShuttingDown = false; 1262 1263 /** 1264 * Current sequence id for oom_adj computation traversal. 1265 */ 1266 int mAdjSeq = 0; 1267 1268 /** 1269 * Current sequence id for process LRU updating. 1270 */ 1271 int mLruSeq = 0; 1272 1273 /** 1274 * Keep track of the non-cached/empty process we last found, to help 1275 * determine how to distribute cached/empty processes next time. 1276 */ 1277 int mNumNonCachedProcs = 0; 1278 1279 /** 1280 * Keep track of the number of cached hidden procs, to balance oom adj 1281 * distribution between those and empty procs. 1282 */ 1283 int mNumCachedHiddenProcs = 0; 1284 1285 /** 1286 * Keep track of the number of service processes we last found, to 1287 * determine on the next iteration which should be B services. 1288 */ 1289 int mNumServiceProcs = 0; 1290 int mNewNumAServiceProcs = 0; 1291 int mNewNumServiceProcs = 0; 1292 1293 /** 1294 * Allow the current computed overall memory level of the system to go down? 1295 * This is set to false when we are killing processes for reasons other than 1296 * memory management, so that the now smaller process list will not be taken as 1297 * an indication that memory is tighter. 1298 */ 1299 boolean mAllowLowerMemLevel = false; 1300 1301 /** 1302 * The last computed memory level, for holding when we are in a state that 1303 * processes are going away for other reasons. 1304 */ 1305 int mLastMemoryLevel = ProcessStats.ADJ_MEM_FACTOR_NORMAL; 1306 1307 /** 1308 * The last total number of process we have, to determine if changes actually look 1309 * like a shrinking number of process due to lower RAM. 1310 */ 1311 int mLastNumProcesses; 1312 1313 /** 1314 * The uptime of the last time we performed idle maintenance. 1315 */ 1316 long mLastIdleTime = SystemClock.uptimeMillis(); 1317 1318 /** 1319 * Total time spent with RAM that has been added in the past since the last idle time. 1320 */ 1321 long mLowRamTimeSinceLastIdle = 0; 1322 1323 /** 1324 * If RAM is currently low, when that horrible situation started. 1325 */ 1326 long mLowRamStartTime = 0; 1327 1328 /** 1329 * For reporting to battery stats the current top application. 1330 */ 1331 private String mCurResumedPackage = null; 1332 private int mCurResumedUid = -1; 1333 1334 /** 1335 * For reporting to battery stats the apps currently running foreground 1336 * service. The ProcessMap is package/uid tuples; each of these contain 1337 * an array of the currently foreground processes. 1338 */ 1339 final ProcessMap<ArrayList<ProcessRecord>> mForegroundPackages 1340 = new ProcessMap<ArrayList<ProcessRecord>>(); 1341 1342 /** 1343 * This is set if we had to do a delayed dexopt of an app before launching 1344 * it, to increase the ANR timeouts in that case. 1345 */ 1346 boolean mDidDexOpt; 1347 1348 /** 1349 * Set if the systemServer made a call to enterSafeMode. 1350 */ 1351 boolean mSafeMode; 1352 1353 /** 1354 * If true, we are running under a test environment so will sample PSS from processes 1355 * much more rapidly to try to collect better data when the tests are rapidly 1356 * running through apps. 1357 */ 1358 boolean mTestPssMode = false; 1359 1360 String mDebugApp = null; 1361 boolean mWaitForDebugger = false; 1362 boolean mDebugTransient = false; 1363 String mOrigDebugApp = null; 1364 boolean mOrigWaitForDebugger = false; 1365 boolean mAlwaysFinishActivities = false; 1366 boolean mLenientBackgroundCheck = false; 1367 boolean mForceResizableActivities; 1368 boolean mSupportsMultiWindow; 1369 boolean mSupportsFreeformWindowManagement; 1370 boolean mSupportsPictureInPicture; 1371 boolean mSupportsLeanbackOnly; 1372 IActivityController mController = null; 1373 boolean mControllerIsAMonkey = false; 1374 String mProfileApp = null; 1375 ProcessRecord mProfileProc = null; 1376 String mProfileFile; 1377 ParcelFileDescriptor mProfileFd; 1378 int mSamplingInterval = 0; 1379 boolean mAutoStopProfiler = false; 1380 int mProfileType = 0; 1381 final ProcessMap<Pair<Long, String>> mMemWatchProcesses = new ProcessMap<>(); 1382 String mMemWatchDumpProcName; 1383 String mMemWatchDumpFile; 1384 int mMemWatchDumpPid; 1385 int mMemWatchDumpUid; 1386 String mTrackAllocationApp = null; 1387 String mNativeDebuggingApp = null; 1388 1389 final long[] mTmpLong = new long[2]; 1390 1391 static final class ProcessChangeItem { 1392 static final int CHANGE_ACTIVITIES = 1<<0; 1393 static final int CHANGE_PROCESS_STATE = 1<<1; 1394 int changes; 1395 int uid; 1396 int pid; 1397 int processState; 1398 boolean foregroundActivities; 1399 } 1400 1401 final RemoteCallbackList<IProcessObserver> mProcessObservers = new RemoteCallbackList<>(); 1402 ProcessChangeItem[] mActiveProcessChanges = new ProcessChangeItem[5]; 1403 1404 final ArrayList<ProcessChangeItem> mPendingProcessChanges = new ArrayList<>(); 1405 final ArrayList<ProcessChangeItem> mAvailProcessChanges = new ArrayList<>(); 1406 1407 final RemoteCallbackList<IUidObserver> mUidObservers = new RemoteCallbackList<>(); 1408 UidRecord.ChangeItem[] mActiveUidChanges = new UidRecord.ChangeItem[5]; 1409 1410 final ArrayList<UidRecord.ChangeItem> mPendingUidChanges = new ArrayList<>(); 1411 final ArrayList<UidRecord.ChangeItem> mAvailUidChanges = new ArrayList<>(); 1412 1413 /** 1414 * Runtime CPU use collection thread. This object's lock is used to 1415 * perform synchronization with the thread (notifying it to run). 1416 */ 1417 final Thread mProcessCpuThread; 1418 1419 /** 1420 * Used to collect per-process CPU use for ANRs, battery stats, etc. 1421 * Must acquire this object's lock when accessing it. 1422 * NOTE: this lock will be held while doing long operations (trawling 1423 * through all processes in /proc), so it should never be acquired by 1424 * any critical paths such as when holding the main activity manager lock. 1425 */ 1426 final ProcessCpuTracker mProcessCpuTracker = new ProcessCpuTracker( 1427 MONITOR_THREAD_CPU_USAGE); 1428 final AtomicLong mLastCpuTime = new AtomicLong(0); 1429 final AtomicBoolean mProcessCpuMutexFree = new AtomicBoolean(true); 1430 1431 long mLastWriteTime = 0; 1432 1433 /** 1434 * Used to retain an update lock when the foreground activity is in 1435 * immersive mode. 1436 */ 1437 final UpdateLock mUpdateLock = new UpdateLock("immersive"); 1438 1439 /** 1440 * Set to true after the system has finished booting. 1441 */ 1442 boolean mBooted = false; 1443 1444 int mProcessLimit = ProcessList.MAX_CACHED_APPS; 1445 int mProcessLimitOverride = -1; 1446 1447 WindowManagerService mWindowManager; 1448 final ActivityThread mSystemThread; 1449 1450 private final class AppDeathRecipient implements IBinder.DeathRecipient { 1451 final ProcessRecord mApp; 1452 final int mPid; 1453 final IApplicationThread mAppThread; 1454 1455 AppDeathRecipient(ProcessRecord app, int pid, 1456 IApplicationThread thread) { 1457 if (DEBUG_ALL) Slog.v( 1458 TAG, "New death recipient " + this 1459 + " for thread " + thread.asBinder()); 1460 mApp = app; 1461 mPid = pid; 1462 mAppThread = thread; 1463 } 1464 1465 @Override 1466 public void binderDied() { 1467 if (DEBUG_ALL) Slog.v( 1468 TAG, "Death received in " + this 1469 + " for thread " + mAppThread.asBinder()); 1470 synchronized(ActivityManagerService.this) { 1471 appDiedLocked(mApp, mPid, mAppThread, true); 1472 } 1473 } 1474 } 1475 1476 static final int SHOW_ERROR_UI_MSG = 1; 1477 static final int SHOW_NOT_RESPONDING_UI_MSG = 2; 1478 static final int SHOW_FACTORY_ERROR_UI_MSG = 3; 1479 static final int UPDATE_CONFIGURATION_MSG = 4; 1480 static final int GC_BACKGROUND_PROCESSES_MSG = 5; 1481 static final int WAIT_FOR_DEBUGGER_UI_MSG = 6; 1482 static final int SERVICE_TIMEOUT_MSG = 12; 1483 static final int UPDATE_TIME_ZONE = 13; 1484 static final int SHOW_UID_ERROR_UI_MSG = 14; 1485 static final int SHOW_FINGERPRINT_ERROR_UI_MSG = 15; 1486 static final int PROC_START_TIMEOUT_MSG = 20; 1487 static final int DO_PENDING_ACTIVITY_LAUNCHES_MSG = 21; 1488 static final int KILL_APPLICATION_MSG = 22; 1489 static final int FINALIZE_PENDING_INTENT_MSG = 23; 1490 static final int POST_HEAVY_NOTIFICATION_MSG = 24; 1491 static final int CANCEL_HEAVY_NOTIFICATION_MSG = 25; 1492 static final int SHOW_STRICT_MODE_VIOLATION_UI_MSG = 26; 1493 static final int CHECK_EXCESSIVE_WAKE_LOCKS_MSG = 27; 1494 static final int CLEAR_DNS_CACHE_MSG = 28; 1495 static final int UPDATE_HTTP_PROXY_MSG = 29; 1496 static final int SHOW_COMPAT_MODE_DIALOG_UI_MSG = 30; 1497 static final int DISPATCH_PROCESSES_CHANGED_UI_MSG = 31; 1498 static final int DISPATCH_PROCESS_DIED_UI_MSG = 32; 1499 static final int REPORT_MEM_USAGE_MSG = 33; 1500 static final int REPORT_USER_SWITCH_MSG = 34; 1501 static final int CONTINUE_USER_SWITCH_MSG = 35; 1502 static final int USER_SWITCH_TIMEOUT_MSG = 36; 1503 static final int IMMERSIVE_MODE_LOCK_MSG = 37; 1504 static final int PERSIST_URI_GRANTS_MSG = 38; 1505 static final int REQUEST_ALL_PSS_MSG = 39; 1506 static final int START_PROFILES_MSG = 40; 1507 static final int UPDATE_TIME = 41; 1508 static final int SYSTEM_USER_START_MSG = 42; 1509 static final int SYSTEM_USER_CURRENT_MSG = 43; 1510 static final int ENTER_ANIMATION_COMPLETE_MSG = 44; 1511 static final int FINISH_BOOTING_MSG = 45; 1512 static final int START_USER_SWITCH_UI_MSG = 46; 1513 static final int SEND_LOCALE_TO_MOUNT_DAEMON_MSG = 47; 1514 static final int DISMISS_DIALOG_UI_MSG = 48; 1515 static final int NOTIFY_CLEARTEXT_NETWORK_MSG = 49; 1516 static final int POST_DUMP_HEAP_NOTIFICATION_MSG = 50; 1517 static final int DELETE_DUMPHEAP_MSG = 51; 1518 static final int FOREGROUND_PROFILE_CHANGED_MSG = 52; 1519 static final int DISPATCH_UIDS_CHANGED_UI_MSG = 53; 1520 static final int REPORT_TIME_TRACKER_MSG = 54; 1521 static final int REPORT_USER_SWITCH_COMPLETE_MSG = 55; 1522 static final int SHUTDOWN_UI_AUTOMATION_CONNECTION_MSG = 56; 1523 static final int CONTENT_PROVIDER_PUBLISH_TIMEOUT_MSG = 57; 1524 static final int IDLE_UIDS_MSG = 58; 1525 static final int SYSTEM_USER_UNLOCK_MSG = 59; 1526 static final int LOG_STACK_STATE = 60; 1527 static final int VR_MODE_CHANGE_MSG = 61; 1528 static final int VR_MODE_APPLY_IF_NEEDED_MSG = 62; 1529 static final int SHOW_UNSUPPORTED_DISPLAY_SIZE_DIALOG_MSG = 63; 1530 static final int HANDLE_TRUST_STORAGE_UPDATE_MSG = 64; 1531 static final int REPORT_LOCKED_BOOT_COMPLETE_MSG = 65; 1532 static final int START_USER_SWITCH_FG_MSG = 712; 1533 1534 static final int FIRST_ACTIVITY_STACK_MSG = 100; 1535 static final int FIRST_BROADCAST_QUEUE_MSG = 200; 1536 static final int FIRST_COMPAT_MODE_MSG = 300; 1537 static final int FIRST_SUPERVISOR_STACK_MSG = 100; 1538 1539 static ServiceThread sKillThread = null; 1540 static KillHandler sKillHandler = null; 1541 1542 CompatModeDialog mCompatModeDialog; 1543 UnsupportedDisplaySizeDialog mUnsupportedDisplaySizeDialog; 1544 long mLastMemUsageReportTime = 0; 1545 1546 /** 1547 * Flag whether the current user is a "monkey", i.e. whether 1548 * the UI is driven by a UI automation tool. 1549 */ 1550 private boolean mUserIsMonkey; 1551 1552 /** Flag whether the device has a Recents UI */ 1553 boolean mHasRecents; 1554 1555 /** The dimensions of the thumbnails in the Recents UI. */ 1556 int mThumbnailWidth; 1557 int mThumbnailHeight; 1558 float mFullscreenThumbnailScale; 1559 1560 final ServiceThread mHandlerThread; 1561 final MainHandler mHandler; 1562 final UiHandler mUiHandler; 1563 1564 PackageManagerInternal mPackageManagerInt; 1565 1566 // VoiceInteraction session ID that changes for each new request except when 1567 // being called for multiwindow assist in a single session. 1568 private int mViSessionId = 1000; 1569 1570 final boolean mPermissionReviewRequired; 1571 1572 /** 1573 * Current global configuration information. Contains general settings for the entire system, 1574 * also corresponds to the merged configuration of the default display. 1575 */ 1576 Configuration getGlobalConfiguration() { 1577 return mStackSupervisor.getConfiguration(); 1578 } 1579 1580 final class KillHandler extends Handler { 1581 static final int KILL_PROCESS_GROUP_MSG = 4000; 1582 1583 public KillHandler(Looper looper) { 1584 super(looper, null, true); 1585 } 1586 1587 @Override 1588 public void handleMessage(Message msg) { 1589 switch (msg.what) { 1590 case KILL_PROCESS_GROUP_MSG: 1591 { 1592 Trace.traceBegin(Trace.TRACE_TAG_ACTIVITY_MANAGER, "killProcessGroup"); 1593 Process.killProcessGroup(msg.arg1 /* uid */, msg.arg2 /* pid */); 1594 Trace.traceEnd(Trace.TRACE_TAG_ACTIVITY_MANAGER); 1595 } 1596 break; 1597 1598 default: 1599 super.handleMessage(msg); 1600 } 1601 } 1602 } 1603 1604 final class UiHandler extends Handler { 1605 public UiHandler() { 1606 super(com.android.server.UiThread.get().getLooper(), null, true); 1607 } 1608 1609 @Override 1610 public void handleMessage(Message msg) { 1611 switch (msg.what) { 1612 case SHOW_ERROR_UI_MSG: { 1613 mAppErrors.handleShowAppErrorUi(msg); 1614 ensureBootCompleted(); 1615 } break; 1616 case SHOW_NOT_RESPONDING_UI_MSG: { 1617 mAppErrors.handleShowAnrUi(msg); 1618 ensureBootCompleted(); 1619 } break; 1620 case SHOW_STRICT_MODE_VIOLATION_UI_MSG: { 1621 HashMap<String, Object> data = (HashMap<String, Object>) msg.obj; 1622 synchronized (ActivityManagerService.this) { 1623 ProcessRecord proc = (ProcessRecord) data.get("app"); 1624 if (proc == null) { 1625 Slog.e(TAG, "App not found when showing strict mode dialog."); 1626 break; 1627 } 1628 if (proc.crashDialog != null) { 1629 Slog.e(TAG, "App already has strict mode dialog: " + proc); 1630 return; 1631 } 1632 AppErrorResult res = (AppErrorResult) data.get("result"); 1633 if (mShowDialogs && !mSleeping && !mShuttingDown) { 1634 Dialog d = new StrictModeViolationDialog(mContext, 1635 ActivityManagerService.this, res, proc); 1636 d.show(); 1637 proc.crashDialog = d; 1638 } else { 1639 // The device is asleep, so just pretend that the user 1640 // saw a crash dialog and hit "force quit". 1641 res.set(0); 1642 } 1643 } 1644 ensureBootCompleted(); 1645 } break; 1646 case SHOW_FACTORY_ERROR_UI_MSG: { 1647 Dialog d = new FactoryErrorDialog( 1648 mContext, msg.getData().getCharSequence("msg")); 1649 d.show(); 1650 ensureBootCompleted(); 1651 } break; 1652 case WAIT_FOR_DEBUGGER_UI_MSG: { 1653 synchronized (ActivityManagerService.this) { 1654 ProcessRecord app = (ProcessRecord)msg.obj; 1655 if (msg.arg1 != 0) { 1656 if (!app.waitedForDebugger) { 1657 Dialog d = new AppWaitingForDebuggerDialog( 1658 ActivityManagerService.this, 1659 mContext, app); 1660 app.waitDialog = d; 1661 app.waitedForDebugger = true; 1662 d.show(); 1663 } 1664 } else { 1665 if (app.waitDialog != null) { 1666 app.waitDialog.dismiss(); 1667 app.waitDialog = null; 1668 } 1669 } 1670 } 1671 } break; 1672 case SHOW_UID_ERROR_UI_MSG: { 1673 if (mShowDialogs) { 1674 AlertDialog d = new BaseErrorDialog(mContext); 1675 d.getWindow().setType(WindowManager.LayoutParams.TYPE_SYSTEM_ERROR); 1676 d.setCancelable(false); 1677 d.setTitle(mContext.getText(R.string.android_system_label)); 1678 d.setMessage(mContext.getText(R.string.system_error_wipe_data)); 1679 d.setButton(DialogInterface.BUTTON_POSITIVE, mContext.getText(R.string.ok), 1680 obtainMessage(DISMISS_DIALOG_UI_MSG, d)); 1681 d.show(); 1682 } 1683 } break; 1684 case SHOW_FINGERPRINT_ERROR_UI_MSG: { 1685 if (mShowDialogs) { 1686 AlertDialog d = new BaseErrorDialog(mContext); 1687 d.getWindow().setType(WindowManager.LayoutParams.TYPE_SYSTEM_ERROR); 1688 d.setCancelable(false); 1689 d.setTitle(mContext.getText(R.string.android_system_label)); 1690 d.setMessage(mContext.getText(R.string.system_error_manufacturer)); 1691 d.setButton(DialogInterface.BUTTON_POSITIVE, mContext.getText(R.string.ok), 1692 obtainMessage(DISMISS_DIALOG_UI_MSG, d)); 1693 d.show(); 1694 } 1695 } break; 1696 case SHOW_COMPAT_MODE_DIALOG_UI_MSG: { 1697 synchronized (ActivityManagerService.this) { 1698 ActivityRecord ar = (ActivityRecord) msg.obj; 1699 if (mCompatModeDialog != null) { 1700 if (mCompatModeDialog.mAppInfo.packageName.equals( 1701 ar.info.applicationInfo.packageName)) { 1702 return; 1703 } 1704 mCompatModeDialog.dismiss(); 1705 mCompatModeDialog = null; 1706 } 1707 if (ar != null && false) { 1708 if (mCompatModePackages.getPackageAskCompatModeLocked( 1709 ar.packageName)) { 1710 int mode = mCompatModePackages.computeCompatModeLocked( 1711 ar.info.applicationInfo); 1712 if (mode == ActivityManager.COMPAT_MODE_DISABLED 1713 || mode == ActivityManager.COMPAT_MODE_ENABLED) { 1714 mCompatModeDialog = new CompatModeDialog( 1715 ActivityManagerService.this, mContext, 1716 ar.info.applicationInfo); 1717 mCompatModeDialog.show(); 1718 } 1719 } 1720 } 1721 } 1722 break; 1723 } 1724 case SHOW_UNSUPPORTED_DISPLAY_SIZE_DIALOG_MSG: { 1725 synchronized (ActivityManagerService.this) { 1726 final ActivityRecord ar = (ActivityRecord) msg.obj; 1727 if (mUnsupportedDisplaySizeDialog != null) { 1728 mUnsupportedDisplaySizeDialog.dismiss(); 1729 mUnsupportedDisplaySizeDialog = null; 1730 } 1731 if (ar != null && mCompatModePackages.getPackageNotifyUnsupportedZoomLocked( 1732 ar.packageName)) { 1733 // TODO(multi-display): Show dialog on appropriate display. 1734 mUnsupportedDisplaySizeDialog = new UnsupportedDisplaySizeDialog( 1735 ActivityManagerService.this, mContext, ar.info.applicationInfo); 1736 mUnsupportedDisplaySizeDialog.show(); 1737 } 1738 } 1739 break; 1740 } 1741 case START_USER_SWITCH_UI_MSG: { 1742 mUserController.showUserSwitchDialog((Pair<UserInfo, UserInfo>) msg.obj); 1743 break; 1744 } 1745 case DISMISS_DIALOG_UI_MSG: { 1746 final Dialog d = (Dialog) msg.obj; 1747 d.dismiss(); 1748 break; 1749 } 1750 case DISPATCH_PROCESSES_CHANGED_UI_MSG: { 1751 dispatchProcessesChanged(); 1752 break; 1753 } 1754 case DISPATCH_PROCESS_DIED_UI_MSG: { 1755 final int pid = msg.arg1; 1756 final int uid = msg.arg2; 1757 dispatchProcessDied(pid, uid); 1758 break; 1759 } 1760 case DISPATCH_UIDS_CHANGED_UI_MSG: { 1761 dispatchUidsChanged(); 1762 } break; 1763 } 1764 } 1765 } 1766 1767 final class MainHandler extends Handler { 1768 public MainHandler(Looper looper) { 1769 super(looper, null, true); 1770 } 1771 1772 @Override 1773 public void handleMessage(Message msg) { 1774 switch (msg.what) { 1775 case UPDATE_CONFIGURATION_MSG: { 1776 final ContentResolver resolver = mContext.getContentResolver(); 1777 Settings.System.putConfigurationForUser(resolver, (Configuration) msg.obj, 1778 msg.arg1); 1779 } break; 1780 case GC_BACKGROUND_PROCESSES_MSG: { 1781 synchronized (ActivityManagerService.this) { 1782 performAppGcsIfAppropriateLocked(); 1783 } 1784 } break; 1785 case SERVICE_TIMEOUT_MSG: { 1786 if (mDidDexOpt) { 1787 mDidDexOpt = false; 1788 Message nmsg = mHandler.obtainMessage(SERVICE_TIMEOUT_MSG); 1789 nmsg.obj = msg.obj; 1790 mHandler.sendMessageDelayed(nmsg, ActiveServices.SERVICE_TIMEOUT); 1791 return; 1792 } 1793 mServices.serviceTimeout((ProcessRecord)msg.obj); 1794 } break; 1795 case UPDATE_TIME_ZONE: { 1796 synchronized (ActivityManagerService.this) { 1797 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 1798 ProcessRecord r = mLruProcesses.get(i); 1799 if (r.thread != null) { 1800 try { 1801 r.thread.updateTimeZone(); 1802 } catch (RemoteException ex) { 1803 Slog.w(TAG, "Failed to update time zone for: " + r.info.processName); 1804 } 1805 } 1806 } 1807 } 1808 } break; 1809 case CLEAR_DNS_CACHE_MSG: { 1810 synchronized (ActivityManagerService.this) { 1811 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 1812 ProcessRecord r = mLruProcesses.get(i); 1813 if (r.thread != null) { 1814 try { 1815 r.thread.clearDnsCache(); 1816 } catch (RemoteException ex) { 1817 Slog.w(TAG, "Failed to clear dns cache for: " + r.info.processName); 1818 } 1819 } 1820 } 1821 } 1822 } break; 1823 case UPDATE_HTTP_PROXY_MSG: { 1824 ProxyInfo proxy = (ProxyInfo)msg.obj; 1825 String host = ""; 1826 String port = ""; 1827 String exclList = ""; 1828 Uri pacFileUrl = Uri.EMPTY; 1829 if (proxy != null) { 1830 host = proxy.getHost(); 1831 port = Integer.toString(proxy.getPort()); 1832 exclList = proxy.getExclusionListAsString(); 1833 pacFileUrl = proxy.getPacFileUrl(); 1834 } 1835 synchronized (ActivityManagerService.this) { 1836 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 1837 ProcessRecord r = mLruProcesses.get(i); 1838 if (r.thread != null) { 1839 try { 1840 r.thread.setHttpProxy(host, port, exclList, pacFileUrl); 1841 } catch (RemoteException ex) { 1842 Slog.w(TAG, "Failed to update http proxy for: " + 1843 r.info.processName); 1844 } 1845 } 1846 } 1847 } 1848 } break; 1849 case PROC_START_TIMEOUT_MSG: { 1850 if (mDidDexOpt) { 1851 mDidDexOpt = false; 1852 Message nmsg = mHandler.obtainMessage(PROC_START_TIMEOUT_MSG); 1853 nmsg.obj = msg.obj; 1854 mHandler.sendMessageDelayed(nmsg, PROC_START_TIMEOUT); 1855 return; 1856 } 1857 ProcessRecord app = (ProcessRecord)msg.obj; 1858 synchronized (ActivityManagerService.this) { 1859 processStartTimedOutLocked(app); 1860 } 1861 } break; 1862 case CONTENT_PROVIDER_PUBLISH_TIMEOUT_MSG: { 1863 ProcessRecord app = (ProcessRecord)msg.obj; 1864 synchronized (ActivityManagerService.this) { 1865 processContentProviderPublishTimedOutLocked(app); 1866 } 1867 } break; 1868 case DO_PENDING_ACTIVITY_LAUNCHES_MSG: { 1869 synchronized (ActivityManagerService.this) { 1870 mActivityStarter.doPendingActivityLaunchesLocked(true); 1871 } 1872 } break; 1873 case KILL_APPLICATION_MSG: { 1874 synchronized (ActivityManagerService.this) { 1875 final int appId = msg.arg1; 1876 final int userId = msg.arg2; 1877 Bundle bundle = (Bundle)msg.obj; 1878 String pkg = bundle.getString("pkg"); 1879 String reason = bundle.getString("reason"); 1880 forceStopPackageLocked(pkg, appId, false, false, true, false, 1881 false, userId, reason); 1882 } 1883 } break; 1884 case FINALIZE_PENDING_INTENT_MSG: { 1885 ((PendingIntentRecord)msg.obj).completeFinalize(); 1886 } break; 1887 case POST_HEAVY_NOTIFICATION_MSG: { 1888 INotificationManager inm = NotificationManager.getService(); 1889 if (inm == null) { 1890 return; 1891 } 1892 1893 ActivityRecord root = (ActivityRecord)msg.obj; 1894 ProcessRecord process = root.app; 1895 if (process == null) { 1896 return; 1897 } 1898 1899 try { 1900 Context context = mContext.createPackageContext(process.info.packageName, 0); 1901 String text = mContext.getString(R.string.heavy_weight_notification, 1902 context.getApplicationInfo().loadLabel(context.getPackageManager())); 1903 Notification notification = new Notification.Builder(context) 1904 .setSmallIcon(com.android.internal.R.drawable.stat_sys_adb) 1905 .setWhen(0) 1906 .setOngoing(true) 1907 .setTicker(text) 1908 .setColor(mContext.getColor( 1909 com.android.internal.R.color.system_notification_accent_color)) 1910 .setContentTitle(text) 1911 .setContentText( 1912 mContext.getText(R.string.heavy_weight_notification_detail)) 1913 .setContentIntent(PendingIntent.getActivityAsUser(mContext, 0, 1914 root.intent, PendingIntent.FLAG_CANCEL_CURRENT, null, 1915 new UserHandle(root.userId))) 1916 .build(); 1917 try { 1918 int[] outId = new int[1]; 1919 inm.enqueueNotificationWithTag("android", "android", null, 1920 R.string.heavy_weight_notification, 1921 notification, outId, root.userId); 1922 } catch (RuntimeException e) { 1923 Slog.w(ActivityManagerService.TAG, 1924 "Error showing notification for heavy-weight app", e); 1925 } catch (RemoteException e) { 1926 } 1927 } catch (NameNotFoundException e) { 1928 Slog.w(TAG, "Unable to create context for heavy notification", e); 1929 } 1930 } break; 1931 case CANCEL_HEAVY_NOTIFICATION_MSG: { 1932 INotificationManager inm = NotificationManager.getService(); 1933 if (inm == null) { 1934 return; 1935 } 1936 try { 1937 inm.cancelNotificationWithTag("android", null, 1938 R.string.heavy_weight_notification, msg.arg1); 1939 } catch (RuntimeException e) { 1940 Slog.w(ActivityManagerService.TAG, 1941 "Error canceling notification for service", e); 1942 } catch (RemoteException e) { 1943 } 1944 } break; 1945 case CHECK_EXCESSIVE_WAKE_LOCKS_MSG: { 1946 synchronized (ActivityManagerService.this) { 1947 checkExcessivePowerUsageLocked(true); 1948 removeMessages(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 1949 Message nmsg = obtainMessage(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 1950 sendMessageDelayed(nmsg, POWER_CHECK_DELAY); 1951 } 1952 } break; 1953 case REPORT_MEM_USAGE_MSG: { 1954 final ArrayList<ProcessMemInfo> memInfos = (ArrayList<ProcessMemInfo>)msg.obj; 1955 Thread thread = new Thread() { 1956 @Override public void run() { 1957 reportMemUsage(memInfos); 1958 } 1959 }; 1960 thread.start(); 1961 break; 1962 } 1963 case START_USER_SWITCH_FG_MSG: { 1964 mUserController.startUserInForeground(msg.arg1); 1965 break; 1966 } 1967 case REPORT_USER_SWITCH_MSG: { 1968 mUserController.dispatchUserSwitch((UserState) msg.obj, msg.arg1, msg.arg2); 1969 break; 1970 } 1971 case CONTINUE_USER_SWITCH_MSG: { 1972 mUserController.continueUserSwitch((UserState) msg.obj, msg.arg1, msg.arg2); 1973 break; 1974 } 1975 case USER_SWITCH_TIMEOUT_MSG: { 1976 mUserController.timeoutUserSwitch((UserState) msg.obj, msg.arg1, msg.arg2); 1977 break; 1978 } 1979 case IMMERSIVE_MODE_LOCK_MSG: { 1980 final boolean nextState = (msg.arg1 != 0); 1981 if (mUpdateLock.isHeld() != nextState) { 1982 if (DEBUG_IMMERSIVE) Slog.d(TAG_IMMERSIVE, 1983 "Applying new update lock state '" + nextState 1984 + "' for " + (ActivityRecord)msg.obj); 1985 if (nextState) { 1986 mUpdateLock.acquire(); 1987 } else { 1988 mUpdateLock.release(); 1989 } 1990 } 1991 break; 1992 } 1993 case PERSIST_URI_GRANTS_MSG: { 1994 writeGrantedUriPermissions(); 1995 break; 1996 } 1997 case REQUEST_ALL_PSS_MSG: { 1998 synchronized (ActivityManagerService.this) { 1999 requestPssAllProcsLocked(SystemClock.uptimeMillis(), true, false); 2000 } 2001 break; 2002 } 2003 case START_PROFILES_MSG: { 2004 synchronized (ActivityManagerService.this) { 2005 mUserController.startProfilesLocked(); 2006 } 2007 break; 2008 } 2009 case UPDATE_TIME: { 2010 synchronized (ActivityManagerService.this) { 2011 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 2012 ProcessRecord r = mLruProcesses.get(i); 2013 if (r.thread != null) { 2014 try { 2015 r.thread.updateTimePrefs(msg.arg1 == 0 ? false : true); 2016 } catch (RemoteException ex) { 2017 Slog.w(TAG, "Failed to update preferences for: " + r.info.processName); 2018 } 2019 } 2020 } 2021 } 2022 break; 2023 } 2024 case SYSTEM_USER_START_MSG: { 2025 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_USER_RUNNING_START, 2026 Integer.toString(msg.arg1), msg.arg1); 2027 mSystemServiceManager.startUser(msg.arg1); 2028 break; 2029 } 2030 case SYSTEM_USER_UNLOCK_MSG: { 2031 final int userId = msg.arg1; 2032 mSystemServiceManager.unlockUser(userId); 2033 synchronized (ActivityManagerService.this) { 2034 mRecentTasks.loadUserRecentsLocked(userId); 2035 } 2036 if (userId == UserHandle.USER_SYSTEM) { 2037 startPersistentApps(PackageManager.MATCH_DIRECT_BOOT_UNAWARE); 2038 } 2039 installEncryptionUnawareProviders(userId); 2040 mUserController.finishUserUnlocked((UserState) msg.obj); 2041 break; 2042 } 2043 case SYSTEM_USER_CURRENT_MSG: { 2044 mBatteryStatsService.noteEvent( 2045 BatteryStats.HistoryItem.EVENT_USER_FOREGROUND_FINISH, 2046 Integer.toString(msg.arg2), msg.arg2); 2047 mBatteryStatsService.noteEvent( 2048 BatteryStats.HistoryItem.EVENT_USER_FOREGROUND_START, 2049 Integer.toString(msg.arg1), msg.arg1); 2050 mSystemServiceManager.switchUser(msg.arg1); 2051 break; 2052 } 2053 case ENTER_ANIMATION_COMPLETE_MSG: { 2054 synchronized (ActivityManagerService.this) { 2055 ActivityRecord r = ActivityRecord.forTokenLocked((IBinder) msg.obj); 2056 if (r != null && r.app != null && r.app.thread != null) { 2057 try { 2058 r.app.thread.scheduleEnterAnimationComplete(r.appToken); 2059 } catch (RemoteException e) { 2060 } 2061 } 2062 } 2063 break; 2064 } 2065 case FINISH_BOOTING_MSG: { 2066 if (msg.arg1 != 0) { 2067 Trace.traceBegin(Trace.TRACE_TAG_ACTIVITY_MANAGER, "FinishBooting"); 2068 finishBooting(); 2069 Trace.traceEnd(Trace.TRACE_TAG_ACTIVITY_MANAGER); 2070 } 2071 if (msg.arg2 != 0) { 2072 enableScreenAfterBoot(); 2073 } 2074 break; 2075 } 2076 case SEND_LOCALE_TO_MOUNT_DAEMON_MSG: { 2077 try { 2078 Locale l = (Locale) msg.obj; 2079 IBinder service = ServiceManager.getService("mount"); 2080 IMountService mountService = IMountService.Stub.asInterface(service); 2081 Log.d(TAG, "Storing locale " + l.toLanguageTag() + " for decryption UI"); 2082 mountService.setField(StorageManager.SYSTEM_LOCALE_KEY, l.toLanguageTag()); 2083 } catch (RemoteException e) { 2084 Log.e(TAG, "Error storing locale for decryption UI", e); 2085 } 2086 break; 2087 } 2088 case NOTIFY_CLEARTEXT_NETWORK_MSG: { 2089 final int uid = msg.arg1; 2090 final byte[] firstPacket = (byte[]) msg.obj; 2091 2092 synchronized (mPidsSelfLocked) { 2093 for (int i = 0; i < mPidsSelfLocked.size(); i++) { 2094 final ProcessRecord p = mPidsSelfLocked.valueAt(i); 2095 if (p.uid == uid) { 2096 try { 2097 p.thread.notifyCleartextNetwork(firstPacket); 2098 } catch (RemoteException ignored) { 2099 } 2100 } 2101 } 2102 } 2103 break; 2104 } 2105 case POST_DUMP_HEAP_NOTIFICATION_MSG: { 2106 final String procName; 2107 final int uid; 2108 final long memLimit; 2109 final String reportPackage; 2110 synchronized (ActivityManagerService.this) { 2111 procName = mMemWatchDumpProcName; 2112 uid = mMemWatchDumpUid; 2113 Pair<Long, String> val = mMemWatchProcesses.get(procName, uid); 2114 if (val == null) { 2115 val = mMemWatchProcesses.get(procName, 0); 2116 } 2117 if (val != null) { 2118 memLimit = val.first; 2119 reportPackage = val.second; 2120 } else { 2121 memLimit = 0; 2122 reportPackage = null; 2123 } 2124 } 2125 if (procName == null) { 2126 return; 2127 } 2128 2129 if (DEBUG_PSS) Slog.d(TAG_PSS, 2130 "Showing dump heap notification from " + procName + "/" + uid); 2131 2132 INotificationManager inm = NotificationManager.getService(); 2133 if (inm == null) { 2134 return; 2135 } 2136 2137 String text = mContext.getString(R.string.dump_heap_notification, procName); 2138 2139 2140 Intent deleteIntent = new Intent(); 2141 deleteIntent.setAction(DumpHeapActivity.ACTION_DELETE_DUMPHEAP); 2142 Intent intent = new Intent(); 2143 intent.setClassName("android", DumpHeapActivity.class.getName()); 2144 intent.putExtra(DumpHeapActivity.KEY_PROCESS, procName); 2145 intent.putExtra(DumpHeapActivity.KEY_SIZE, memLimit); 2146 if (reportPackage != null) { 2147 intent.putExtra(DumpHeapActivity.KEY_DIRECT_LAUNCH, reportPackage); 2148 } 2149 int userId = UserHandle.getUserId(uid); 2150 Notification notification = new Notification.Builder(mContext) 2151 .setSmallIcon(com.android.internal.R.drawable.stat_sys_adb) 2152 .setWhen(0) 2153 .setOngoing(true) 2154 .setAutoCancel(true) 2155 .setTicker(text) 2156 .setColor(mContext.getColor( 2157 com.android.internal.R.color.system_notification_accent_color)) 2158 .setContentTitle(text) 2159 .setContentText( 2160 mContext.getText(R.string.dump_heap_notification_detail)) 2161 .setContentIntent(PendingIntent.getActivityAsUser(mContext, 0, 2162 intent, PendingIntent.FLAG_CANCEL_CURRENT, null, 2163 new UserHandle(userId))) 2164 .setDeleteIntent(PendingIntent.getBroadcastAsUser(mContext, 0, 2165 deleteIntent, 0, UserHandle.SYSTEM)) 2166 .build(); 2167 2168 try { 2169 int[] outId = new int[1]; 2170 inm.enqueueNotificationWithTag("android", "android", null, 2171 R.string.dump_heap_notification, 2172 notification, outId, userId); 2173 } catch (RuntimeException e) { 2174 Slog.w(ActivityManagerService.TAG, 2175 "Error showing notification for dump heap", e); 2176 } catch (RemoteException e) { 2177 } 2178 } break; 2179 case DELETE_DUMPHEAP_MSG: { 2180 revokeUriPermission(ActivityThread.currentActivityThread().getApplicationThread(), 2181 DumpHeapActivity.JAVA_URI, 2182 Intent.FLAG_GRANT_READ_URI_PERMISSION 2183 | Intent.FLAG_GRANT_WRITE_URI_PERMISSION, 2184 UserHandle.myUserId()); 2185 synchronized (ActivityManagerService.this) { 2186 mMemWatchDumpFile = null; 2187 mMemWatchDumpProcName = null; 2188 mMemWatchDumpPid = -1; 2189 mMemWatchDumpUid = -1; 2190 } 2191 } break; 2192 case FOREGROUND_PROFILE_CHANGED_MSG: { 2193 mUserController.dispatchForegroundProfileChanged(msg.arg1); 2194 } break; 2195 case REPORT_TIME_TRACKER_MSG: { 2196 AppTimeTracker tracker = (AppTimeTracker)msg.obj; 2197 tracker.deliverResult(mContext); 2198 } break; 2199 case REPORT_USER_SWITCH_COMPLETE_MSG: { 2200 mUserController.dispatchUserSwitchComplete(msg.arg1); 2201 } break; 2202 case REPORT_LOCKED_BOOT_COMPLETE_MSG: { 2203 mUserController.dispatchLockedBootComplete(msg.arg1); 2204 } break; 2205 case SHUTDOWN_UI_AUTOMATION_CONNECTION_MSG: { 2206 IUiAutomationConnection connection = (IUiAutomationConnection) msg.obj; 2207 try { 2208 connection.shutdown(); 2209 } catch (RemoteException e) { 2210 Slog.w(TAG, "Error shutting down UiAutomationConnection"); 2211 } 2212 // Only a UiAutomation can set this flag and now that 2213 // it is finished we make sure it is reset to its default. 2214 mUserIsMonkey = false; 2215 } break; 2216 case IDLE_UIDS_MSG: { 2217 idleUids(); 2218 } break; 2219 case VR_MODE_CHANGE_MSG: { 2220 VrManagerInternal vrService = LocalServices.getService(VrManagerInternal.class); 2221 if (vrService == null) { 2222 break; 2223 } 2224 final ActivityRecord r = (ActivityRecord) msg.obj; 2225 boolean vrMode; 2226 ComponentName requestedPackage; 2227 ComponentName callingPackage; 2228 int userId; 2229 synchronized (ActivityManagerService.this) { 2230 vrMode = r.requestedVrComponent != null; 2231 requestedPackage = r.requestedVrComponent; 2232 userId = r.userId; 2233 callingPackage = r.info.getComponentName(); 2234 if (mInVrMode != vrMode) { 2235 mInVrMode = vrMode; 2236 mShowDialogs = shouldShowDialogs(getGlobalConfiguration(), mInVrMode); 2237 if (r.app != null) { 2238 ProcessRecord proc = r.app; 2239 if (proc.vrThreadTid > 0) { 2240 if (proc.curSchedGroup == ProcessList.SCHED_GROUP_TOP_APP) { 2241 try { 2242 if (mInVrMode == true) { 2243 Process.setThreadScheduler(proc.vrThreadTid, 2244 Process.SCHED_FIFO | Process.SCHED_RESET_ON_FORK, 1); 2245 } else { 2246 Process.setThreadScheduler(proc.vrThreadTid, 2247 Process.SCHED_OTHER, 0); 2248 } 2249 } catch (IllegalArgumentException e) { 2250 Slog.w(TAG, "Failed to set scheduling policy, thread does" 2251 + " not exist:\n" + e); 2252 } 2253 } 2254 } 2255 } 2256 } 2257 } 2258 vrService.setVrMode(vrMode, requestedPackage, userId, callingPackage); 2259 } break; 2260 case VR_MODE_APPLY_IF_NEEDED_MSG: { 2261 final ActivityRecord r = (ActivityRecord) msg.obj; 2262 final boolean needsVrMode = r != null && r.requestedVrComponent != null; 2263 if (needsVrMode) { 2264 applyVrMode(msg.arg1 == 1, r.requestedVrComponent, r.userId, 2265 r.info.getComponentName(), false); 2266 } 2267 } break; 2268 case HANDLE_TRUST_STORAGE_UPDATE_MSG: { 2269 synchronized (ActivityManagerService.this) { 2270 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 2271 ProcessRecord r = mLruProcesses.get(i); 2272 if (r.thread != null) { 2273 try { 2274 r.thread.handleTrustStorageUpdate(); 2275 } catch (RemoteException ex) { 2276 Slog.w(TAG, "Failed to handle trust storage update for: " + 2277 r.info.processName); 2278 } 2279 } 2280 } 2281 } 2282 } break; 2283 } 2284 } 2285 }; 2286 2287 static final int COLLECT_PSS_BG_MSG = 1; 2288 2289 final Handler mBgHandler = new Handler(BackgroundThread.getHandler().getLooper()) { 2290 @Override 2291 public void handleMessage(Message msg) { 2292 switch (msg.what) { 2293 case COLLECT_PSS_BG_MSG: { 2294 long start = SystemClock.uptimeMillis(); 2295 MemInfoReader memInfo = null; 2296 synchronized (ActivityManagerService.this) { 2297 if (mFullPssPending) { 2298 mFullPssPending = false; 2299 memInfo = new MemInfoReader(); 2300 } 2301 } 2302 if (memInfo != null) { 2303 updateCpuStatsNow(); 2304 long nativeTotalPss = 0; 2305 final List<ProcessCpuTracker.Stats> stats; 2306 synchronized (mProcessCpuTracker) { 2307 stats = mProcessCpuTracker.getStats( (st)-> { 2308 return st.vsize > 0 && st.uid < Process.FIRST_APPLICATION_UID; 2309 }); 2310 } 2311 final int N = stats.size(); 2312 for (int j = 0; j < N; j++) { 2313 synchronized (mPidsSelfLocked) { 2314 if (mPidsSelfLocked.indexOfKey(stats.get(j).pid) >= 0) { 2315 // This is one of our own processes; skip it. 2316 continue; 2317 } 2318 } 2319 nativeTotalPss += Debug.getPss(stats.get(j).pid, null, null); 2320 } 2321 memInfo.readMemInfo(); 2322 synchronized (ActivityManagerService.this) { 2323 if (DEBUG_PSS) Slog.d(TAG_PSS, "Collected native and kernel memory in " 2324 + (SystemClock.uptimeMillis()-start) + "ms"); 2325 final long cachedKb = memInfo.getCachedSizeKb(); 2326 final long freeKb = memInfo.getFreeSizeKb(); 2327 final long zramKb = memInfo.getZramTotalSizeKb(); 2328 final long kernelKb = memInfo.getKernelUsedSizeKb(); 2329 EventLogTags.writeAmMeminfo(cachedKb*1024, freeKb*1024, zramKb*1024, 2330 kernelKb*1024, nativeTotalPss*1024); 2331 mProcessStats.addSysMemUsageLocked(cachedKb, freeKb, zramKb, kernelKb, 2332 nativeTotalPss); 2333 } 2334 } 2335 2336 int num = 0; 2337 long[] tmp = new long[2]; 2338 do { 2339 ProcessRecord proc; 2340 int procState; 2341 int pid; 2342 long lastPssTime; 2343 synchronized (ActivityManagerService.this) { 2344 if (mPendingPssProcesses.size() <= 0) { 2345 if (mTestPssMode || DEBUG_PSS) Slog.d(TAG_PSS, 2346 "Collected PSS of " + num + " processes in " 2347 + (SystemClock.uptimeMillis() - start) + "ms"); 2348 mPendingPssProcesses.clear(); 2349 return; 2350 } 2351 proc = mPendingPssProcesses.remove(0); 2352 procState = proc.pssProcState; 2353 lastPssTime = proc.lastPssTime; 2354 if (proc.thread != null && procState == proc.setProcState 2355 && (lastPssTime+ProcessList.PSS_SAFE_TIME_FROM_STATE_CHANGE) 2356 < SystemClock.uptimeMillis()) { 2357 pid = proc.pid; 2358 } else { 2359 proc = null; 2360 pid = 0; 2361 } 2362 } 2363 if (proc != null) { 2364 long pss = Debug.getPss(pid, tmp, null); 2365 synchronized (ActivityManagerService.this) { 2366 if (pss != 0 && proc.thread != null && proc.setProcState == procState 2367 && proc.pid == pid && proc.lastPssTime == lastPssTime) { 2368 num++; 2369 recordPssSampleLocked(proc, procState, pss, tmp[0], tmp[1], 2370 SystemClock.uptimeMillis()); 2371 } 2372 } 2373 } 2374 } while (true); 2375 } 2376 } 2377 } 2378 }; 2379 2380 public void setSystemProcess() { 2381 try { 2382 ServiceManager.addService(Context.ACTIVITY_SERVICE, this, true); 2383 ServiceManager.addService(ProcessStats.SERVICE_NAME, mProcessStats); 2384 ServiceManager.addService("meminfo", new MemBinder(this)); 2385 ServiceManager.addService("gfxinfo", new GraphicsBinder(this)); 2386 ServiceManager.addService("dbinfo", new DbBinder(this)); 2387 if (MONITOR_CPU_USAGE) { 2388 ServiceManager.addService("cpuinfo", new CpuBinder(this)); 2389 } 2390 ServiceManager.addService("permission", new PermissionController(this)); 2391 ServiceManager.addService("processinfo", new ProcessInfoService(this)); 2392 2393 ApplicationInfo info = mContext.getPackageManager().getApplicationInfo( 2394 "android", STOCK_PM_FLAGS | MATCH_SYSTEM_ONLY); 2395 mSystemThread.installSystemApplicationInfo(info, getClass().getClassLoader()); 2396 2397 synchronized (this) { 2398 ProcessRecord app = newProcessRecordLocked(info, info.processName, false, 0); 2399 app.persistent = true; 2400 app.pid = MY_PID; 2401 app.maxAdj = ProcessList.SYSTEM_ADJ; 2402 app.makeActive(mSystemThread.getApplicationThread(), mProcessStats); 2403 synchronized (mPidsSelfLocked) { 2404 mPidsSelfLocked.put(app.pid, app); 2405 } 2406 updateLruProcessLocked(app, false, null); 2407 updateOomAdjLocked(); 2408 } 2409 } catch (PackageManager.NameNotFoundException e) { 2410 throw new RuntimeException( 2411 "Unable to find android system package", e); 2412 } 2413 } 2414 2415 public void setWindowManager(WindowManagerService wm) { 2416 mWindowManager = wm; 2417 mStackSupervisor.setWindowManager(wm); 2418 mActivityStarter.setWindowManager(wm); 2419 } 2420 2421 public void setUsageStatsManager(UsageStatsManagerInternal usageStatsManager) { 2422 mUsageStatsService = usageStatsManager; 2423 } 2424 2425 public void startObservingNativeCrashes() { 2426 final NativeCrashListener ncl = new NativeCrashListener(this); 2427 ncl.start(); 2428 } 2429 2430 public IAppOpsService getAppOpsService() { 2431 return mAppOpsService; 2432 } 2433 2434 static class MemBinder extends Binder { 2435 ActivityManagerService mActivityManagerService; 2436 MemBinder(ActivityManagerService activityManagerService) { 2437 mActivityManagerService = activityManagerService; 2438 } 2439 2440 @Override 2441 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 2442 if (mActivityManagerService.checkCallingPermission(android.Manifest.permission.DUMP) 2443 != PackageManager.PERMISSION_GRANTED) { 2444 pw.println("Permission Denial: can't dump meminfo from from pid=" 2445 + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid() 2446 + " without permission " + android.Manifest.permission.DUMP); 2447 return; 2448 } 2449 2450 mActivityManagerService.dumpApplicationMemoryUsage(fd, pw, " ", args, false, null); 2451 } 2452 } 2453 2454 static class GraphicsBinder extends Binder { 2455 ActivityManagerService mActivityManagerService; 2456 GraphicsBinder(ActivityManagerService activityManagerService) { 2457 mActivityManagerService = activityManagerService; 2458 } 2459 2460 @Override 2461 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 2462 if (mActivityManagerService.checkCallingPermission(android.Manifest.permission.DUMP) 2463 != PackageManager.PERMISSION_GRANTED) { 2464 pw.println("Permission Denial: can't dump gfxinfo from from pid=" 2465 + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid() 2466 + " without permission " + android.Manifest.permission.DUMP); 2467 return; 2468 } 2469 2470 mActivityManagerService.dumpGraphicsHardwareUsage(fd, pw, args); 2471 } 2472 } 2473 2474 static class DbBinder extends Binder { 2475 ActivityManagerService mActivityManagerService; 2476 DbBinder(ActivityManagerService activityManagerService) { 2477 mActivityManagerService = activityManagerService; 2478 } 2479 2480 @Override 2481 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 2482 if (mActivityManagerService.checkCallingPermission(android.Manifest.permission.DUMP) 2483 != PackageManager.PERMISSION_GRANTED) { 2484 pw.println("Permission Denial: can't dump dbinfo from from pid=" 2485 + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid() 2486 + " without permission " + android.Manifest.permission.DUMP); 2487 return; 2488 } 2489 2490 mActivityManagerService.dumpDbInfo(fd, pw, args); 2491 } 2492 } 2493 2494 static class CpuBinder extends Binder { 2495 ActivityManagerService mActivityManagerService; 2496 CpuBinder(ActivityManagerService activityManagerService) { 2497 mActivityManagerService = activityManagerService; 2498 } 2499 2500 @Override 2501 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 2502 if (mActivityManagerService.checkCallingPermission(android.Manifest.permission.DUMP) 2503 != PackageManager.PERMISSION_GRANTED) { 2504 pw.println("Permission Denial: can't dump cpuinfo from from pid=" 2505 + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid() 2506 + " without permission " + android.Manifest.permission.DUMP); 2507 return; 2508 } 2509 2510 synchronized (mActivityManagerService.mProcessCpuTracker) { 2511 pw.print(mActivityManagerService.mProcessCpuTracker.printCurrentLoad()); 2512 pw.print(mActivityManagerService.mProcessCpuTracker.printCurrentState( 2513 SystemClock.uptimeMillis())); 2514 } 2515 } 2516 } 2517 2518 public static final class Lifecycle extends SystemService { 2519 private final ActivityManagerService mService; 2520 2521 public Lifecycle(Context context) { 2522 super(context); 2523 mService = new ActivityManagerService(context); 2524 } 2525 2526 @Override 2527 public void onStart() { 2528 mService.start(); 2529 } 2530 2531 public ActivityManagerService getService() { 2532 return mService; 2533 } 2534 } 2535 2536 // Note: This method is invoked on the main thread but may need to attach various 2537 // handlers to other threads. So take care to be explicit about the looper. 2538 public ActivityManagerService(Context systemContext) { 2539 mContext = systemContext; 2540 mFactoryTest = FactoryTest.getMode(); 2541 mSystemThread = ActivityThread.currentActivityThread(); 2542 2543 Slog.i(TAG, "Memory class: " + ActivityManager.staticGetMemoryClass()); 2544 2545 mPermissionReviewRequired = mContext.getResources().getBoolean( 2546 com.android.internal.R.bool.config_permissionReviewRequired); 2547 2548 mHandlerThread = new ServiceThread(TAG, 2549 android.os.Process.THREAD_PRIORITY_FOREGROUND, false /*allowIo*/); 2550 mHandlerThread.start(); 2551 mHandler = new MainHandler(mHandlerThread.getLooper()); 2552 mUiHandler = new UiHandler(); 2553 2554 /* static; one-time init here */ 2555 if (sKillHandler == null) { 2556 sKillThread = new ServiceThread(TAG + ":kill", 2557 android.os.Process.THREAD_PRIORITY_BACKGROUND, true /* allowIo */); 2558 sKillThread.start(); 2559 sKillHandler = new KillHandler(sKillThread.getLooper()); 2560 } 2561 2562 mFgBroadcastQueue = new BroadcastQueue(this, mHandler, 2563 "foreground", BROADCAST_FG_TIMEOUT, false); 2564 mBgBroadcastQueue = new BroadcastQueue(this, mHandler, 2565 "background", BROADCAST_BG_TIMEOUT, true); 2566 mBroadcastQueues[0] = mFgBroadcastQueue; 2567 mBroadcastQueues[1] = mBgBroadcastQueue; 2568 2569 mServices = new ActiveServices(this); 2570 mProviderMap = new ProviderMap(this); 2571 mAppErrors = new AppErrors(mContext, this); 2572 2573 // TODO: Move creation of battery stats service outside of activity manager service. 2574 File dataDir = Environment.getDataDirectory(); 2575 File systemDir = new File(dataDir, "system"); 2576 systemDir.mkdirs(); 2577 mBatteryStatsService = new BatteryStatsService(systemDir, mHandler); 2578 mBatteryStatsService.getActiveStatistics().readLocked(); 2579 mBatteryStatsService.scheduleWriteToDisk(); 2580 mOnBattery = DEBUG_POWER ? true 2581 : mBatteryStatsService.getActiveStatistics().getIsOnBattery(); 2582 mBatteryStatsService.getActiveStatistics().setCallback(this); 2583 2584 mProcessStats = new ProcessStatsService(this, new File(systemDir, "procstats")); 2585 2586 mAppOpsService = new AppOpsService(new File(systemDir, "appops.xml"), mHandler); 2587 mAppOpsService.startWatchingMode(AppOpsManager.OP_RUN_IN_BACKGROUND, null, 2588 new IAppOpsCallback.Stub() { 2589 @Override public void opChanged(int op, int uid, String packageName) { 2590 if (op == AppOpsManager.OP_RUN_IN_BACKGROUND && packageName != null) { 2591 if (mAppOpsService.checkOperation(op, uid, packageName) 2592 != AppOpsManager.MODE_ALLOWED) { 2593 runInBackgroundDisabled(uid); 2594 } 2595 } 2596 } 2597 }); 2598 2599 mGrantFile = new AtomicFile(new File(systemDir, "urigrants.xml")); 2600 2601 mUserController = new UserController(this); 2602 2603 GL_ES_VERSION = SystemProperties.getInt("ro.opengles.version", 2604 ConfigurationInfo.GL_ES_VERSION_UNDEFINED); 2605 2606 if (SystemProperties.getInt("sys.use_fifo_ui", 0) != 0) { 2607 mUseFifoUiScheduling = true; 2608 } 2609 2610 mTrackingAssociations = "1".equals(SystemProperties.get("debug.track-associations")); 2611 2612 mTempConfig.setToDefaults(); 2613 mTempConfig.setLocales(LocaleList.getDefault()); 2614 mConfigurationSeq = mTempConfig.seq = 1; 2615 2616 mProcessCpuTracker.init(); 2617 2618 mStackSupervisor = new ActivityStackSupervisor(this); 2619 mStackSupervisor.onConfigurationChanged(mTempConfig); 2620 mKeyguardController = mStackSupervisor.mKeyguardController; 2621 mCompatModePackages = new CompatModePackages(this, systemDir, mHandler); 2622 mIntentFirewall = new IntentFirewall(new IntentFirewallInterface(), mHandler); 2623 mTaskChangeNotificationController = 2624 new TaskChangeNotificationController(this, mStackSupervisor, mHandler); 2625 mActivityStarter = new ActivityStarter(this, mStackSupervisor); 2626 mRecentTasks = new RecentTasks(this, mStackSupervisor); 2627 2628 mProcessCpuThread = new Thread("CpuTracker") { 2629 @Override 2630 public void run() { 2631 while (true) { 2632 try { 2633 try { 2634 synchronized(this) { 2635 final long now = SystemClock.uptimeMillis(); 2636 long nextCpuDelay = (mLastCpuTime.get()+MONITOR_CPU_MAX_TIME)-now; 2637 long nextWriteDelay = (mLastWriteTime+BATTERY_STATS_TIME)-now; 2638 //Slog.i(TAG, "Cpu delay=" + nextCpuDelay 2639 // + ", write delay=" + nextWriteDelay); 2640 if (nextWriteDelay < nextCpuDelay) { 2641 nextCpuDelay = nextWriteDelay; 2642 } 2643 if (nextCpuDelay > 0) { 2644 mProcessCpuMutexFree.set(true); 2645 this.wait(nextCpuDelay); 2646 } 2647 } 2648 } catch (InterruptedException e) { 2649 } 2650 updateCpuStatsNow(); 2651 } catch (Exception e) { 2652 Slog.e(TAG, "Unexpected exception collecting process stats", e); 2653 } 2654 } 2655 } 2656 }; 2657 2658 Watchdog.getInstance().addMonitor(this); 2659 Watchdog.getInstance().addThread(mHandler); 2660 } 2661 2662 public void setSystemServiceManager(SystemServiceManager mgr) { 2663 mSystemServiceManager = mgr; 2664 } 2665 2666 public void setInstaller(Installer installer) { 2667 mInstaller = installer; 2668 } 2669 2670 private void start() { 2671 Process.removeAllProcessGroups(); 2672 mProcessCpuThread.start(); 2673 2674 mBatteryStatsService.publish(mContext); 2675 mAppOpsService.publish(mContext); 2676 Slog.d("AppOps", "AppOpsService published"); 2677 LocalServices.addService(ActivityManagerInternal.class, new LocalService()); 2678 } 2679 2680 void onUserStoppedLocked(int userId) { 2681 mRecentTasks.unloadUserDataFromMemoryLocked(userId); 2682 } 2683 2684 public void initPowerManagement() { 2685 mStackSupervisor.initPowerManagement(); 2686 mBatteryStatsService.initPowerManagement(); 2687 mLocalPowerManager = LocalServices.getService(PowerManagerInternal.class); 2688 PowerManager pm = (PowerManager)mContext.getSystemService(Context.POWER_SERVICE); 2689 mVoiceWakeLock = pm.newWakeLock(PowerManager.PARTIAL_WAKE_LOCK, "*voice*"); 2690 mVoiceWakeLock.setReferenceCounted(false); 2691 } 2692 2693 @Override 2694 public boolean onTransact(int code, Parcel data, Parcel reply, int flags) 2695 throws RemoteException { 2696 if (code == SYSPROPS_TRANSACTION) { 2697 // We need to tell all apps about the system property change. 2698 ArrayList<IBinder> procs = new ArrayList<IBinder>(); 2699 synchronized(this) { 2700 final int NP = mProcessNames.getMap().size(); 2701 for (int ip=0; ip<NP; ip++) { 2702 SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 2703 final int NA = apps.size(); 2704 for (int ia=0; ia<NA; ia++) { 2705 ProcessRecord app = apps.valueAt(ia); 2706 if (app.thread != null) { 2707 procs.add(app.thread.asBinder()); 2708 } 2709 } 2710 } 2711 } 2712 2713 int N = procs.size(); 2714 for (int i=0; i<N; i++) { 2715 Parcel data2 = Parcel.obtain(); 2716 try { 2717 procs.get(i).transact(IBinder.SYSPROPS_TRANSACTION, data2, null, 0); 2718 } catch (RemoteException e) { 2719 } 2720 data2.recycle(); 2721 } 2722 } 2723 try { 2724 return super.onTransact(code, data, reply, flags); 2725 } catch (RuntimeException e) { 2726 // The activity manager only throws security exceptions, so let's 2727 // log all others. 2728 if (!(e instanceof SecurityException)) { 2729 Slog.wtf(TAG, "Activity Manager Crash", e); 2730 } 2731 throw e; 2732 } 2733 } 2734 2735 void updateCpuStats() { 2736 final long now = SystemClock.uptimeMillis(); 2737 if (mLastCpuTime.get() >= now - MONITOR_CPU_MIN_TIME) { 2738 return; 2739 } 2740 if (mProcessCpuMutexFree.compareAndSet(true, false)) { 2741 synchronized (mProcessCpuThread) { 2742 mProcessCpuThread.notify(); 2743 } 2744 } 2745 } 2746 2747 void updateCpuStatsNow() { 2748 synchronized (mProcessCpuTracker) { 2749 mProcessCpuMutexFree.set(false); 2750 final long now = SystemClock.uptimeMillis(); 2751 boolean haveNewCpuStats = false; 2752 2753 if (MONITOR_CPU_USAGE && 2754 mLastCpuTime.get() < (now-MONITOR_CPU_MIN_TIME)) { 2755 mLastCpuTime.set(now); 2756 mProcessCpuTracker.update(); 2757 if (mProcessCpuTracker.hasGoodLastStats()) { 2758 haveNewCpuStats = true; 2759 //Slog.i(TAG, mProcessCpu.printCurrentState()); 2760 //Slog.i(TAG, "Total CPU usage: " 2761 // + mProcessCpu.getTotalCpuPercent() + "%"); 2762 2763 // Slog the cpu usage if the property is set. 2764 if ("true".equals(SystemProperties.get("events.cpu"))) { 2765 int user = mProcessCpuTracker.getLastUserTime(); 2766 int system = mProcessCpuTracker.getLastSystemTime(); 2767 int iowait = mProcessCpuTracker.getLastIoWaitTime(); 2768 int irq = mProcessCpuTracker.getLastIrqTime(); 2769 int softIrq = mProcessCpuTracker.getLastSoftIrqTime(); 2770 int idle = mProcessCpuTracker.getLastIdleTime(); 2771 2772 int total = user + system + iowait + irq + softIrq + idle; 2773 if (total == 0) total = 1; 2774 2775 EventLog.writeEvent(EventLogTags.CPU, 2776 ((user+system+iowait+irq+softIrq) * 100) / total, 2777 (user * 100) / total, 2778 (system * 100) / total, 2779 (iowait * 100) / total, 2780 (irq * 100) / total, 2781 (softIrq * 100) / total); 2782 } 2783 } 2784 } 2785 2786 final BatteryStatsImpl bstats = mBatteryStatsService.getActiveStatistics(); 2787 synchronized(bstats) { 2788 synchronized(mPidsSelfLocked) { 2789 if (haveNewCpuStats) { 2790 if (bstats.startAddingCpuLocked()) { 2791 int totalUTime = 0; 2792 int totalSTime = 0; 2793 final int N = mProcessCpuTracker.countStats(); 2794 for (int i=0; i<N; i++) { 2795 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(i); 2796 if (!st.working) { 2797 continue; 2798 } 2799 ProcessRecord pr = mPidsSelfLocked.get(st.pid); 2800 totalUTime += st.rel_utime; 2801 totalSTime += st.rel_stime; 2802 if (pr != null) { 2803 BatteryStatsImpl.Uid.Proc ps = pr.curProcBatteryStats; 2804 if (ps == null || !ps.isActive()) { 2805 pr.curProcBatteryStats = ps = bstats.getProcessStatsLocked( 2806 pr.info.uid, pr.processName); 2807 } 2808 ps.addCpuTimeLocked(st.rel_utime, st.rel_stime); 2809 pr.curCpuTime += st.rel_utime + st.rel_stime; 2810 } else { 2811 BatteryStatsImpl.Uid.Proc ps = st.batteryStats; 2812 if (ps == null || !ps.isActive()) { 2813 st.batteryStats = ps = bstats.getProcessStatsLocked( 2814 bstats.mapUid(st.uid), st.name); 2815 } 2816 ps.addCpuTimeLocked(st.rel_utime, st.rel_stime); 2817 } 2818 } 2819 final int userTime = mProcessCpuTracker.getLastUserTime(); 2820 final int systemTime = mProcessCpuTracker.getLastSystemTime(); 2821 final int iowaitTime = mProcessCpuTracker.getLastIoWaitTime(); 2822 final int irqTime = mProcessCpuTracker.getLastIrqTime(); 2823 final int softIrqTime = mProcessCpuTracker.getLastSoftIrqTime(); 2824 final int idleTime = mProcessCpuTracker.getLastIdleTime(); 2825 bstats.finishAddingCpuLocked(totalUTime, totalSTime, userTime, 2826 systemTime, iowaitTime, irqTime, softIrqTime, idleTime); 2827 } 2828 } 2829 } 2830 2831 if (mLastWriteTime < (now-BATTERY_STATS_TIME)) { 2832 mLastWriteTime = now; 2833 mBatteryStatsService.scheduleWriteToDisk(); 2834 } 2835 } 2836 } 2837 } 2838 2839 @Override 2840 public void batteryNeedsCpuUpdate() { 2841 updateCpuStatsNow(); 2842 } 2843 2844 @Override 2845 public void batteryPowerChanged(boolean onBattery) { 2846 // When plugging in, update the CPU stats first before changing 2847 // the plug state. 2848 updateCpuStatsNow(); 2849 synchronized (this) { 2850 synchronized(mPidsSelfLocked) { 2851 mOnBattery = DEBUG_POWER ? true : onBattery; 2852 } 2853 } 2854 } 2855 2856 @Override 2857 public void batterySendBroadcast(Intent intent) { 2858 broadcastIntentLocked(null, null, intent, null, null, 0, null, null, null, 2859 AppOpsManager.OP_NONE, null, false, false, 2860 -1, Process.SYSTEM_UID, UserHandle.USER_ALL); 2861 } 2862 2863 /** 2864 * Initialize the application bind args. These are passed to each 2865 * process when the bindApplication() IPC is sent to the process. They're 2866 * lazily setup to make sure the services are running when they're asked for. 2867 */ 2868 private HashMap<String, IBinder> getCommonServicesLocked(boolean isolated) { 2869 // Isolated processes won't get this optimization, so that we don't 2870 // violate the rules about which services they have access to. 2871 if (isolated) { 2872 if (mIsolatedAppBindArgs == null) { 2873 mIsolatedAppBindArgs = new HashMap<>(); 2874 mIsolatedAppBindArgs.put("package", ServiceManager.getService("package")); 2875 } 2876 return mIsolatedAppBindArgs; 2877 } 2878 2879 if (mAppBindArgs == null) { 2880 mAppBindArgs = new HashMap<>(); 2881 2882 // Setup the application init args 2883 mAppBindArgs.put("package", ServiceManager.getService("package")); 2884 mAppBindArgs.put("window", ServiceManager.getService("window")); 2885 mAppBindArgs.put(Context.ALARM_SERVICE, 2886 ServiceManager.getService(Context.ALARM_SERVICE)); 2887 } 2888 return mAppBindArgs; 2889 } 2890 2891 /** 2892 * Update AMS states when an activity is resumed. This should only be called by 2893 * {@link ActivityStack#setResumedActivityLocked} when an activity is resumed. 2894 */ 2895 void setResumedActivityUncheckLocked(ActivityRecord r, String reason) { 2896 if (r.task.isApplicationTask()) { 2897 if (mCurAppTimeTracker != r.appTimeTracker) { 2898 // We are switching app tracking. Complete the current one. 2899 if (mCurAppTimeTracker != null) { 2900 mCurAppTimeTracker.stop(); 2901 mHandler.obtainMessage( 2902 REPORT_TIME_TRACKER_MSG, mCurAppTimeTracker).sendToTarget(); 2903 mStackSupervisor.clearOtherAppTimeTrackers(r.appTimeTracker); 2904 mCurAppTimeTracker = null; 2905 } 2906 if (r.appTimeTracker != null) { 2907 mCurAppTimeTracker = r.appTimeTracker; 2908 startTimeTrackingFocusedActivityLocked(); 2909 } 2910 } else { 2911 startTimeTrackingFocusedActivityLocked(); 2912 } 2913 } else { 2914 r.appTimeTracker = null; 2915 } 2916 // TODO: VI Maybe r.task.voiceInteractor || r.voiceInteractor != null 2917 // TODO: Probably not, because we don't want to resume voice on switching 2918 // back to this activity 2919 if (r.task.voiceInteractor != null) { 2920 startRunningVoiceLocked(r.task.voiceSession, r.info.applicationInfo.uid); 2921 } else { 2922 finishRunningVoiceLocked(); 2923 IVoiceInteractionSession session; 2924 if (mLastResumedActivity != null 2925 && ((session = mLastResumedActivity.task.voiceSession) != null 2926 || (session = mLastResumedActivity.voiceSession) != null)) { 2927 // We had been in a voice interaction session, but now focused has 2928 // move to something different. Just finish the session, we can't 2929 // return to it and retain the proper state and synchronization with 2930 // the voice interaction service. 2931 finishVoiceTask(session); 2932 } 2933 } 2934 2935 mWindowManager.setFocusedApp(r.appToken, true); 2936 2937 applyUpdateLockStateLocked(r); 2938 applyUpdateVrModeLocked(r); 2939 if (mLastResumedActivity != null && r.userId != mLastResumedActivity.userId) { 2940 mHandler.removeMessages(FOREGROUND_PROFILE_CHANGED_MSG); 2941 mHandler.obtainMessage( 2942 FOREGROUND_PROFILE_CHANGED_MSG, r.userId, 0).sendToTarget(); 2943 } 2944 2945 mLastResumedActivity = r; 2946 2947 EventLogTags.writeAmSetResumedActivity( 2948 r == null ? -1 : r.userId, 2949 r == null ? "NULL" : r.shortComponentName, 2950 reason); 2951 } 2952 2953 @Override 2954 public void setFocusedStack(int stackId) { 2955 enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "setFocusedStack()"); 2956 if (DEBUG_FOCUS) Slog.d(TAG_FOCUS, "setFocusedStack: stackId=" + stackId); 2957 final long callingId = Binder.clearCallingIdentity(); 2958 try { 2959 synchronized (this) { 2960 final ActivityStack stack = mStackSupervisor.getStack(stackId); 2961 if (stack == null) { 2962 return; 2963 } 2964 final ActivityRecord r = stack.topRunningActivityLocked(); 2965 if (mStackSupervisor.moveFocusableActivityStackToFrontLocked(r, "setFocusedStack")) { 2966 mStackSupervisor.resumeFocusedStackTopActivityLocked(); 2967 } 2968 } 2969 } finally { 2970 Binder.restoreCallingIdentity(callingId); 2971 } 2972 } 2973 2974 @Override 2975 public void setFocusedTask(int taskId) { 2976 enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "setFocusedTask()"); 2977 if (DEBUG_FOCUS) Slog.d(TAG_FOCUS, "setFocusedTask: taskId=" + taskId); 2978 final long callingId = Binder.clearCallingIdentity(); 2979 try { 2980 synchronized (this) { 2981 final TaskRecord task = mStackSupervisor.anyTaskForIdLocked(taskId); 2982 if (task == null) { 2983 return; 2984 } 2985 final ActivityRecord r = task.topRunningActivityLocked(); 2986 if (mStackSupervisor.moveFocusableActivityStackToFrontLocked(r, "setFocusedTask")) { 2987 mStackSupervisor.resumeFocusedStackTopActivityLocked(); 2988 } 2989 } 2990 } finally { 2991 Binder.restoreCallingIdentity(callingId); 2992 } 2993 } 2994 2995 /** Sets the task stack listener that gets callbacks when a task stack changes. */ 2996 @Override 2997 public void registerTaskStackListener(ITaskStackListener listener) throws RemoteException { 2998 enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "registerTaskStackListener()"); 2999 mTaskChangeNotificationController.registerTaskStackListener(listener); 3000 } 3001 3002 /** 3003 * Unregister a task stack listener so that it stops receiving callbacks. 3004 */ 3005 @Override 3006 public void unregisterTaskStackListener(ITaskStackListener listener) throws RemoteException { 3007 enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "unregisterTaskStackListener()"); 3008 mTaskChangeNotificationController.unregisterTaskStackListener(listener); 3009 } 3010 3011 @Override 3012 public void notifyActivityDrawn(IBinder token) { 3013 if (DEBUG_VISIBILITY) Slog.d(TAG_VISIBILITY, "notifyActivityDrawn: token=" + token); 3014 synchronized (this) { 3015 ActivityRecord r = mStackSupervisor.isInAnyStackLocked(token); 3016 if (r != null) { 3017 r.getStack().notifyActivityDrawnLocked(r); 3018 } 3019 } 3020 } 3021 3022 final void applyUpdateLockStateLocked(ActivityRecord r) { 3023 // Modifications to the UpdateLock state are done on our handler, outside 3024 // the activity manager's locks. The new state is determined based on the 3025 // state *now* of the relevant activity record. The object is passed to 3026 // the handler solely for logging detail, not to be consulted/modified. 3027 final boolean nextState = r != null && r.immersive; 3028 mHandler.sendMessage( 3029 mHandler.obtainMessage(IMMERSIVE_MODE_LOCK_MSG, (nextState) ? 1 : 0, 0, r)); 3030 } 3031 3032 final void applyUpdateVrModeLocked(ActivityRecord r) { 3033 mHandler.sendMessage( 3034 mHandler.obtainMessage(VR_MODE_CHANGE_MSG, 0, 0, r)); 3035 } 3036 3037 void applyVrModeIfNeededLocked(ActivityRecord r, boolean enable) { 3038 mHandler.sendMessage( 3039 mHandler.obtainMessage(VR_MODE_APPLY_IF_NEEDED_MSG, enable ? 1 : 0, 0, r)); 3040 } 3041 3042 private void applyVrMode(boolean enabled, ComponentName packageName, int userId, 3043 ComponentName callingPackage, boolean immediate) { 3044 VrManagerInternal vrService = 3045 LocalServices.getService(VrManagerInternal.class); 3046 if (immediate) { 3047 vrService.setVrModeImmediate(enabled, packageName, userId, callingPackage); 3048 } else { 3049 vrService.setVrMode(enabled, packageName, userId, callingPackage); 3050 } 3051 } 3052 3053 final void showAskCompatModeDialogLocked(ActivityRecord r) { 3054 Message msg = Message.obtain(); 3055 msg.what = SHOW_COMPAT_MODE_DIALOG_UI_MSG; 3056 msg.obj = r.task.askedCompatMode ? null : r; 3057 mUiHandler.sendMessage(msg); 3058 } 3059 3060 final void showUnsupportedZoomDialogIfNeededLocked(ActivityRecord r) { 3061 final Configuration globalConfig = getGlobalConfiguration(); 3062 if (globalConfig.densityDpi != DisplayMetrics.DENSITY_DEVICE_STABLE 3063 && r.appInfo.requiresSmallestWidthDp > globalConfig.smallestScreenWidthDp) { 3064 final Message msg = Message.obtain(); 3065 msg.what = SHOW_UNSUPPORTED_DISPLAY_SIZE_DIALOG_MSG; 3066 msg.obj = r; 3067 mUiHandler.sendMessage(msg); 3068 } 3069 } 3070 3071 private int updateLruProcessInternalLocked(ProcessRecord app, long now, int index, 3072 String what, Object obj, ProcessRecord srcApp) { 3073 app.lastActivityTime = now; 3074 3075 if (app.activities.size() > 0) { 3076 // Don't want to touch dependent processes that are hosting activities. 3077 return index; 3078 } 3079 3080 int lrui = mLruProcesses.lastIndexOf(app); 3081 if (lrui < 0) { 3082 Slog.wtf(TAG, "Adding dependent process " + app + " not on LRU list: " 3083 + what + " " + obj + " from " + srcApp); 3084 return index; 3085 } 3086 3087 if (lrui >= index) { 3088 // Don't want to cause this to move dependent processes *back* in the 3089 // list as if they were less frequently used. 3090 return index; 3091 } 3092 3093 if (lrui >= mLruProcessActivityStart) { 3094 // Don't want to touch dependent processes that are hosting activities. 3095 return index; 3096 } 3097 3098 mLruProcesses.remove(lrui); 3099 if (index > 0) { 3100 index--; 3101 } 3102 if (DEBUG_LRU) Slog.d(TAG_LRU, "Moving dep from " + lrui + " to " + index 3103 + " in LRU list: " + app); 3104 mLruProcesses.add(index, app); 3105 return index; 3106 } 3107 3108 static void killProcessGroup(int uid, int pid) { 3109 if (sKillHandler != null) { 3110 sKillHandler.sendMessage( 3111 sKillHandler.obtainMessage(KillHandler.KILL_PROCESS_GROUP_MSG, uid, pid)); 3112 } else { 3113 Slog.w(TAG, "Asked to kill process group before system bringup!"); 3114 Process.killProcessGroup(uid, pid); 3115 } 3116 } 3117 3118 final void removeLruProcessLocked(ProcessRecord app) { 3119 int lrui = mLruProcesses.lastIndexOf(app); 3120 if (lrui >= 0) { 3121 if (!app.killed) { 3122 Slog.wtfStack(TAG, "Removing process that hasn't been killed: " + app); 3123 Process.killProcessQuiet(app.pid); 3124 killProcessGroup(app.uid, app.pid); 3125 } 3126 if (lrui <= mLruProcessActivityStart) { 3127 mLruProcessActivityStart--; 3128 } 3129 if (lrui <= mLruProcessServiceStart) { 3130 mLruProcessServiceStart--; 3131 } 3132 mLruProcesses.remove(lrui); 3133 } 3134 } 3135 3136 final void updateLruProcessLocked(ProcessRecord app, boolean activityChange, 3137 ProcessRecord client) { 3138 final boolean hasActivity = app.activities.size() > 0 || app.hasClientActivities 3139 || app.treatLikeActivity; 3140 final boolean hasService = false; // not impl yet. app.services.size() > 0; 3141 if (!activityChange && hasActivity) { 3142 // The process has activities, so we are only allowing activity-based adjustments 3143 // to move it. It should be kept in the front of the list with other 3144 // processes that have activities, and we don't want those to change their 3145 // order except due to activity operations. 3146 return; 3147 } 3148 3149 mLruSeq++; 3150 final long now = SystemClock.uptimeMillis(); 3151 app.lastActivityTime = now; 3152 3153 // First a quick reject: if the app is already at the position we will 3154 // put it, then there is nothing to do. 3155 if (hasActivity) { 3156 final int N = mLruProcesses.size(); 3157 if (N > 0 && mLruProcesses.get(N-1) == app) { 3158 if (DEBUG_LRU) Slog.d(TAG_LRU, "Not moving, already top activity: " + app); 3159 return; 3160 } 3161 } else { 3162 if (mLruProcessServiceStart > 0 3163 && mLruProcesses.get(mLruProcessServiceStart-1) == app) { 3164 if (DEBUG_LRU) Slog.d(TAG_LRU, "Not moving, already top other: " + app); 3165 return; 3166 } 3167 } 3168 3169 int lrui = mLruProcesses.lastIndexOf(app); 3170 3171 if (app.persistent && lrui >= 0) { 3172 // We don't care about the position of persistent processes, as long as 3173 // they are in the list. 3174 if (DEBUG_LRU) Slog.d(TAG_LRU, "Not moving, persistent: " + app); 3175 return; 3176 } 3177 3178 /* In progress: compute new position first, so we can avoid doing work 3179 if the process is not actually going to move. Not yet working. 3180 int addIndex; 3181 int nextIndex; 3182 boolean inActivity = false, inService = false; 3183 if (hasActivity) { 3184 // Process has activities, put it at the very tipsy-top. 3185 addIndex = mLruProcesses.size(); 3186 nextIndex = mLruProcessServiceStart; 3187 inActivity = true; 3188 } else if (hasService) { 3189 // Process has services, put it at the top of the service list. 3190 addIndex = mLruProcessActivityStart; 3191 nextIndex = mLruProcessServiceStart; 3192 inActivity = true; 3193 inService = true; 3194 } else { 3195 // Process not otherwise of interest, it goes to the top of the non-service area. 3196 addIndex = mLruProcessServiceStart; 3197 if (client != null) { 3198 int clientIndex = mLruProcesses.lastIndexOf(client); 3199 if (clientIndex < 0) Slog.d(TAG, "Unknown client " + client + " when updating " 3200 + app); 3201 if (clientIndex >= 0 && addIndex > clientIndex) { 3202 addIndex = clientIndex; 3203 } 3204 } 3205 nextIndex = addIndex > 0 ? addIndex-1 : addIndex; 3206 } 3207 3208 Slog.d(TAG, "Update LRU at " + lrui + " to " + addIndex + " (act=" 3209 + mLruProcessActivityStart + "): " + app); 3210 */ 3211 3212 if (lrui >= 0) { 3213 if (lrui < mLruProcessActivityStart) { 3214 mLruProcessActivityStart--; 3215 } 3216 if (lrui < mLruProcessServiceStart) { 3217 mLruProcessServiceStart--; 3218 } 3219 /* 3220 if (addIndex > lrui) { 3221 addIndex--; 3222 } 3223 if (nextIndex > lrui) { 3224 nextIndex--; 3225 } 3226 */ 3227 mLruProcesses.remove(lrui); 3228 } 3229 3230 /* 3231 mLruProcesses.add(addIndex, app); 3232 if (inActivity) { 3233 mLruProcessActivityStart++; 3234 } 3235 if (inService) { 3236 mLruProcessActivityStart++; 3237 } 3238 */ 3239 3240 int nextIndex; 3241 if (hasActivity) { 3242 final int N = mLruProcesses.size(); 3243 if (app.activities.size() == 0 && mLruProcessActivityStart < (N - 1)) { 3244 // Process doesn't have activities, but has clients with 3245 // activities... move it up, but one below the top (the top 3246 // should always have a real activity). 3247 if (DEBUG_LRU) Slog.d(TAG_LRU, 3248 "Adding to second-top of LRU activity list: " + app); 3249 mLruProcesses.add(N - 1, app); 3250 // To keep it from spamming the LRU list (by making a bunch of clients), 3251 // we will push down any other entries owned by the app. 3252 final int uid = app.info.uid; 3253 for (int i = N - 2; i > mLruProcessActivityStart; i--) { 3254 ProcessRecord subProc = mLruProcesses.get(i); 3255 if (subProc.info.uid == uid) { 3256 // We want to push this one down the list. If the process after 3257 // it is for the same uid, however, don't do so, because we don't 3258 // want them internally to be re-ordered. 3259 if (mLruProcesses.get(i - 1).info.uid != uid) { 3260 if (DEBUG_LRU) Slog.d(TAG_LRU, 3261 "Pushing uid " + uid + " swapping at " + i + ": " 3262 + mLruProcesses.get(i) + " : " + mLruProcesses.get(i - 1)); 3263 ProcessRecord tmp = mLruProcesses.get(i); 3264 mLruProcesses.set(i, mLruProcesses.get(i - 1)); 3265 mLruProcesses.set(i - 1, tmp); 3266 i--; 3267 } 3268 } else { 3269 // A gap, we can stop here. 3270 break; 3271 } 3272 } 3273 } else { 3274 // Process has activities, put it at the very tipsy-top. 3275 if (DEBUG_LRU) Slog.d(TAG_LRU, "Adding to top of LRU activity list: " + app); 3276 mLruProcesses.add(app); 3277 } 3278 nextIndex = mLruProcessServiceStart; 3279 } else if (hasService) { 3280 // Process has services, put it at the top of the service list. 3281 if (DEBUG_LRU) Slog.d(TAG_LRU, "Adding to top of LRU service list: " + app); 3282 mLruProcesses.add(mLruProcessActivityStart, app); 3283 nextIndex = mLruProcessServiceStart; 3284 mLruProcessActivityStart++; 3285 } else { 3286 // Process not otherwise of interest, it goes to the top of the non-service area. 3287 int index = mLruProcessServiceStart; 3288 if (client != null) { 3289 // If there is a client, don't allow the process to be moved up higher 3290 // in the list than that client. 3291 int clientIndex = mLruProcesses.lastIndexOf(client); 3292 if (DEBUG_LRU && clientIndex < 0) Slog.d(TAG_LRU, "Unknown client " + client 3293 + " when updating " + app); 3294 if (clientIndex <= lrui) { 3295 // Don't allow the client index restriction to push it down farther in the 3296 // list than it already is. 3297 clientIndex = lrui; 3298 } 3299 if (clientIndex >= 0 && index > clientIndex) { 3300 index = clientIndex; 3301 } 3302 } 3303 if (DEBUG_LRU) Slog.d(TAG_LRU, "Adding at " + index + " of LRU list: " + app); 3304 mLruProcesses.add(index, app); 3305 nextIndex = index-1; 3306 mLruProcessActivityStart++; 3307 mLruProcessServiceStart++; 3308 } 3309 3310 // If the app is currently using a content provider or service, 3311 // bump those processes as well. 3312 for (int j=app.connections.size()-1; j>=0; j--) { 3313 ConnectionRecord cr = app.connections.valueAt(j); 3314 if (cr.binding != null && !cr.serviceDead && cr.binding.service != null 3315 && cr.binding.service.app != null 3316 && cr.binding.service.app.lruSeq != mLruSeq 3317 && !cr.binding.service.app.persistent) { 3318 nextIndex = updateLruProcessInternalLocked(cr.binding.service.app, now, nextIndex, 3319 "service connection", cr, app); 3320 } 3321 } 3322 for (int j=app.conProviders.size()-1; j>=0; j--) { 3323 ContentProviderRecord cpr = app.conProviders.get(j).provider; 3324 if (cpr.proc != null && cpr.proc.lruSeq != mLruSeq && !cpr.proc.persistent) { 3325 nextIndex = updateLruProcessInternalLocked(cpr.proc, now, nextIndex, 3326 "provider reference", cpr, app); 3327 } 3328 } 3329 } 3330 3331 final ProcessRecord getProcessRecordLocked(String processName, int uid, boolean keepIfLarge) { 3332 if (uid == Process.SYSTEM_UID) { 3333 // The system gets to run in any process. If there are multiple 3334 // processes with the same uid, just pick the first (this 3335 // should never happen). 3336 SparseArray<ProcessRecord> procs = mProcessNames.getMap().get(processName); 3337 if (procs == null) return null; 3338 final int procCount = procs.size(); 3339 for (int i = 0; i < procCount; i++) { 3340 final int procUid = procs.keyAt(i); 3341 if (UserHandle.isApp(procUid) || !UserHandle.isSameUser(procUid, uid)) { 3342 // Don't use an app process or different user process for system component. 3343 continue; 3344 } 3345 return procs.valueAt(i); 3346 } 3347 } 3348 ProcessRecord proc = mProcessNames.get(processName, uid); 3349 if (false && proc != null && !keepIfLarge 3350 && proc.setProcState >= ActivityManager.PROCESS_STATE_CACHED_EMPTY 3351 && proc.lastCachedPss >= 4000) { 3352 // Turn this condition on to cause killing to happen regularly, for testing. 3353 if (proc.baseProcessTracker != null) { 3354 proc.baseProcessTracker.reportCachedKill(proc.pkgList, proc.lastCachedPss); 3355 } 3356 proc.kill(Long.toString(proc.lastCachedPss) + "k from cached", true); 3357 } else if (proc != null && !keepIfLarge 3358 && mLastMemoryLevel > ProcessStats.ADJ_MEM_FACTOR_NORMAL 3359 && proc.setProcState >= ActivityManager.PROCESS_STATE_CACHED_EMPTY) { 3360 if (DEBUG_PSS) Slog.d(TAG_PSS, "May not keep " + proc + ": pss=" + proc.lastCachedPss); 3361 if (proc.lastCachedPss >= mProcessList.getCachedRestoreThresholdKb()) { 3362 if (proc.baseProcessTracker != null) { 3363 proc.baseProcessTracker.reportCachedKill(proc.pkgList, proc.lastCachedPss); 3364 } 3365 proc.kill(Long.toString(proc.lastCachedPss) + "k from cached", true); 3366 } 3367 } 3368 return proc; 3369 } 3370 3371 void notifyPackageUse(String packageName, int reason) { 3372 IPackageManager pm = AppGlobals.getPackageManager(); 3373 try { 3374 pm.notifyPackageUse(packageName, reason); 3375 } catch (RemoteException e) { 3376 } 3377 } 3378 3379 boolean isNextTransitionForward() { 3380 int transit = mWindowManager.getPendingAppTransition(); 3381 return transit == TRANSIT_ACTIVITY_OPEN 3382 || transit == TRANSIT_TASK_OPEN 3383 || transit == TRANSIT_TASK_TO_FRONT; 3384 } 3385 3386 int startIsolatedProcess(String entryPoint, String[] entryPointArgs, 3387 String processName, String abiOverride, int uid, Runnable crashHandler) { 3388 synchronized(this) { 3389 ApplicationInfo info = new ApplicationInfo(); 3390 // In general the ApplicationInfo.uid isn't neccesarily equal to ProcessRecord.uid. 3391 // For isolated processes, the former contains the parent's uid and the latter the 3392 // actual uid of the isolated process. 3393 // In the special case introduced by this method (which is, starting an isolated 3394 // process directly from the SystemServer without an actual parent app process) the 3395 // closest thing to a parent's uid is SYSTEM_UID. 3396 // The only important thing here is to keep AI.uid != PR.uid, in order to trigger 3397 // the |isolated| logic in the ProcessRecord constructor. 3398 info.uid = Process.SYSTEM_UID; 3399 info.processName = processName; 3400 info.className = entryPoint; 3401 info.packageName = "android"; 3402 ProcessRecord proc = startProcessLocked(processName, info /* info */, 3403 false /* knownToBeDead */, 0 /* intentFlags */, "" /* hostingType */, 3404 null /* hostingName */, true /* allowWhileBooting */, true /* isolated */, 3405 uid, true /* keepIfLarge */, abiOverride, entryPoint, entryPointArgs, 3406 crashHandler); 3407 return proc != null ? proc.pid : 0; 3408 } 3409 } 3410 3411 final ProcessRecord startProcessLocked(String processName, 3412 ApplicationInfo info, boolean knownToBeDead, int intentFlags, 3413 String hostingType, ComponentName hostingName, boolean allowWhileBooting, 3414 boolean isolated, boolean keepIfLarge) { 3415 return startProcessLocked(processName, info, knownToBeDead, intentFlags, hostingType, 3416 hostingName, allowWhileBooting, isolated, 0 /* isolatedUid */, keepIfLarge, 3417 null /* ABI override */, null /* entryPoint */, null /* entryPointArgs */, 3418 null /* crashHandler */); 3419 } 3420 3421 final ProcessRecord startProcessLocked(String processName, ApplicationInfo info, 3422 boolean knownToBeDead, int intentFlags, String hostingType, ComponentName hostingName, 3423 boolean allowWhileBooting, boolean isolated, int isolatedUid, boolean keepIfLarge, 3424 String abiOverride, String entryPoint, String[] entryPointArgs, Runnable crashHandler) { 3425 long startTime = SystemClock.elapsedRealtime(); 3426 ProcessRecord app; 3427 if (!isolated) { 3428 app = getProcessRecordLocked(processName, info.uid, keepIfLarge); 3429 checkTime(startTime, "startProcess: after getProcessRecord"); 3430 3431 if ((intentFlags & Intent.FLAG_FROM_BACKGROUND) != 0) { 3432 // If we are in the background, then check to see if this process 3433 // is bad. If so, we will just silently fail. 3434 if (mAppErrors.isBadProcessLocked(info)) { 3435 if (DEBUG_PROCESSES) Slog.v(TAG, "Bad process: " + info.uid 3436 + "/" + info.processName); 3437 return null; 3438 } 3439 } else { 3440 // When the user is explicitly starting a process, then clear its 3441 // crash count so that we won't make it bad until they see at 3442 // least one crash dialog again, and make the process good again 3443 // if it had been bad. 3444 if (DEBUG_PROCESSES) Slog.v(TAG, "Clearing bad process: " + info.uid 3445 + "/" + info.processName); 3446 mAppErrors.resetProcessCrashTimeLocked(info); 3447 if (mAppErrors.isBadProcessLocked(info)) { 3448 EventLog.writeEvent(EventLogTags.AM_PROC_GOOD, 3449 UserHandle.getUserId(info.uid), info.uid, 3450 info.processName); 3451 mAppErrors.clearBadProcessLocked(info); 3452 if (app != null) { 3453 app.bad = false; 3454 } 3455 } 3456 } 3457 } else { 3458 // If this is an isolated process, it can't re-use an existing process. 3459 app = null; 3460 } 3461 3462 // We don't have to do anything more if: 3463 // (1) There is an existing application record; and 3464 // (2) The caller doesn't think it is dead, OR there is no thread 3465 // object attached to it so we know it couldn't have crashed; and 3466 // (3) There is a pid assigned to it, so it is either starting or 3467 // already running. 3468 if (DEBUG_PROCESSES) Slog.v(TAG_PROCESSES, "startProcess: name=" + processName 3469 + " app=" + app + " knownToBeDead=" + knownToBeDead 3470 + " thread=" + (app != null ? app.thread : null) 3471 + " pid=" + (app != null ? app.pid : -1)); 3472 if (app != null && app.pid > 0) { 3473 if ((!knownToBeDead && !app.killed) || app.thread == null) { 3474 // We already have the app running, or are waiting for it to 3475 // come up (we have a pid but not yet its thread), so keep it. 3476 if (DEBUG_PROCESSES) Slog.v(TAG_PROCESSES, "App already running: " + app); 3477 // If this is a new package in the process, add the package to the list 3478 app.addPackage(info.packageName, info.versionCode, mProcessStats); 3479 checkTime(startTime, "startProcess: done, added package to proc"); 3480 return app; 3481 } 3482 3483 // An application record is attached to a previous process, 3484 // clean it up now. 3485 if (DEBUG_PROCESSES || DEBUG_CLEANUP) Slog.v(TAG_PROCESSES, "App died: " + app); 3486 checkTime(startTime, "startProcess: bad proc running, killing"); 3487 killProcessGroup(app.uid, app.pid); 3488 handleAppDiedLocked(app, true, true); 3489 checkTime(startTime, "startProcess: done killing old proc"); 3490 } 3491 3492 String hostingNameStr = hostingName != null 3493 ? hostingName.flattenToShortString() : null; 3494 3495 if (app == null) { 3496 checkTime(startTime, "startProcess: creating new process record"); 3497 app = newProcessRecordLocked(info, processName, isolated, isolatedUid); 3498 if (app == null) { 3499 Slog.w(TAG, "Failed making new process record for " 3500 + processName + "/" + info.uid + " isolated=" + isolated); 3501 return null; 3502 } 3503 app.crashHandler = crashHandler; 3504 checkTime(startTime, "startProcess: done creating new process record"); 3505 } else { 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: added package to existing proc"); 3509 } 3510 3511 // If the system is not ready yet, then hold off on starting this 3512 // process until it is. 3513 if (!mProcessesReady 3514 && !isAllowedWhileBooting(info) 3515 && !allowWhileBooting) { 3516 if (!mProcessesOnHold.contains(app)) { 3517 mProcessesOnHold.add(app); 3518 } 3519 if (DEBUG_PROCESSES) Slog.v(TAG_PROCESSES, 3520 "System not ready, putting on hold: " + app); 3521 checkTime(startTime, "startProcess: returning with proc on hold"); 3522 return app; 3523 } 3524 3525 checkTime(startTime, "startProcess: stepping in to startProcess"); 3526 startProcessLocked( 3527 app, hostingType, hostingNameStr, abiOverride, entryPoint, entryPointArgs); 3528 checkTime(startTime, "startProcess: done starting proc!"); 3529 return (app.pid != 0) ? app : null; 3530 } 3531 3532 boolean isAllowedWhileBooting(ApplicationInfo ai) { 3533 return (ai.flags&ApplicationInfo.FLAG_PERSISTENT) != 0; 3534 } 3535 3536 private final void startProcessLocked(ProcessRecord app, 3537 String hostingType, String hostingNameStr) { 3538 startProcessLocked(app, hostingType, hostingNameStr, null /* abiOverride */, 3539 null /* entryPoint */, null /* entryPointArgs */); 3540 } 3541 3542 private final void startProcessLocked(ProcessRecord app, String hostingType, 3543 String hostingNameStr, String abiOverride, String entryPoint, String[] entryPointArgs) { 3544 long startTime = SystemClock.elapsedRealtime(); 3545 if (app.pid > 0 && app.pid != MY_PID) { 3546 checkTime(startTime, "startProcess: removing from pids map"); 3547 synchronized (mPidsSelfLocked) { 3548 mPidsSelfLocked.remove(app.pid); 3549 mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app); 3550 } 3551 checkTime(startTime, "startProcess: done removing from pids map"); 3552 app.setPid(0); 3553 } 3554 3555 if (DEBUG_PROCESSES && mProcessesOnHold.contains(app)) Slog.v(TAG_PROCESSES, 3556 "startProcessLocked removing on hold: " + app); 3557 mProcessesOnHold.remove(app); 3558 3559 checkTime(startTime, "startProcess: starting to update cpu stats"); 3560 updateCpuStats(); 3561 checkTime(startTime, "startProcess: done updating cpu stats"); 3562 3563 try { 3564 try { 3565 final int userId = UserHandle.getUserId(app.uid); 3566 AppGlobals.getPackageManager().checkPackageStartable(app.info.packageName, userId); 3567 } catch (RemoteException e) { 3568 throw e.rethrowAsRuntimeException(); 3569 } 3570 3571 int uid = app.uid; 3572 int[] gids = null; 3573 int mountExternal = Zygote.MOUNT_EXTERNAL_NONE; 3574 if (!app.isolated) { 3575 int[] permGids = null; 3576 try { 3577 checkTime(startTime, "startProcess: getting gids from package manager"); 3578 final IPackageManager pm = AppGlobals.getPackageManager(); 3579 permGids = pm.getPackageGids(app.info.packageName, 3580 MATCH_DEBUG_TRIAGED_MISSING, app.userId); 3581 MountServiceInternal mountServiceInternal = LocalServices.getService( 3582 MountServiceInternal.class); 3583 mountExternal = mountServiceInternal.getExternalStorageMountMode(uid, 3584 app.info.packageName); 3585 } catch (RemoteException e) { 3586 throw e.rethrowAsRuntimeException(); 3587 } 3588 3589 /* 3590 * Add shared application and profile GIDs so applications can share some 3591 * resources like shared libraries and access user-wide resources 3592 */ 3593 if (ArrayUtils.isEmpty(permGids)) { 3594 gids = new int[2]; 3595 } else { 3596 gids = new int[permGids.length + 2]; 3597 System.arraycopy(permGids, 0, gids, 2, permGids.length); 3598 } 3599 gids[0] = UserHandle.getSharedAppGid(UserHandle.getAppId(uid)); 3600 gids[1] = UserHandle.getUserGid(UserHandle.getUserId(uid)); 3601 } 3602 checkTime(startTime, "startProcess: building args"); 3603 if (mFactoryTest != FactoryTest.FACTORY_TEST_OFF) { 3604 if (mFactoryTest == FactoryTest.FACTORY_TEST_LOW_LEVEL 3605 && mTopComponent != null 3606 && app.processName.equals(mTopComponent.getPackageName())) { 3607 uid = 0; 3608 } 3609 if (mFactoryTest == FactoryTest.FACTORY_TEST_HIGH_LEVEL 3610 && (app.info.flags&ApplicationInfo.FLAG_FACTORY_TEST) != 0) { 3611 uid = 0; 3612 } 3613 } 3614 int debugFlags = 0; 3615 if ((app.info.flags & ApplicationInfo.FLAG_DEBUGGABLE) != 0) { 3616 debugFlags |= Zygote.DEBUG_ENABLE_DEBUGGER; 3617 // Also turn on CheckJNI for debuggable apps. It's quite 3618 // awkward to turn on otherwise. 3619 debugFlags |= Zygote.DEBUG_ENABLE_CHECKJNI; 3620 } 3621 // Run the app in safe mode if its manifest requests so or the 3622 // system is booted in safe mode. 3623 if ((app.info.flags & ApplicationInfo.FLAG_VM_SAFE_MODE) != 0 || 3624 mSafeMode == true) { 3625 debugFlags |= Zygote.DEBUG_ENABLE_SAFEMODE; 3626 } 3627 if ("1".equals(SystemProperties.get("debug.checkjni"))) { 3628 debugFlags |= Zygote.DEBUG_ENABLE_CHECKJNI; 3629 } 3630 String genDebugInfoProperty = SystemProperties.get("debug.generate-debug-info"); 3631 if ("true".equals(genDebugInfoProperty)) { 3632 debugFlags |= Zygote.DEBUG_GENERATE_DEBUG_INFO; 3633 } 3634 if ("1".equals(SystemProperties.get("debug.jni.logging"))) { 3635 debugFlags |= Zygote.DEBUG_ENABLE_JNI_LOGGING; 3636 } 3637 if ("1".equals(SystemProperties.get("debug.assert"))) { 3638 debugFlags |= Zygote.DEBUG_ENABLE_ASSERT; 3639 } 3640 if (mNativeDebuggingApp != null && mNativeDebuggingApp.equals(app.processName)) { 3641 // Enable all debug flags required by the native debugger. 3642 debugFlags |= Zygote.DEBUG_ALWAYS_JIT; // Don't interpret anything 3643 debugFlags |= Zygote.DEBUG_GENERATE_DEBUG_INFO; // Generate debug info 3644 debugFlags |= Zygote.DEBUG_NATIVE_DEBUGGABLE; // Disbale optimizations 3645 mNativeDebuggingApp = null; 3646 } 3647 3648 String requiredAbi = (abiOverride != null) ? abiOverride : app.info.primaryCpuAbi; 3649 if (requiredAbi == null) { 3650 requiredAbi = Build.SUPPORTED_ABIS[0]; 3651 } 3652 3653 String instructionSet = null; 3654 if (app.info.primaryCpuAbi != null) { 3655 instructionSet = VMRuntime.getInstructionSet(app.info.primaryCpuAbi); 3656 } 3657 3658 app.gids = gids; 3659 app.requiredAbi = requiredAbi; 3660 app.instructionSet = instructionSet; 3661 3662 // Start the process. It will either succeed and return a result containing 3663 // the PID of the new process, or else throw a RuntimeException. 3664 boolean isActivityProcess = (entryPoint == null); 3665 if (entryPoint == null) entryPoint = "android.app.ActivityThread"; 3666 Trace.traceBegin(Trace.TRACE_TAG_ACTIVITY_MANAGER, "Start proc: " + 3667 app.processName); 3668 checkTime(startTime, "startProcess: asking zygote to start proc"); 3669 Process.ProcessStartResult startResult = Process.start(entryPoint, 3670 app.processName, uid, uid, gids, debugFlags, mountExternal, 3671 app.info.targetSdkVersion, app.info.seinfo, requiredAbi, instructionSet, 3672 app.info.dataDir, entryPointArgs); 3673 checkTime(startTime, "startProcess: returned from zygote!"); 3674 Trace.traceEnd(Trace.TRACE_TAG_ACTIVITY_MANAGER); 3675 3676 mBatteryStatsService.noteProcessStart(app.processName, app.info.uid); 3677 checkTime(startTime, "startProcess: done updating battery stats"); 3678 3679 EventLog.writeEvent(EventLogTags.AM_PROC_START, 3680 UserHandle.getUserId(uid), startResult.pid, uid, 3681 app.processName, hostingType, 3682 hostingNameStr != null ? hostingNameStr : ""); 3683 3684 try { 3685 AppGlobals.getPackageManager().logAppProcessStartIfNeeded(app.processName, app.uid, 3686 app.info.seinfo, app.info.sourceDir, startResult.pid); 3687 } catch (RemoteException ex) { 3688 // Ignore 3689 } 3690 3691 if (app.persistent) { 3692 Watchdog.getInstance().processStarted(app.processName, startResult.pid); 3693 } 3694 3695 checkTime(startTime, "startProcess: building log message"); 3696 StringBuilder buf = mStringBuilder; 3697 buf.setLength(0); 3698 buf.append("Start proc "); 3699 buf.append(startResult.pid); 3700 buf.append(':'); 3701 buf.append(app.processName); 3702 buf.append('/'); 3703 UserHandle.formatUid(buf, uid); 3704 if (!isActivityProcess) { 3705 buf.append(" ["); 3706 buf.append(entryPoint); 3707 buf.append("]"); 3708 } 3709 buf.append(" for "); 3710 buf.append(hostingType); 3711 if (hostingNameStr != null) { 3712 buf.append(" "); 3713 buf.append(hostingNameStr); 3714 } 3715 Slog.i(TAG, buf.toString()); 3716 app.setPid(startResult.pid); 3717 app.usingWrapper = startResult.usingWrapper; 3718 app.removed = false; 3719 app.killed = false; 3720 app.killedByAm = false; 3721 checkTime(startTime, "startProcess: starting to update pids map"); 3722 ProcessRecord oldApp; 3723 synchronized (mPidsSelfLocked) { 3724 oldApp = mPidsSelfLocked.get(startResult.pid); 3725 } 3726 // If there is already an app occupying that pid that hasn't been cleaned up 3727 if (oldApp != null && !app.isolated) { 3728 // Clean up anything relating to this pid first 3729 Slog.w(TAG, "Reusing pid " + startResult.pid 3730 + " while app is still mapped to it"); 3731 cleanUpApplicationRecordLocked(oldApp, false, false, -1, 3732 true /*replacingPid*/); 3733 } 3734 synchronized (mPidsSelfLocked) { 3735 this.mPidsSelfLocked.put(startResult.pid, app); 3736 if (isActivityProcess) { 3737 Message msg = mHandler.obtainMessage(PROC_START_TIMEOUT_MSG); 3738 msg.obj = app; 3739 mHandler.sendMessageDelayed(msg, startResult.usingWrapper 3740 ? PROC_START_TIMEOUT_WITH_WRAPPER : PROC_START_TIMEOUT); 3741 } 3742 } 3743 checkTime(startTime, "startProcess: done updating pids map"); 3744 } catch (RuntimeException e) { 3745 Slog.e(TAG, "Failure starting process " + app.processName, e); 3746 3747 // Something went very wrong while trying to start this process; one 3748 // common case is when the package is frozen due to an active 3749 // upgrade. To recover, clean up any active bookkeeping related to 3750 // starting this process. (We already invoked this method once when 3751 // the package was initially frozen through KILL_APPLICATION_MSG, so 3752 // it doesn't hurt to use it again.) 3753 forceStopPackageLocked(app.info.packageName, UserHandle.getAppId(app.uid), false, 3754 false, true, false, false, UserHandle.getUserId(app.userId), "start failure"); 3755 } 3756 } 3757 3758 void updateUsageStats(ActivityRecord component, boolean resumed) { 3759 if (DEBUG_SWITCH) Slog.d(TAG_SWITCH, 3760 "updateUsageStats: comp=" + component + "res=" + resumed); 3761 final BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 3762 if (resumed) { 3763 if (mUsageStatsService != null) { 3764 mUsageStatsService.reportEvent(component.realActivity, component.userId, 3765 UsageEvents.Event.MOVE_TO_FOREGROUND); 3766 } 3767 synchronized (stats) { 3768 stats.noteActivityResumedLocked(component.app.uid); 3769 } 3770 } else { 3771 if (mUsageStatsService != null) { 3772 mUsageStatsService.reportEvent(component.realActivity, component.userId, 3773 UsageEvents.Event.MOVE_TO_BACKGROUND); 3774 } 3775 synchronized (stats) { 3776 stats.noteActivityPausedLocked(component.app.uid); 3777 } 3778 } 3779 } 3780 3781 Intent getHomeIntent() { 3782 Intent intent = new Intent(mTopAction, mTopData != null ? Uri.parse(mTopData) : null); 3783 intent.setComponent(mTopComponent); 3784 intent.addFlags(Intent.FLAG_DEBUG_TRIAGED_MISSING); 3785 if (mFactoryTest != FactoryTest.FACTORY_TEST_LOW_LEVEL) { 3786 intent.addCategory(Intent.CATEGORY_HOME); 3787 } 3788 return intent; 3789 } 3790 3791 boolean startHomeActivityLocked(int userId, String reason) { 3792 if (mFactoryTest == FactoryTest.FACTORY_TEST_LOW_LEVEL 3793 && mTopAction == null) { 3794 // We are running in factory test mode, but unable to find 3795 // the factory test app, so just sit around displaying the 3796 // error message and don't try to start anything. 3797 return false; 3798 } 3799 Intent intent = getHomeIntent(); 3800 ActivityInfo aInfo = resolveActivityInfo(intent, STOCK_PM_FLAGS, userId); 3801 if (aInfo != null) { 3802 intent.setComponent(new ComponentName(aInfo.applicationInfo.packageName, aInfo.name)); 3803 // Don't do this if the home app is currently being 3804 // instrumented. 3805 aInfo = new ActivityInfo(aInfo); 3806 aInfo.applicationInfo = getAppInfoForUser(aInfo.applicationInfo, userId); 3807 ProcessRecord app = getProcessRecordLocked(aInfo.processName, 3808 aInfo.applicationInfo.uid, true); 3809 if (app == null || app.instrumentationClass == null) { 3810 intent.setFlags(intent.getFlags() | Intent.FLAG_ACTIVITY_NEW_TASK); 3811 mActivityStarter.startHomeActivityLocked(intent, aInfo, reason); 3812 } 3813 } else { 3814 Slog.wtf(TAG, "No home screen found for " + intent, new Throwable()); 3815 } 3816 3817 return true; 3818 } 3819 3820 private ActivityInfo resolveActivityInfo(Intent intent, int flags, int userId) { 3821 ActivityInfo ai = null; 3822 ComponentName comp = intent.getComponent(); 3823 try { 3824 if (comp != null) { 3825 // Factory test. 3826 ai = AppGlobals.getPackageManager().getActivityInfo(comp, flags, userId); 3827 } else { 3828 ResolveInfo info = AppGlobals.getPackageManager().resolveIntent( 3829 intent, 3830 intent.resolveTypeIfNeeded(mContext.getContentResolver()), 3831 flags, userId); 3832 3833 if (info != null) { 3834 ai = info.activityInfo; 3835 } 3836 } 3837 } catch (RemoteException e) { 3838 // ignore 3839 } 3840 3841 return ai; 3842 } 3843 3844 /** 3845 * Starts the "new version setup screen" if appropriate. 3846 */ 3847 void startSetupActivityLocked() { 3848 // Only do this once per boot. 3849 if (mCheckedForSetup) { 3850 return; 3851 } 3852 3853 // We will show this screen if the current one is a different 3854 // version than the last one shown, and we are not running in 3855 // low-level factory test mode. 3856 final ContentResolver resolver = mContext.getContentResolver(); 3857 if (mFactoryTest != FactoryTest.FACTORY_TEST_LOW_LEVEL && 3858 Settings.Global.getInt(resolver, 3859 Settings.Global.DEVICE_PROVISIONED, 0) != 0) { 3860 mCheckedForSetup = true; 3861 3862 // See if we should be showing the platform update setup UI. 3863 final Intent intent = new Intent(Intent.ACTION_UPGRADE_SETUP); 3864 final List<ResolveInfo> ris = mContext.getPackageManager().queryIntentActivities(intent, 3865 PackageManager.MATCH_SYSTEM_ONLY | PackageManager.GET_META_DATA); 3866 if (!ris.isEmpty()) { 3867 final ResolveInfo ri = ris.get(0); 3868 String vers = ri.activityInfo.metaData != null 3869 ? ri.activityInfo.metaData.getString(Intent.METADATA_SETUP_VERSION) 3870 : null; 3871 if (vers == null && ri.activityInfo.applicationInfo.metaData != null) { 3872 vers = ri.activityInfo.applicationInfo.metaData.getString( 3873 Intent.METADATA_SETUP_VERSION); 3874 } 3875 String lastVers = Settings.Secure.getString( 3876 resolver, Settings.Secure.LAST_SETUP_SHOWN); 3877 if (vers != null && !vers.equals(lastVers)) { 3878 intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK); 3879 intent.setComponent(new ComponentName( 3880 ri.activityInfo.packageName, ri.activityInfo.name)); 3881 mActivityStarter.startActivityLocked(null, intent, null /*ephemeralIntent*/, 3882 null, ri.activityInfo, null /*rInfo*/, null, null, null, null, 0, 0, 0, 3883 null, 0, 0, 0, null, false, false, null, null, null); 3884 } 3885 } 3886 } 3887 } 3888 3889 CompatibilityInfo compatibilityInfoForPackageLocked(ApplicationInfo ai) { 3890 return mCompatModePackages.compatibilityInfoForPackageLocked(ai); 3891 } 3892 3893 void enforceNotIsolatedCaller(String caller) { 3894 if (UserHandle.isIsolated(Binder.getCallingUid())) { 3895 throw new SecurityException("Isolated process not allowed to call " + caller); 3896 } 3897 } 3898 3899 void enforceShellRestriction(String restriction, int userHandle) { 3900 if (Binder.getCallingUid() == Process.SHELL_UID) { 3901 if (userHandle < 0 || mUserController.hasUserRestriction(restriction, userHandle)) { 3902 throw new SecurityException("Shell does not have permission to access user " 3903 + userHandle); 3904 } 3905 } 3906 } 3907 3908 @Override 3909 public int getFrontActivityScreenCompatMode() { 3910 enforceNotIsolatedCaller("getFrontActivityScreenCompatMode"); 3911 synchronized (this) { 3912 return mCompatModePackages.getFrontActivityScreenCompatModeLocked(); 3913 } 3914 } 3915 3916 @Override 3917 public void setFrontActivityScreenCompatMode(int mode) { 3918 enforceCallingPermission(android.Manifest.permission.SET_SCREEN_COMPATIBILITY, 3919 "setFrontActivityScreenCompatMode"); 3920 synchronized (this) { 3921 mCompatModePackages.setFrontActivityScreenCompatModeLocked(mode); 3922 } 3923 } 3924 3925 @Override 3926 public int getPackageScreenCompatMode(String packageName) { 3927 enforceNotIsolatedCaller("getPackageScreenCompatMode"); 3928 synchronized (this) { 3929 return mCompatModePackages.getPackageScreenCompatModeLocked(packageName); 3930 } 3931 } 3932 3933 @Override 3934 public void setPackageScreenCompatMode(String packageName, int mode) { 3935 enforceCallingPermission(android.Manifest.permission.SET_SCREEN_COMPATIBILITY, 3936 "setPackageScreenCompatMode"); 3937 synchronized (this) { 3938 mCompatModePackages.setPackageScreenCompatModeLocked(packageName, mode); 3939 } 3940 } 3941 3942 @Override 3943 public boolean getPackageAskScreenCompat(String packageName) { 3944 enforceNotIsolatedCaller("getPackageAskScreenCompat"); 3945 synchronized (this) { 3946 return mCompatModePackages.getPackageAskCompatModeLocked(packageName); 3947 } 3948 } 3949 3950 @Override 3951 public void setPackageAskScreenCompat(String packageName, boolean ask) { 3952 enforceCallingPermission(android.Manifest.permission.SET_SCREEN_COMPATIBILITY, 3953 "setPackageAskScreenCompat"); 3954 synchronized (this) { 3955 mCompatModePackages.setPackageAskCompatModeLocked(packageName, ask); 3956 } 3957 } 3958 3959 private boolean hasUsageStatsPermission(String callingPackage) { 3960 final int mode = mAppOpsService.checkOperation(AppOpsManager.OP_GET_USAGE_STATS, 3961 Binder.getCallingUid(), callingPackage); 3962 if (mode == AppOpsManager.MODE_DEFAULT) { 3963 return checkCallingPermission(Manifest.permission.PACKAGE_USAGE_STATS) 3964 == PackageManager.PERMISSION_GRANTED; 3965 } 3966 return mode == AppOpsManager.MODE_ALLOWED; 3967 } 3968 3969 @Override 3970 public int getPackageProcessState(String packageName, String callingPackage) { 3971 if (!hasUsageStatsPermission(callingPackage)) { 3972 enforceCallingPermission(android.Manifest.permission.PACKAGE_USAGE_STATS, 3973 "getPackageProcessState"); 3974 } 3975 3976 int procState = ActivityManager.PROCESS_STATE_NONEXISTENT; 3977 synchronized (this) { 3978 for (int i=mLruProcesses.size()-1; i>=0; i--) { 3979 final ProcessRecord proc = mLruProcesses.get(i); 3980 if (procState == ActivityManager.PROCESS_STATE_NONEXISTENT 3981 || procState > proc.setProcState) { 3982 if (proc.pkgList.containsKey(packageName)) { 3983 procState = proc.setProcState; 3984 break; 3985 } 3986 if (proc.pkgDeps != null && proc.pkgDeps.contains(packageName)) { 3987 procState = proc.setProcState; 3988 } 3989 } 3990 } 3991 } 3992 return procState; 3993 } 3994 3995 @Override 3996 public boolean setProcessMemoryTrimLevel(String process, int userId, int level) 3997 throws RemoteException { 3998 synchronized (this) { 3999 final ProcessRecord app = findProcessLocked(process, userId, "setProcessMemoryTrimLevel"); 4000 if (app == null) { 4001 throw new IllegalArgumentException("Unknown process: " + process); 4002 } 4003 if (app.thread == null) { 4004 throw new IllegalArgumentException("Process has no app thread"); 4005 } 4006 if (app.trimMemoryLevel >= level) { 4007 throw new IllegalArgumentException( 4008 "Unable to set a higher trim level than current level"); 4009 } 4010 if (!(level < ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN || 4011 app.curProcState >= ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND)) { 4012 throw new IllegalArgumentException("Unable to set a background trim level " 4013 + "on a foreground process"); 4014 } 4015 app.thread.scheduleTrimMemory(level); 4016 app.trimMemoryLevel = level; 4017 return true; 4018 } 4019 } 4020 4021 private void dispatchProcessesChanged() { 4022 int N; 4023 synchronized (this) { 4024 N = mPendingProcessChanges.size(); 4025 if (mActiveProcessChanges.length < N) { 4026 mActiveProcessChanges = new ProcessChangeItem[N]; 4027 } 4028 mPendingProcessChanges.toArray(mActiveProcessChanges); 4029 mPendingProcessChanges.clear(); 4030 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG_PROCESS_OBSERVERS, 4031 "*** Delivering " + N + " process changes"); 4032 } 4033 4034 int i = mProcessObservers.beginBroadcast(); 4035 while (i > 0) { 4036 i--; 4037 final IProcessObserver observer = mProcessObservers.getBroadcastItem(i); 4038 if (observer != null) { 4039 try { 4040 for (int j=0; j<N; j++) { 4041 ProcessChangeItem item = mActiveProcessChanges[j]; 4042 if ((item.changes&ProcessChangeItem.CHANGE_ACTIVITIES) != 0) { 4043 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG_PROCESS_OBSERVERS, 4044 "ACTIVITIES CHANGED pid=" + item.pid + " uid=" 4045 + item.uid + ": " + item.foregroundActivities); 4046 observer.onForegroundActivitiesChanged(item.pid, item.uid, 4047 item.foregroundActivities); 4048 } 4049 if ((item.changes&ProcessChangeItem.CHANGE_PROCESS_STATE) != 0) { 4050 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG_PROCESS_OBSERVERS, 4051 "PROCSTATE CHANGED pid=" + item.pid + " uid=" + item.uid 4052 + ": " + item.processState); 4053 observer.onProcessStateChanged(item.pid, item.uid, item.processState); 4054 } 4055 } 4056 } catch (RemoteException e) { 4057 } 4058 } 4059 } 4060 mProcessObservers.finishBroadcast(); 4061 4062 synchronized (this) { 4063 for (int j=0; j<N; j++) { 4064 mAvailProcessChanges.add(mActiveProcessChanges[j]); 4065 } 4066 } 4067 } 4068 4069 private void dispatchProcessDied(int pid, int uid) { 4070 int i = mProcessObservers.beginBroadcast(); 4071 while (i > 0) { 4072 i--; 4073 final IProcessObserver observer = mProcessObservers.getBroadcastItem(i); 4074 if (observer != null) { 4075 try { 4076 observer.onProcessDied(pid, uid); 4077 } catch (RemoteException e) { 4078 } 4079 } 4080 } 4081 mProcessObservers.finishBroadcast(); 4082 } 4083 4084 private void dispatchUidsChanged() { 4085 int N; 4086 synchronized (this) { 4087 N = mPendingUidChanges.size(); 4088 if (mActiveUidChanges.length < N) { 4089 mActiveUidChanges = new UidRecord.ChangeItem[N]; 4090 } 4091 for (int i=0; i<N; i++) { 4092 final UidRecord.ChangeItem change = mPendingUidChanges.get(i); 4093 mActiveUidChanges[i] = change; 4094 if (change.uidRecord != null) { 4095 change.uidRecord.pendingChange = null; 4096 change.uidRecord = null; 4097 } 4098 } 4099 mPendingUidChanges.clear(); 4100 if (DEBUG_UID_OBSERVERS) Slog.i(TAG_UID_OBSERVERS, 4101 "*** Delivering " + N + " uid changes"); 4102 } 4103 4104 int i = mUidObservers.beginBroadcast(); 4105 while (i > 0) { 4106 i--; 4107 final IUidObserver observer = mUidObservers.getBroadcastItem(i); 4108 final int which = (Integer)mUidObservers.getBroadcastCookie(i); 4109 if (observer != null) { 4110 try { 4111 for (int j=0; j<N; j++) { 4112 UidRecord.ChangeItem item = mActiveUidChanges[j]; 4113 final int change = item.change; 4114 UidRecord validateUid = null; 4115 if (VALIDATE_UID_STATES && i == 0) { 4116 validateUid = mValidateUids.get(item.uid); 4117 if (validateUid == null && change != UidRecord.CHANGE_GONE 4118 && change != UidRecord.CHANGE_GONE_IDLE) { 4119 validateUid = new UidRecord(item.uid); 4120 mValidateUids.put(item.uid, validateUid); 4121 } 4122 } 4123 if (change == UidRecord.CHANGE_IDLE 4124 || change == UidRecord.CHANGE_GONE_IDLE) { 4125 if ((which & ActivityManager.UID_OBSERVER_IDLE) != 0) { 4126 if (DEBUG_UID_OBSERVERS) Slog.i(TAG_UID_OBSERVERS, 4127 "UID idle uid=" + item.uid); 4128 observer.onUidIdle(item.uid); 4129 } 4130 if (VALIDATE_UID_STATES && i == 0) { 4131 if (validateUid != null) { 4132 validateUid.idle = true; 4133 } 4134 } 4135 } else if (change == UidRecord.CHANGE_ACTIVE) { 4136 if ((which & ActivityManager.UID_OBSERVER_ACTIVE) != 0) { 4137 if (DEBUG_UID_OBSERVERS) Slog.i(TAG_UID_OBSERVERS, 4138 "UID active uid=" + item.uid); 4139 observer.onUidActive(item.uid); 4140 } 4141 if (VALIDATE_UID_STATES && i == 0) { 4142 validateUid.idle = false; 4143 } 4144 } 4145 if (change == UidRecord.CHANGE_GONE 4146 || change == UidRecord.CHANGE_GONE_IDLE) { 4147 if ((which & ActivityManager.UID_OBSERVER_GONE) != 0) { 4148 if (DEBUG_UID_OBSERVERS) Slog.i(TAG_UID_OBSERVERS, 4149 "UID gone uid=" + item.uid); 4150 observer.onUidGone(item.uid); 4151 } 4152 if (VALIDATE_UID_STATES && i == 0) { 4153 if (validateUid != null) { 4154 mValidateUids.remove(item.uid); 4155 } 4156 } 4157 } else { 4158 if ((which & ActivityManager.UID_OBSERVER_PROCSTATE) != 0) { 4159 if (DEBUG_UID_OBSERVERS) Slog.i(TAG_UID_OBSERVERS, 4160 "UID CHANGED uid=" + item.uid 4161 + ": " + item.processState); 4162 observer.onUidStateChanged(item.uid, item.processState); 4163 } 4164 if (VALIDATE_UID_STATES && i == 0) { 4165 validateUid.curProcState = validateUid.setProcState 4166 = item.processState; 4167 } 4168 } 4169 } 4170 } catch (RemoteException e) { 4171 } 4172 } 4173 } 4174 mUidObservers.finishBroadcast(); 4175 4176 synchronized (this) { 4177 for (int j=0; j<N; j++) { 4178 mAvailUidChanges.add(mActiveUidChanges[j]); 4179 } 4180 } 4181 } 4182 4183 @Override 4184 public final int startActivity(IApplicationThread caller, String callingPackage, 4185 Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode, 4186 int startFlags, ProfilerInfo profilerInfo, Bundle bOptions) { 4187 return startActivityAsUser(caller, callingPackage, intent, resolvedType, resultTo, 4188 resultWho, requestCode, startFlags, profilerInfo, bOptions, 4189 UserHandle.getCallingUserId()); 4190 } 4191 4192 final int startActivity(Intent intent, ActivityStackSupervisor.ActivityContainer container) { 4193 enforceNotIsolatedCaller("ActivityContainer.startActivity"); 4194 final int userId = mUserController.handleIncomingUser(Binder.getCallingPid(), 4195 Binder.getCallingUid(), mStackSupervisor.mCurrentUser, false, 4196 ActivityManagerService.ALLOW_FULL_ONLY, "ActivityContainer", null); 4197 4198 // TODO: Switch to user app stacks here. 4199 String mimeType = intent.getType(); 4200 final Uri data = intent.getData(); 4201 if (mimeType == null && data != null && "content".equals(data.getScheme())) { 4202 mimeType = getProviderMimeType(data, userId); 4203 } 4204 container.checkEmbeddedAllowedInner(userId, intent, mimeType); 4205 4206 intent.addFlags(FORCE_NEW_TASK_FLAGS); 4207 return mActivityStarter.startActivityMayWait(null, -1, null, intent, mimeType, null, null, null, 4208 null, 0, 0, null, null, null, null, false, userId, container, null); 4209 } 4210 4211 @Override 4212 public final int startActivityAsUser(IApplicationThread caller, String callingPackage, 4213 Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode, 4214 int startFlags, ProfilerInfo profilerInfo, Bundle bOptions, int userId) { 4215 enforceNotIsolatedCaller("startActivity"); 4216 userId = mUserController.handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 4217 userId, false, ALLOW_FULL_ONLY, "startActivity", null); 4218 // TODO: Switch to user app stacks here. 4219 return mActivityStarter.startActivityMayWait(caller, -1, callingPackage, intent, 4220 resolvedType, null, null, resultTo, resultWho, requestCode, startFlags, 4221 profilerInfo, null, null, bOptions, false, userId, null, null); 4222 } 4223 4224 @Override 4225 public final int startActivityAsCaller(IApplicationThread caller, String callingPackage, 4226 Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode, 4227 int startFlags, ProfilerInfo profilerInfo, Bundle bOptions, boolean ignoreTargetSecurity, 4228 int userId) { 4229 4230 // This is very dangerous -- it allows you to perform a start activity (including 4231 // permission grants) as any app that may launch one of your own activities. So 4232 // we will only allow this to be done from activities that are part of the core framework, 4233 // and then only when they are running as the system. 4234 final ActivityRecord sourceRecord; 4235 final int targetUid; 4236 final String targetPackage; 4237 synchronized (this) { 4238 if (resultTo == null) { 4239 throw new SecurityException("Must be called from an activity"); 4240 } 4241 sourceRecord = mStackSupervisor.isInAnyStackLocked(resultTo); 4242 if (sourceRecord == null) { 4243 throw new SecurityException("Called with bad activity token: " + resultTo); 4244 } 4245 if (!sourceRecord.info.packageName.equals("android")) { 4246 throw new SecurityException( 4247 "Must be called from an activity that is declared in the android package"); 4248 } 4249 if (sourceRecord.app == null) { 4250 throw new SecurityException("Called without a process attached to activity"); 4251 } 4252 if (UserHandle.getAppId(sourceRecord.app.uid) != Process.SYSTEM_UID) { 4253 // This is still okay, as long as this activity is running under the 4254 // uid of the original calling activity. 4255 if (sourceRecord.app.uid != sourceRecord.launchedFromUid) { 4256 throw new SecurityException( 4257 "Calling activity in uid " + sourceRecord.app.uid 4258 + " must be system uid or original calling uid " 4259 + sourceRecord.launchedFromUid); 4260 } 4261 } 4262 if (ignoreTargetSecurity) { 4263 if (intent.getComponent() == null) { 4264 throw new SecurityException( 4265 "Component must be specified with ignoreTargetSecurity"); 4266 } 4267 if (intent.getSelector() != null) { 4268 throw new SecurityException( 4269 "Selector not allowed with ignoreTargetSecurity"); 4270 } 4271 } 4272 targetUid = sourceRecord.launchedFromUid; 4273 targetPackage = sourceRecord.launchedFromPackage; 4274 } 4275 4276 if (userId == UserHandle.USER_NULL) { 4277 userId = UserHandle.getUserId(sourceRecord.app.uid); 4278 } 4279 4280 // TODO: Switch to user app stacks here. 4281 try { 4282 int ret = mActivityStarter.startActivityMayWait(null, targetUid, targetPackage, intent, 4283 resolvedType, null, null, resultTo, resultWho, requestCode, startFlags, null, 4284 null, null, bOptions, ignoreTargetSecurity, userId, null, null); 4285 return ret; 4286 } catch (SecurityException e) { 4287 // XXX need to figure out how to propagate to original app. 4288 // A SecurityException here is generally actually a fault of the original 4289 // calling activity (such as a fairly granting permissions), so propagate it 4290 // back to them. 4291 /* 4292 StringBuilder msg = new StringBuilder(); 4293 msg.append("While launching"); 4294 msg.append(intent.toString()); 4295 msg.append(": "); 4296 msg.append(e.getMessage()); 4297 */ 4298 throw e; 4299 } 4300 } 4301 4302 @Override 4303 public final WaitResult startActivityAndWait(IApplicationThread caller, String callingPackage, 4304 Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode, 4305 int startFlags, ProfilerInfo profilerInfo, Bundle bOptions, int userId) { 4306 enforceNotIsolatedCaller("startActivityAndWait"); 4307 userId = mUserController.handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 4308 userId, false, ALLOW_FULL_ONLY, "startActivityAndWait", null); 4309 WaitResult res = new WaitResult(); 4310 // TODO: Switch to user app stacks here. 4311 mActivityStarter.startActivityMayWait(caller, -1, callingPackage, intent, resolvedType, 4312 null, null, resultTo, resultWho, requestCode, startFlags, profilerInfo, res, null, 4313 bOptions, false, userId, null, null); 4314 return res; 4315 } 4316 4317 @Override 4318 public final int startActivityWithConfig(IApplicationThread caller, String callingPackage, 4319 Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode, 4320 int startFlags, Configuration config, Bundle bOptions, int userId) { 4321 enforceNotIsolatedCaller("startActivityWithConfig"); 4322 userId = mUserController.handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 4323 userId, false, ALLOW_FULL_ONLY, "startActivityWithConfig", null); 4324 // TODO: Switch to user app stacks here. 4325 int ret = mActivityStarter.startActivityMayWait(caller, -1, callingPackage, intent, 4326 resolvedType, null, null, resultTo, resultWho, requestCode, startFlags, 4327 null, null, config, bOptions, false, userId, null, null); 4328 return ret; 4329 } 4330 4331 @Override 4332 public int startActivityIntentSender(IApplicationThread caller, IntentSender intent, 4333 Intent fillInIntent, String resolvedType, IBinder resultTo, String resultWho, 4334 int requestCode, int flagsMask, int flagsValues, Bundle bOptions) 4335 throws TransactionTooLargeException { 4336 enforceNotIsolatedCaller("startActivityIntentSender"); 4337 // Refuse possible leaked file descriptors 4338 if (fillInIntent != null && fillInIntent.hasFileDescriptors()) { 4339 throw new IllegalArgumentException("File descriptors passed in Intent"); 4340 } 4341 4342 IIntentSender sender = intent.getTarget(); 4343 if (!(sender instanceof PendingIntentRecord)) { 4344 throw new IllegalArgumentException("Bad PendingIntent object"); 4345 } 4346 4347 PendingIntentRecord pir = (PendingIntentRecord)sender; 4348 4349 synchronized (this) { 4350 // If this is coming from the currently resumed activity, it is 4351 // effectively saying that app switches are allowed at this point. 4352 final ActivityStack stack = getFocusedStack(); 4353 if (stack.mResumedActivity != null && 4354 stack.mResumedActivity.info.applicationInfo.uid == Binder.getCallingUid()) { 4355 mAppSwitchesAllowedTime = 0; 4356 } 4357 } 4358 int ret = pir.sendInner(0, fillInIntent, resolvedType, null, null, 4359 resultTo, resultWho, requestCode, flagsMask, flagsValues, bOptions, null); 4360 return ret; 4361 } 4362 4363 @Override 4364 public int startVoiceActivity(String callingPackage, int callingPid, int callingUid, 4365 Intent intent, String resolvedType, IVoiceInteractionSession session, 4366 IVoiceInteractor interactor, int startFlags, ProfilerInfo profilerInfo, 4367 Bundle bOptions, int userId) { 4368 if (checkCallingPermission(Manifest.permission.BIND_VOICE_INTERACTION) 4369 != PackageManager.PERMISSION_GRANTED) { 4370 String msg = "Permission Denial: startVoiceActivity() from pid=" 4371 + Binder.getCallingPid() 4372 + ", uid=" + Binder.getCallingUid() 4373 + " requires " + android.Manifest.permission.BIND_VOICE_INTERACTION; 4374 Slog.w(TAG, msg); 4375 throw new SecurityException(msg); 4376 } 4377 if (session == null || interactor == null) { 4378 throw new NullPointerException("null session or interactor"); 4379 } 4380 userId = mUserController.handleIncomingUser(callingPid, callingUid, userId, false, 4381 ALLOW_FULL_ONLY, "startVoiceActivity", null); 4382 // TODO: Switch to user app stacks here. 4383 return mActivityStarter.startActivityMayWait(null, callingUid, callingPackage, intent, 4384 resolvedType, session, interactor, null, null, 0, startFlags, profilerInfo, null, 4385 null, bOptions, false, userId, null, null); 4386 } 4387 4388 @Override 4389 public void startLocalVoiceInteraction(IBinder callingActivity, Bundle options) 4390 throws RemoteException { 4391 Slog.i(TAG, "Activity tried to startVoiceInteraction"); 4392 synchronized (this) { 4393 ActivityRecord activity = getFocusedStack().topActivity(); 4394 if (ActivityRecord.forTokenLocked(callingActivity) != activity) { 4395 throw new SecurityException("Only focused activity can call startVoiceInteraction"); 4396 } 4397 if (mRunningVoice != null || activity.task.voiceSession != null 4398 || activity.voiceSession != null) { 4399 Slog.w(TAG, "Already in a voice interaction, cannot start new voice interaction"); 4400 return; 4401 } 4402 if (activity.pendingVoiceInteractionStart) { 4403 Slog.w(TAG, "Pending start of voice interaction already."); 4404 return; 4405 } 4406 activity.pendingVoiceInteractionStart = true; 4407 } 4408 LocalServices.getService(VoiceInteractionManagerInternal.class) 4409 .startLocalVoiceInteraction(callingActivity, options); 4410 } 4411 4412 @Override 4413 public void stopLocalVoiceInteraction(IBinder callingActivity) throws RemoteException { 4414 LocalServices.getService(VoiceInteractionManagerInternal.class) 4415 .stopLocalVoiceInteraction(callingActivity); 4416 } 4417 4418 @Override 4419 public boolean supportsLocalVoiceInteraction() throws RemoteException { 4420 return LocalServices.getService(VoiceInteractionManagerInternal.class) 4421 .supportsLocalVoiceInteraction(); 4422 } 4423 4424 void onLocalVoiceInteractionStartedLocked(IBinder activity, 4425 IVoiceInteractionSession voiceSession, IVoiceInteractor voiceInteractor) { 4426 ActivityRecord activityToCallback = ActivityRecord.forTokenLocked(activity); 4427 if (activityToCallback == null) return; 4428 activityToCallback.setVoiceSessionLocked(voiceSession); 4429 4430 // Inform the activity 4431 try { 4432 activityToCallback.app.thread.scheduleLocalVoiceInteractionStarted(activity, 4433 voiceInteractor); 4434 long token = Binder.clearCallingIdentity(); 4435 try { 4436 startRunningVoiceLocked(voiceSession, activityToCallback.appInfo.uid); 4437 } finally { 4438 Binder.restoreCallingIdentity(token); 4439 } 4440 // TODO: VI Should we cache the activity so that it's easier to find later 4441 // rather than scan through all the stacks and activities? 4442 } catch (RemoteException re) { 4443 activityToCallback.clearVoiceSessionLocked(); 4444 // TODO: VI Should this terminate the voice session? 4445 } 4446 } 4447 4448 @Override 4449 public void setVoiceKeepAwake(IVoiceInteractionSession session, boolean keepAwake) { 4450 synchronized (this) { 4451 if (mRunningVoice != null && mRunningVoice.asBinder() == session.asBinder()) { 4452 if (keepAwake) { 4453 mVoiceWakeLock.acquire(); 4454 } else { 4455 mVoiceWakeLock.release(); 4456 } 4457 } 4458 } 4459 } 4460 4461 @Override 4462 public boolean startNextMatchingActivity(IBinder callingActivity, 4463 Intent intent, Bundle bOptions) { 4464 // Refuse possible leaked file descriptors 4465 if (intent != null && intent.hasFileDescriptors() == true) { 4466 throw new IllegalArgumentException("File descriptors passed in Intent"); 4467 } 4468 ActivityOptions options = ActivityOptions.fromBundle(bOptions); 4469 4470 synchronized (this) { 4471 final ActivityRecord r = ActivityRecord.isInStackLocked(callingActivity); 4472 if (r == null) { 4473 ActivityOptions.abort(options); 4474 return false; 4475 } 4476 if (r.app == null || r.app.thread == null) { 4477 // The caller is not running... d'oh! 4478 ActivityOptions.abort(options); 4479 return false; 4480 } 4481 intent = new Intent(intent); 4482 // The caller is not allowed to change the data. 4483 intent.setDataAndType(r.intent.getData(), r.intent.getType()); 4484 // And we are resetting to find the next component... 4485 intent.setComponent(null); 4486 4487 final boolean debug = ((intent.getFlags() & Intent.FLAG_DEBUG_LOG_RESOLUTION) != 0); 4488 4489 ActivityInfo aInfo = null; 4490 try { 4491 List<ResolveInfo> resolves = 4492 AppGlobals.getPackageManager().queryIntentActivities( 4493 intent, r.resolvedType, 4494 PackageManager.MATCH_DEFAULT_ONLY | STOCK_PM_FLAGS, 4495 UserHandle.getCallingUserId()).getList(); 4496 4497 // Look for the original activity in the list... 4498 final int N = resolves != null ? resolves.size() : 0; 4499 for (int i=0; i<N; i++) { 4500 ResolveInfo rInfo = resolves.get(i); 4501 if (rInfo.activityInfo.packageName.equals(r.packageName) 4502 && rInfo.activityInfo.name.equals(r.info.name)) { 4503 // We found the current one... the next matching is 4504 // after it. 4505 i++; 4506 if (i<N) { 4507 aInfo = resolves.get(i).activityInfo; 4508 } 4509 if (debug) { 4510 Slog.v(TAG, "Next matching activity: found current " + r.packageName 4511 + "/" + r.info.name); 4512 Slog.v(TAG, "Next matching activity: next is " + ((aInfo == null) 4513 ? "null" : aInfo.packageName + "/" + aInfo.name)); 4514 } 4515 break; 4516 } 4517 } 4518 } catch (RemoteException e) { 4519 } 4520 4521 if (aInfo == null) { 4522 // Nobody who is next! 4523 ActivityOptions.abort(options); 4524 if (debug) Slog.d(TAG, "Next matching activity: nothing found"); 4525 return false; 4526 } 4527 4528 intent.setComponent(new ComponentName( 4529 aInfo.applicationInfo.packageName, aInfo.name)); 4530 intent.setFlags(intent.getFlags()&~( 4531 Intent.FLAG_ACTIVITY_FORWARD_RESULT| 4532 Intent.FLAG_ACTIVITY_CLEAR_TOP| 4533 Intent.FLAG_ACTIVITY_MULTIPLE_TASK| 4534 Intent.FLAG_ACTIVITY_NEW_TASK)); 4535 4536 // Okay now we need to start the new activity, replacing the 4537 // currently running activity. This is a little tricky because 4538 // we want to start the new one as if the current one is finished, 4539 // but not finish the current one first so that there is no flicker. 4540 // And thus... 4541 final boolean wasFinishing = r.finishing; 4542 r.finishing = true; 4543 4544 // Propagate reply information over to the new activity. 4545 final ActivityRecord resultTo = r.resultTo; 4546 final String resultWho = r.resultWho; 4547 final int requestCode = r.requestCode; 4548 r.resultTo = null; 4549 if (resultTo != null) { 4550 resultTo.removeResultsLocked(r, resultWho, requestCode); 4551 } 4552 4553 final long origId = Binder.clearCallingIdentity(); 4554 int res = mActivityStarter.startActivityLocked(r.app.thread, intent, 4555 null /*ephemeralIntent*/, r.resolvedType, aInfo, null /*rInfo*/, null, 4556 null, resultTo != null ? resultTo.appToken : null, resultWho, requestCode, -1, 4557 r.launchedFromUid, r.launchedFromPackage, -1, r.launchedFromUid, 0, options, 4558 false, false, null, null, null); 4559 Binder.restoreCallingIdentity(origId); 4560 4561 r.finishing = wasFinishing; 4562 if (res != ActivityManager.START_SUCCESS) { 4563 return false; 4564 } 4565 return true; 4566 } 4567 } 4568 4569 @Override 4570 public final int startActivityFromRecents(int taskId, Bundle bOptions) { 4571 if (checkCallingPermission(START_TASKS_FROM_RECENTS) != PackageManager.PERMISSION_GRANTED) { 4572 String msg = "Permission Denial: startActivityFromRecents called without " + 4573 START_TASKS_FROM_RECENTS; 4574 Slog.w(TAG, msg); 4575 throw new SecurityException(msg); 4576 } 4577 final long origId = Binder.clearCallingIdentity(); 4578 try { 4579 synchronized (this) { 4580 return mStackSupervisor.startActivityFromRecentsInner(taskId, bOptions); 4581 } 4582 } finally { 4583 Binder.restoreCallingIdentity(origId); 4584 } 4585 } 4586 4587 final int startActivityInPackage(int uid, String callingPackage, 4588 Intent intent, String resolvedType, IBinder resultTo, 4589 String resultWho, int requestCode, int startFlags, Bundle bOptions, int userId, 4590 IActivityContainer container, TaskRecord inTask) { 4591 4592 userId = mUserController.handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 4593 userId, false, ALLOW_FULL_ONLY, "startActivityInPackage", null); 4594 4595 // TODO: Switch to user app stacks here. 4596 int ret = mActivityStarter.startActivityMayWait(null, uid, callingPackage, intent, 4597 resolvedType, null, null, resultTo, resultWho, requestCode, startFlags, 4598 null, null, null, bOptions, false, userId, container, inTask); 4599 return ret; 4600 } 4601 4602 @Override 4603 public final int startActivities(IApplicationThread caller, String callingPackage, 4604 Intent[] intents, String[] resolvedTypes, IBinder resultTo, Bundle bOptions, 4605 int userId) { 4606 enforceNotIsolatedCaller("startActivities"); 4607 userId = mUserController.handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 4608 userId, false, ALLOW_FULL_ONLY, "startActivity", null); 4609 // TODO: Switch to user app stacks here. 4610 int ret = mActivityStarter.startActivities(caller, -1, callingPackage, intents, 4611 resolvedTypes, resultTo, bOptions, userId); 4612 return ret; 4613 } 4614 4615 final int startActivitiesInPackage(int uid, String callingPackage, 4616 Intent[] intents, String[] resolvedTypes, IBinder resultTo, 4617 Bundle bOptions, int userId) { 4618 4619 userId = mUserController.handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 4620 userId, false, ALLOW_FULL_ONLY, "startActivityInPackage", null); 4621 // TODO: Switch to user app stacks here. 4622 int ret = mActivityStarter.startActivities(null, uid, callingPackage, intents, resolvedTypes, 4623 resultTo, bOptions, userId); 4624 return ret; 4625 } 4626 4627 @Override 4628 public void reportActivityFullyDrawn(IBinder token) { 4629 synchronized (this) { 4630 ActivityRecord r = ActivityRecord.isInStackLocked(token); 4631 if (r == null) { 4632 return; 4633 } 4634 r.reportFullyDrawnLocked(); 4635 } 4636 } 4637 4638 @Override 4639 public void setRequestedOrientation(IBinder token, int requestedOrientation) { 4640 synchronized (this) { 4641 ActivityRecord r = ActivityRecord.isInStackLocked(token); 4642 if (r == null) { 4643 return; 4644 } 4645 final long origId = Binder.clearCallingIdentity(); 4646 try { 4647 r.setRequestedOrientation(requestedOrientation); 4648 } finally { 4649 Binder.restoreCallingIdentity(origId); 4650 } 4651 } 4652 } 4653 4654 @Override 4655 public int getRequestedOrientation(IBinder token) { 4656 synchronized (this) { 4657 ActivityRecord r = ActivityRecord.isInStackLocked(token); 4658 if (r == null) { 4659 return ActivityInfo.SCREEN_ORIENTATION_UNSPECIFIED; 4660 } 4661 return mWindowManager.getAppOrientation(r.appToken); 4662 } 4663 } 4664 4665 @Override 4666 public final void requestActivityRelaunch(IBinder token) { 4667 synchronized(this) { 4668 ActivityRecord r = ActivityRecord.isInStackLocked(token); 4669 if (r == null) { 4670 return; 4671 } 4672 final long origId = Binder.clearCallingIdentity(); 4673 try { 4674 r.forceNewConfig = true; 4675 r.ensureActivityConfigurationLocked(0 /* globalChanges */, 4676 false /* preserveWindow */); 4677 } finally { 4678 Binder.restoreCallingIdentity(origId); 4679 } 4680 } 4681 } 4682 4683 /** 4684 * This is the internal entry point for handling Activity.finish(). 4685 * 4686 * @param token The Binder token referencing the Activity we want to finish. 4687 * @param resultCode Result code, if any, from this Activity. 4688 * @param resultData Result data (Intent), if any, from this Activity. 4689 * @param finishTask Whether to finish the task associated with this Activity. 4690 * 4691 * @return Returns true if the activity successfully finished, or false if it is still running. 4692 */ 4693 @Override 4694 public final boolean finishActivity(IBinder token, int resultCode, Intent resultData, 4695 int finishTask) { 4696 // Refuse possible leaked file descriptors 4697 if (resultData != null && resultData.hasFileDescriptors() == true) { 4698 throw new IllegalArgumentException("File descriptors passed in Intent"); 4699 } 4700 4701 synchronized(this) { 4702 ActivityRecord r = ActivityRecord.isInStackLocked(token); 4703 if (r == null) { 4704 return true; 4705 } 4706 // Keep track of the root activity of the task before we finish it 4707 TaskRecord tr = r.task; 4708 ActivityRecord rootR = tr.getRootActivity(); 4709 if (rootR == null) { 4710 Slog.w(TAG, "Finishing task with all activities already finished"); 4711 } 4712 // Do not allow task to finish if last task in lockTask mode. Launchable priv-apps can 4713 // finish. 4714 if (tr.mLockTaskAuth != LOCK_TASK_AUTH_LAUNCHABLE_PRIV && rootR == r && 4715 mStackSupervisor.isLastLockedTask(tr)) { 4716 Slog.i(TAG, "Not finishing task in lock task mode"); 4717 mStackSupervisor.showLockTaskToast(); 4718 return false; 4719 } 4720 if (mController != null) { 4721 // Find the first activity that is not finishing. 4722 ActivityRecord next = r.getStack().topRunningActivityLocked(token, 0); 4723 if (next != null) { 4724 // ask watcher if this is allowed 4725 boolean resumeOK = true; 4726 try { 4727 resumeOK = mController.activityResuming(next.packageName); 4728 } catch (RemoteException e) { 4729 mController = null; 4730 Watchdog.getInstance().setActivityController(null); 4731 } 4732 4733 if (!resumeOK) { 4734 Slog.i(TAG, "Not finishing activity because controller resumed"); 4735 return false; 4736 } 4737 } 4738 } 4739 final long origId = Binder.clearCallingIdentity(); 4740 try { 4741 boolean res; 4742 final boolean finishWithRootActivity = 4743 finishTask == Activity.FINISH_TASK_WITH_ROOT_ACTIVITY; 4744 if (finishTask == Activity.FINISH_TASK_WITH_ACTIVITY 4745 || (finishWithRootActivity && r == rootR)) { 4746 // If requested, remove the task that is associated to this activity only if it 4747 // was the root activity in the task. The result code and data is ignored 4748 // because we don't support returning them across task boundaries. Also, to 4749 // keep backwards compatibility we remove the task from recents when finishing 4750 // task with root activity. 4751 res = removeTaskByIdLocked(tr.taskId, false, finishWithRootActivity); 4752 if (!res) { 4753 Slog.i(TAG, "Removing task failed to finish activity"); 4754 } 4755 } else { 4756 res = tr.getStack().requestFinishActivityLocked(token, resultCode, 4757 resultData, "app-request", true); 4758 if (!res) { 4759 Slog.i(TAG, "Failed to finish by app-request"); 4760 } 4761 } 4762 return res; 4763 } finally { 4764 Binder.restoreCallingIdentity(origId); 4765 } 4766 } 4767 } 4768 4769 @Override 4770 public final void finishHeavyWeightApp() { 4771 if (checkCallingPermission(android.Manifest.permission.FORCE_STOP_PACKAGES) 4772 != PackageManager.PERMISSION_GRANTED) { 4773 String msg = "Permission Denial: finishHeavyWeightApp() from pid=" 4774 + Binder.getCallingPid() 4775 + ", uid=" + Binder.getCallingUid() 4776 + " requires " + android.Manifest.permission.FORCE_STOP_PACKAGES; 4777 Slog.w(TAG, msg); 4778 throw new SecurityException(msg); 4779 } 4780 4781 synchronized(this) { 4782 if (mHeavyWeightProcess == null) { 4783 return; 4784 } 4785 4786 ArrayList<ActivityRecord> activities = new ArrayList<>(mHeavyWeightProcess.activities); 4787 for (int i = 0; i < activities.size(); i++) { 4788 ActivityRecord r = activities.get(i); 4789 if (!r.finishing && r.isInStackLocked()) { 4790 r.getStack().finishActivityLocked(r, Activity.RESULT_CANCELED, 4791 null, "finish-heavy", true); 4792 } 4793 } 4794 4795 mHandler.sendMessage(mHandler.obtainMessage(CANCEL_HEAVY_NOTIFICATION_MSG, 4796 mHeavyWeightProcess.userId, 0)); 4797 mHeavyWeightProcess = null; 4798 } 4799 } 4800 4801 @Override 4802 public void crashApplication(int uid, int initialPid, String packageName, 4803 String message) { 4804 if (checkCallingPermission(android.Manifest.permission.FORCE_STOP_PACKAGES) 4805 != PackageManager.PERMISSION_GRANTED) { 4806 String msg = "Permission Denial: crashApplication() from pid=" 4807 + Binder.getCallingPid() 4808 + ", uid=" + Binder.getCallingUid() 4809 + " requires " + android.Manifest.permission.FORCE_STOP_PACKAGES; 4810 Slog.w(TAG, msg); 4811 throw new SecurityException(msg); 4812 } 4813 4814 synchronized(this) { 4815 mAppErrors.scheduleAppCrashLocked(uid, initialPid, packageName, message); 4816 } 4817 } 4818 4819 @Override 4820 public final void finishSubActivity(IBinder token, String resultWho, 4821 int requestCode) { 4822 synchronized(this) { 4823 final long origId = Binder.clearCallingIdentity(); 4824 ActivityRecord r = ActivityRecord.isInStackLocked(token); 4825 if (r != null) { 4826 r.getStack().finishSubActivityLocked(r, resultWho, requestCode); 4827 } 4828 Binder.restoreCallingIdentity(origId); 4829 } 4830 } 4831 4832 @Override 4833 public boolean finishActivityAffinity(IBinder token) { 4834 synchronized(this) { 4835 final long origId = Binder.clearCallingIdentity(); 4836 try { 4837 ActivityRecord r = ActivityRecord.isInStackLocked(token); 4838 if (r == null) { 4839 return false; 4840 } 4841 4842 // Do not allow task to finish if last task in lockTask mode. Launchable priv-apps 4843 // can finish. 4844 final TaskRecord task = r.task; 4845 if (task.mLockTaskAuth != LOCK_TASK_AUTH_LAUNCHABLE_PRIV && 4846 mStackSupervisor.isLastLockedTask(task) && task.getRootActivity() == r) { 4847 mStackSupervisor.showLockTaskToast(); 4848 return false; 4849 } 4850 return task.getStack().finishActivityAffinityLocked(r); 4851 } finally { 4852 Binder.restoreCallingIdentity(origId); 4853 } 4854 } 4855 } 4856 4857 @Override 4858 public void finishVoiceTask(IVoiceInteractionSession session) { 4859 synchronized (this) { 4860 final long origId = Binder.clearCallingIdentity(); 4861 try { 4862 // TODO: VI Consider treating local voice interactions and voice tasks 4863 // differently here 4864 mStackSupervisor.finishVoiceTask(session); 4865 } finally { 4866 Binder.restoreCallingIdentity(origId); 4867 } 4868 } 4869 4870 } 4871 4872 @Override 4873 public boolean releaseActivityInstance(IBinder token) { 4874 synchronized(this) { 4875 final long origId = Binder.clearCallingIdentity(); 4876 try { 4877 ActivityRecord r = ActivityRecord.isInStackLocked(token); 4878 if (r == null) { 4879 return false; 4880 } 4881 return r.getStack().safelyDestroyActivityLocked(r, "app-req"); 4882 } finally { 4883 Binder.restoreCallingIdentity(origId); 4884 } 4885 } 4886 } 4887 4888 @Override 4889 public void releaseSomeActivities(IApplicationThread appInt) { 4890 synchronized(this) { 4891 final long origId = Binder.clearCallingIdentity(); 4892 try { 4893 ProcessRecord app = getRecordForAppLocked(appInt); 4894 mStackSupervisor.releaseSomeActivitiesLocked(app, "low-mem"); 4895 } finally { 4896 Binder.restoreCallingIdentity(origId); 4897 } 4898 } 4899 } 4900 4901 @Override 4902 public boolean willActivityBeVisible(IBinder token) { 4903 synchronized(this) { 4904 ActivityStack stack = ActivityRecord.getStackLocked(token); 4905 if (stack != null) { 4906 return stack.willActivityBeVisibleLocked(token); 4907 } 4908 return false; 4909 } 4910 } 4911 4912 @Override 4913 public void overridePendingTransition(IBinder token, String packageName, 4914 int enterAnim, int exitAnim) { 4915 synchronized(this) { 4916 ActivityRecord self = ActivityRecord.isInStackLocked(token); 4917 if (self == null) { 4918 return; 4919 } 4920 4921 final long origId = Binder.clearCallingIdentity(); 4922 4923 if (self.state == ActivityState.RESUMED 4924 || self.state == ActivityState.PAUSING) { 4925 mWindowManager.overridePendingAppTransition(packageName, 4926 enterAnim, exitAnim, null); 4927 } 4928 4929 Binder.restoreCallingIdentity(origId); 4930 } 4931 } 4932 4933 /** 4934 * Main function for removing an existing process from the activity manager 4935 * as a result of that process going away. Clears out all connections 4936 * to the process. 4937 */ 4938 private final void handleAppDiedLocked(ProcessRecord app, 4939 boolean restarting, boolean allowRestart) { 4940 int pid = app.pid; 4941 boolean kept = cleanUpApplicationRecordLocked(app, restarting, allowRestart, -1, 4942 false /*replacingPid*/); 4943 if (!kept && !restarting) { 4944 removeLruProcessLocked(app); 4945 if (pid > 0) { 4946 ProcessList.remove(pid); 4947 } 4948 } 4949 4950 if (mProfileProc == app) { 4951 clearProfilerLocked(); 4952 } 4953 4954 // Remove this application's activities from active lists. 4955 boolean hasVisibleActivities = mStackSupervisor.handleAppDiedLocked(app); 4956 4957 app.activities.clear(); 4958 4959 if (app.instrumentationClass != null) { 4960 Slog.w(TAG, "Crash of app " + app.processName 4961 + " running instrumentation " + app.instrumentationClass); 4962 Bundle info = new Bundle(); 4963 info.putString("shortMsg", "Process crashed."); 4964 finishInstrumentationLocked(app, Activity.RESULT_CANCELED, info); 4965 } 4966 4967 mWindowManager.deferSurfaceLayout(); 4968 try { 4969 if (!restarting && hasVisibleActivities 4970 && !mStackSupervisor.resumeFocusedStackTopActivityLocked()) { 4971 // If there was nothing to resume, and we are not already restarting this process, but 4972 // there is a visible activity that is hosted by the process... then make sure all 4973 // visible activities are running, taking care of restarting this process. 4974 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0, !PRESERVE_WINDOWS); 4975 } 4976 } finally { 4977 mWindowManager.continueSurfaceLayout(); 4978 } 4979 } 4980 4981 private final int getLRURecordIndexForAppLocked(IApplicationThread thread) { 4982 IBinder threadBinder = thread.asBinder(); 4983 // Find the application record. 4984 for (int i=mLruProcesses.size()-1; i>=0; i--) { 4985 ProcessRecord rec = mLruProcesses.get(i); 4986 if (rec.thread != null && rec.thread.asBinder() == threadBinder) { 4987 return i; 4988 } 4989 } 4990 return -1; 4991 } 4992 4993 final ProcessRecord getRecordForAppLocked( 4994 IApplicationThread thread) { 4995 if (thread == null) { 4996 return null; 4997 } 4998 4999 int appIndex = getLRURecordIndexForAppLocked(thread); 5000 return appIndex >= 0 ? mLruProcesses.get(appIndex) : null; 5001 } 5002 5003 final void doLowMemReportIfNeededLocked(ProcessRecord dyingProc) { 5004 // If there are no longer any background processes running, 5005 // and the app that died was not running instrumentation, 5006 // then tell everyone we are now low on memory. 5007 boolean haveBg = false; 5008 for (int i=mLruProcesses.size()-1; i>=0; i--) { 5009 ProcessRecord rec = mLruProcesses.get(i); 5010 if (rec.thread != null 5011 && rec.setProcState >= ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 5012 haveBg = true; 5013 break; 5014 } 5015 } 5016 5017 if (!haveBg) { 5018 boolean doReport = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 5019 if (doReport) { 5020 long now = SystemClock.uptimeMillis(); 5021 if (now < (mLastMemUsageReportTime+5*60*1000)) { 5022 doReport = false; 5023 } else { 5024 mLastMemUsageReportTime = now; 5025 } 5026 } 5027 final ArrayList<ProcessMemInfo> memInfos 5028 = doReport ? new ArrayList<ProcessMemInfo>(mLruProcesses.size()) : null; 5029 EventLog.writeEvent(EventLogTags.AM_LOW_MEMORY, mLruProcesses.size()); 5030 long now = SystemClock.uptimeMillis(); 5031 for (int i=mLruProcesses.size()-1; i>=0; i--) { 5032 ProcessRecord rec = mLruProcesses.get(i); 5033 if (rec == dyingProc || rec.thread == null) { 5034 continue; 5035 } 5036 if (doReport) { 5037 memInfos.add(new ProcessMemInfo(rec.processName, rec.pid, rec.setAdj, 5038 rec.setProcState, rec.adjType, rec.makeAdjReason())); 5039 } 5040 if ((rec.lastLowMemory+GC_MIN_INTERVAL) <= now) { 5041 // The low memory report is overriding any current 5042 // state for a GC request. Make sure to do 5043 // heavy/important/visible/foreground processes first. 5044 if (rec.setAdj <= ProcessList.HEAVY_WEIGHT_APP_ADJ) { 5045 rec.lastRequestedGc = 0; 5046 } else { 5047 rec.lastRequestedGc = rec.lastLowMemory; 5048 } 5049 rec.reportLowMemory = true; 5050 rec.lastLowMemory = now; 5051 mProcessesToGc.remove(rec); 5052 addProcessToGcListLocked(rec); 5053 } 5054 } 5055 if (doReport) { 5056 Message msg = mHandler.obtainMessage(REPORT_MEM_USAGE_MSG, memInfos); 5057 mHandler.sendMessage(msg); 5058 } 5059 scheduleAppGcsLocked(); 5060 } 5061 } 5062 5063 final void appDiedLocked(ProcessRecord app) { 5064 appDiedLocked(app, app.pid, app.thread, false); 5065 } 5066 5067 final void appDiedLocked(ProcessRecord app, int pid, IApplicationThread thread, 5068 boolean fromBinderDied) { 5069 // First check if this ProcessRecord is actually active for the pid. 5070 synchronized (mPidsSelfLocked) { 5071 ProcessRecord curProc = mPidsSelfLocked.get(pid); 5072 if (curProc != app) { 5073 Slog.w(TAG, "Spurious death for " + app + ", curProc for " + pid + ": " + curProc); 5074 return; 5075 } 5076 } 5077 5078 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 5079 synchronized (stats) { 5080 stats.noteProcessDiedLocked(app.info.uid, pid); 5081 } 5082 5083 if (!app.killed) { 5084 if (!fromBinderDied) { 5085 Process.killProcessQuiet(pid); 5086 } 5087 killProcessGroup(app.uid, pid); 5088 app.killed = true; 5089 } 5090 5091 // Clean up already done if the process has been re-started. 5092 if (app.pid == pid && app.thread != null && 5093 app.thread.asBinder() == thread.asBinder()) { 5094 boolean doLowMem = app.instrumentationClass == null; 5095 boolean doOomAdj = doLowMem; 5096 if (!app.killedByAm) { 5097 Slog.i(TAG, "Process " + app.processName + " (pid " + pid 5098 + ") has died"); 5099 mAllowLowerMemLevel = true; 5100 } else { 5101 // Note that we always want to do oom adj to update our state with the 5102 // new number of procs. 5103 mAllowLowerMemLevel = false; 5104 doLowMem = false; 5105 } 5106 EventLog.writeEvent(EventLogTags.AM_PROC_DIED, app.userId, app.pid, app.processName); 5107 if (DEBUG_CLEANUP) Slog.v(TAG_CLEANUP, 5108 "Dying app: " + app + ", pid: " + pid + ", thread: " + thread.asBinder()); 5109 handleAppDiedLocked(app, false, true); 5110 5111 if (doOomAdj) { 5112 updateOomAdjLocked(); 5113 } 5114 if (doLowMem) { 5115 doLowMemReportIfNeededLocked(app); 5116 } 5117 } else if (app.pid != pid) { 5118 // A new process has already been started. 5119 Slog.i(TAG, "Process " + app.processName + " (pid " + pid 5120 + ") has died and restarted (pid " + app.pid + ")."); 5121 EventLog.writeEvent(EventLogTags.AM_PROC_DIED, app.userId, app.pid, app.processName); 5122 } else if (DEBUG_PROCESSES) { 5123 Slog.d(TAG_PROCESSES, "Received spurious death notification for thread " 5124 + thread.asBinder()); 5125 } 5126 } 5127 5128 /** 5129 * If a stack trace dump file is configured, dump process stack traces. 5130 * @param clearTraces causes the dump file to be erased prior to the new 5131 * traces being written, if true; when false, the new traces will be 5132 * appended to any existing file content. 5133 * @param firstPids of dalvik VM processes to dump stack traces for first 5134 * @param lastPids of dalvik VM processes to dump stack traces for last 5135 * @param nativeProcs optional list of native process names to dump stack crawls 5136 * @return file containing stack traces, or null if no dump file is configured 5137 */ 5138 public static File dumpStackTraces(boolean clearTraces, ArrayList<Integer> firstPids, 5139 ProcessCpuTracker processCpuTracker, SparseArray<Boolean> lastPids, String[] nativeProcs) { 5140 String tracesPath = SystemProperties.get("dalvik.vm.stack-trace-file", null); 5141 if (tracesPath == null || tracesPath.length() == 0) { 5142 return null; 5143 } 5144 5145 File tracesFile = new File(tracesPath); 5146 try { 5147 if (clearTraces && tracesFile.exists()) tracesFile.delete(); 5148 tracesFile.createNewFile(); 5149 FileUtils.setPermissions(tracesFile.getPath(), 0666, -1, -1); // -rw-rw-rw- 5150 } catch (IOException e) { 5151 Slog.w(TAG, "Unable to prepare ANR traces file: " + tracesPath, e); 5152 return null; 5153 } 5154 5155 dumpStackTraces(tracesPath, firstPids, processCpuTracker, lastPids, nativeProcs); 5156 return tracesFile; 5157 } 5158 5159 private static void dumpStackTraces(String tracesPath, ArrayList<Integer> firstPids, 5160 ProcessCpuTracker processCpuTracker, SparseArray<Boolean> lastPids, String[] nativeProcs) { 5161 // Use a FileObserver to detect when traces finish writing. 5162 // The order of traces is considered important to maintain for legibility. 5163 FileObserver observer = new FileObserver(tracesPath, FileObserver.CLOSE_WRITE) { 5164 @Override 5165 public synchronized void onEvent(int event, String path) { notify(); } 5166 }; 5167 5168 try { 5169 observer.startWatching(); 5170 5171 // First collect all of the stacks of the most important pids. 5172 if (firstPids != null) { 5173 try { 5174 int num = firstPids.size(); 5175 for (int i = 0; i < num; i++) { 5176 synchronized (observer) { 5177 if (DEBUG_ANR) Slog.d(TAG, "Collecting stacks for pid " 5178 + firstPids.get(i)); 5179 final long sime = SystemClock.elapsedRealtime(); 5180 Process.sendSignal(firstPids.get(i), Process.SIGNAL_QUIT); 5181 observer.wait(1000); // Wait for write-close, give up after 1 sec 5182 if (DEBUG_ANR) Slog.d(TAG, "Done with pid " + firstPids.get(i) 5183 + " in " + (SystemClock.elapsedRealtime()-sime) + "ms"); 5184 } 5185 } 5186 } catch (InterruptedException e) { 5187 Slog.wtf(TAG, e); 5188 } 5189 } 5190 5191 // Next collect the stacks of the native pids 5192 if (nativeProcs != null) { 5193 int[] pids = Process.getPidsForCommands(nativeProcs); 5194 if (pids != null) { 5195 for (int pid : pids) { 5196 if (DEBUG_ANR) Slog.d(TAG, "Collecting stacks for native pid " + pid); 5197 final long sime = SystemClock.elapsedRealtime(); 5198 Debug.dumpNativeBacktraceToFile(pid, tracesPath); 5199 if (DEBUG_ANR) Slog.d(TAG, "Done with native pid " + pid 5200 + " in " + (SystemClock.elapsedRealtime()-sime) + "ms"); 5201 } 5202 } 5203 } 5204 5205 // Lastly, measure CPU usage. 5206 if (processCpuTracker != null) { 5207 processCpuTracker.init(); 5208 System.gc(); 5209 processCpuTracker.update(); 5210 try { 5211 synchronized (processCpuTracker) { 5212 processCpuTracker.wait(500); // measure over 1/2 second. 5213 } 5214 } catch (InterruptedException e) { 5215 } 5216 processCpuTracker.update(); 5217 5218 // We'll take the stack crawls of just the top apps using CPU. 5219 final int N = processCpuTracker.countWorkingStats(); 5220 int numProcs = 0; 5221 for (int i=0; i<N && numProcs<5; i++) { 5222 ProcessCpuTracker.Stats stats = processCpuTracker.getWorkingStats(i); 5223 if (lastPids.indexOfKey(stats.pid) >= 0) { 5224 numProcs++; 5225 try { 5226 synchronized (observer) { 5227 if (DEBUG_ANR) Slog.d(TAG, "Collecting stacks for extra pid " 5228 + stats.pid); 5229 final long stime = SystemClock.elapsedRealtime(); 5230 Process.sendSignal(stats.pid, Process.SIGNAL_QUIT); 5231 observer.wait(1000); // Wait for write-close, give up after 1 sec 5232 if (DEBUG_ANR) Slog.d(TAG, "Done with extra pid " + stats.pid 5233 + " in " + (SystemClock.elapsedRealtime()-stime) + "ms"); 5234 } 5235 } catch (InterruptedException e) { 5236 Slog.wtf(TAG, e); 5237 } 5238 } else if (DEBUG_ANR) { 5239 Slog.d(TAG, "Skipping next CPU consuming process, not a java proc: " 5240 + stats.pid); 5241 } 5242 } 5243 } 5244 } finally { 5245 observer.stopWatching(); 5246 } 5247 } 5248 5249 final void logAppTooSlow(ProcessRecord app, long startTime, String msg) { 5250 if (true || IS_USER_BUILD) { 5251 return; 5252 } 5253 String tracesPath = SystemProperties.get("dalvik.vm.stack-trace-file", null); 5254 if (tracesPath == null || tracesPath.length() == 0) { 5255 return; 5256 } 5257 5258 StrictMode.ThreadPolicy oldPolicy = StrictMode.allowThreadDiskReads(); 5259 StrictMode.allowThreadDiskWrites(); 5260 try { 5261 final File tracesFile = new File(tracesPath); 5262 final File tracesDir = tracesFile.getParentFile(); 5263 final File tracesTmp = new File(tracesDir, "__tmp__"); 5264 try { 5265 if (tracesFile.exists()) { 5266 tracesTmp.delete(); 5267 tracesFile.renameTo(tracesTmp); 5268 } 5269 StringBuilder sb = new StringBuilder(); 5270 Time tobj = new Time(); 5271 tobj.set(System.currentTimeMillis()); 5272 sb.append(tobj.format("%Y-%m-%d %H:%M:%S")); 5273 sb.append(": "); 5274 TimeUtils.formatDuration(SystemClock.uptimeMillis()-startTime, sb); 5275 sb.append(" since "); 5276 sb.append(msg); 5277 FileOutputStream fos = new FileOutputStream(tracesFile); 5278 fos.write(sb.toString().getBytes()); 5279 if (app == null) { 5280 fos.write("\n*** No application process!".getBytes()); 5281 } 5282 fos.close(); 5283 FileUtils.setPermissions(tracesFile.getPath(), 0666, -1, -1); // -rw-rw-rw- 5284 } catch (IOException e) { 5285 Slog.w(TAG, "Unable to prepare slow app traces file: " + tracesPath, e); 5286 return; 5287 } 5288 5289 if (app != null) { 5290 ArrayList<Integer> firstPids = new ArrayList<Integer>(); 5291 firstPids.add(app.pid); 5292 dumpStackTraces(tracesPath, firstPids, null, null, null); 5293 } 5294 5295 File lastTracesFile = null; 5296 File curTracesFile = null; 5297 for (int i=9; i>=0; i--) { 5298 String name = String.format(Locale.US, "slow%02d.txt", i); 5299 curTracesFile = new File(tracesDir, name); 5300 if (curTracesFile.exists()) { 5301 if (lastTracesFile != null) { 5302 curTracesFile.renameTo(lastTracesFile); 5303 } else { 5304 curTracesFile.delete(); 5305 } 5306 } 5307 lastTracesFile = curTracesFile; 5308 } 5309 tracesFile.renameTo(curTracesFile); 5310 if (tracesTmp.exists()) { 5311 tracesTmp.renameTo(tracesFile); 5312 } 5313 } finally { 5314 StrictMode.setThreadPolicy(oldPolicy); 5315 } 5316 } 5317 5318 final void showLaunchWarningLocked(final ActivityRecord cur, final ActivityRecord next) { 5319 if (!mLaunchWarningShown) { 5320 mLaunchWarningShown = true; 5321 mUiHandler.post(new Runnable() { 5322 @Override 5323 public void run() { 5324 synchronized (ActivityManagerService.this) { 5325 final Dialog d = new LaunchWarningWindow(mContext, cur, next); 5326 d.show(); 5327 mUiHandler.postDelayed(new Runnable() { 5328 @Override 5329 public void run() { 5330 synchronized (ActivityManagerService.this) { 5331 d.dismiss(); 5332 mLaunchWarningShown = false; 5333 } 5334 } 5335 }, 4000); 5336 } 5337 } 5338 }); 5339 } 5340 } 5341 5342 @Override 5343 public boolean clearApplicationUserData(final String packageName, 5344 final IPackageDataObserver observer, int userId) { 5345 enforceNotIsolatedCaller("clearApplicationUserData"); 5346 int uid = Binder.getCallingUid(); 5347 int pid = Binder.getCallingPid(); 5348 userId = mUserController.handleIncomingUser(pid, uid, userId, false, 5349 ALLOW_FULL_ONLY, "clearApplicationUserData", null); 5350 5351 5352 long callingId = Binder.clearCallingIdentity(); 5353 try { 5354 IPackageManager pm = AppGlobals.getPackageManager(); 5355 int pkgUid = -1; 5356 synchronized(this) { 5357 if (getPackageManagerInternalLocked().isPackageDataProtected( 5358 userId, packageName)) { 5359 throw new SecurityException( 5360 "Cannot clear data for a protected package: " + packageName); 5361 } 5362 5363 try { 5364 pkgUid = pm.getPackageUid(packageName, MATCH_UNINSTALLED_PACKAGES, userId); 5365 } catch (RemoteException e) { 5366 } 5367 if (pkgUid == -1) { 5368 Slog.w(TAG, "Invalid packageName: " + packageName); 5369 if (observer != null) { 5370 try { 5371 observer.onRemoveCompleted(packageName, false); 5372 } catch (RemoteException e) { 5373 Slog.i(TAG, "Observer no longer exists."); 5374 } 5375 } 5376 return false; 5377 } 5378 if (uid == pkgUid || checkComponentPermission( 5379 android.Manifest.permission.CLEAR_APP_USER_DATA, 5380 pid, uid, -1, true) 5381 == PackageManager.PERMISSION_GRANTED) { 5382 forceStopPackageLocked(packageName, pkgUid, "clear data"); 5383 } else { 5384 throw new SecurityException("PID " + pid + " does not have permission " 5385 + android.Manifest.permission.CLEAR_APP_USER_DATA + " to clear data" 5386 + " of package " + packageName); 5387 } 5388 5389 // Remove all tasks match the cleared application package and user 5390 for (int i = mRecentTasks.size() - 1; i >= 0; i--) { 5391 final TaskRecord tr = mRecentTasks.get(i); 5392 final String taskPackageName = 5393 tr.getBaseIntent().getComponent().getPackageName(); 5394 if (tr.userId != userId) continue; 5395 if (!taskPackageName.equals(packageName)) continue; 5396 removeTaskByIdLocked(tr.taskId, false, REMOVE_FROM_RECENTS); 5397 } 5398 } 5399 5400 final int pkgUidF = pkgUid; 5401 final int userIdF = userId; 5402 final IPackageDataObserver localObserver = new IPackageDataObserver.Stub() { 5403 @Override 5404 public void onRemoveCompleted(String packageName, boolean succeeded) 5405 throws RemoteException { 5406 synchronized (ActivityManagerService.this) { 5407 finishForceStopPackageLocked(packageName, pkgUidF); 5408 } 5409 5410 final Intent intent = new Intent(Intent.ACTION_PACKAGE_DATA_CLEARED, 5411 Uri.fromParts("package", packageName, null)); 5412 intent.putExtra(Intent.EXTRA_UID, pkgUidF); 5413 intent.putExtra(Intent.EXTRA_USER_HANDLE, UserHandle.getUserId(pkgUidF)); 5414 broadcastIntentInPackage("android", Process.SYSTEM_UID, intent, 5415 null, null, 0, null, null, null, null, false, false, userIdF); 5416 5417 if (observer != null) { 5418 observer.onRemoveCompleted(packageName, succeeded); 5419 } 5420 } 5421 }; 5422 5423 try { 5424 // Clear application user data 5425 pm.clearApplicationUserData(packageName, localObserver, userId); 5426 5427 synchronized(this) { 5428 // Remove all permissions granted from/to this package 5429 removeUriPermissionsForPackageLocked(packageName, userId, true); 5430 } 5431 5432 // Remove all zen rules created by this package; revoke it's zen access. 5433 INotificationManager inm = NotificationManager.getService(); 5434 inm.removeAutomaticZenRules(packageName); 5435 inm.setNotificationPolicyAccessGranted(packageName, false); 5436 5437 } catch (RemoteException e) { 5438 } 5439 } finally { 5440 Binder.restoreCallingIdentity(callingId); 5441 } 5442 return true; 5443 } 5444 5445 @Override 5446 public void killBackgroundProcesses(final String packageName, int userId) { 5447 if (checkCallingPermission(android.Manifest.permission.KILL_BACKGROUND_PROCESSES) 5448 != PackageManager.PERMISSION_GRANTED && 5449 checkCallingPermission(android.Manifest.permission.RESTART_PACKAGES) 5450 != PackageManager.PERMISSION_GRANTED) { 5451 String msg = "Permission Denial: killBackgroundProcesses() from pid=" 5452 + Binder.getCallingPid() 5453 + ", uid=" + Binder.getCallingUid() 5454 + " requires " + android.Manifest.permission.KILL_BACKGROUND_PROCESSES; 5455 Slog.w(TAG, msg); 5456 throw new SecurityException(msg); 5457 } 5458 5459 userId = mUserController.handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 5460 userId, true, ALLOW_FULL_ONLY, "killBackgroundProcesses", null); 5461 long callingId = Binder.clearCallingIdentity(); 5462 try { 5463 IPackageManager pm = AppGlobals.getPackageManager(); 5464 synchronized(this) { 5465 int appId = -1; 5466 try { 5467 appId = UserHandle.getAppId( 5468 pm.getPackageUid(packageName, MATCH_DEBUG_TRIAGED_MISSING, userId)); 5469 } catch (RemoteException e) { 5470 } 5471 if (appId == -1) { 5472 Slog.w(TAG, "Invalid packageName: " + packageName); 5473 return; 5474 } 5475 killPackageProcessesLocked(packageName, appId, userId, 5476 ProcessList.SERVICE_ADJ, false, true, true, false, "kill background"); 5477 } 5478 } finally { 5479 Binder.restoreCallingIdentity(callingId); 5480 } 5481 } 5482 5483 @Override 5484 public void killAllBackgroundProcesses() { 5485 if (checkCallingPermission(android.Manifest.permission.KILL_BACKGROUND_PROCESSES) 5486 != PackageManager.PERMISSION_GRANTED) { 5487 final String msg = "Permission Denial: killAllBackgroundProcesses() from pid=" 5488 + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid() 5489 + " requires " + android.Manifest.permission.KILL_BACKGROUND_PROCESSES; 5490 Slog.w(TAG, msg); 5491 throw new SecurityException(msg); 5492 } 5493 5494 final long callingId = Binder.clearCallingIdentity(); 5495 try { 5496 synchronized (this) { 5497 final ArrayList<ProcessRecord> procs = new ArrayList<>(); 5498 final int NP = mProcessNames.getMap().size(); 5499 for (int ip = 0; ip < NP; ip++) { 5500 final SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 5501 final int NA = apps.size(); 5502 for (int ia = 0; ia < NA; ia++) { 5503 final ProcessRecord app = apps.valueAt(ia); 5504 if (app.persistent) { 5505 // We don't kill persistent processes. 5506 continue; 5507 } 5508 if (app.removed) { 5509 procs.add(app); 5510 } else if (app.setAdj >= ProcessList.CACHED_APP_MIN_ADJ) { 5511 app.removed = true; 5512 procs.add(app); 5513 } 5514 } 5515 } 5516 5517 final int N = procs.size(); 5518 for (int i = 0; i < N; i++) { 5519 removeProcessLocked(procs.get(i), false, true, "kill all background"); 5520 } 5521 5522 mAllowLowerMemLevel = true; 5523 5524 updateOomAdjLocked(); 5525 doLowMemReportIfNeededLocked(null); 5526 } 5527 } finally { 5528 Binder.restoreCallingIdentity(callingId); 5529 } 5530 } 5531 5532 /** 5533 * Kills all background processes, except those matching any of the 5534 * specified properties. 5535 * 5536 * @param minTargetSdk the target SDK version at or above which to preserve 5537 * processes, or {@code -1} to ignore the target SDK 5538 * @param maxProcState the process state at or below which to preserve 5539 * processes, or {@code -1} to ignore the process state 5540 */ 5541 private void killAllBackgroundProcessesExcept(int minTargetSdk, int maxProcState) { 5542 if (checkCallingPermission(android.Manifest.permission.KILL_BACKGROUND_PROCESSES) 5543 != PackageManager.PERMISSION_GRANTED) { 5544 final String msg = "Permission Denial: killAllBackgroundProcessesExcept() from pid=" 5545 + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid() 5546 + " requires " + android.Manifest.permission.KILL_BACKGROUND_PROCESSES; 5547 Slog.w(TAG, msg); 5548 throw new SecurityException(msg); 5549 } 5550 5551 final long callingId = Binder.clearCallingIdentity(); 5552 try { 5553 synchronized (this) { 5554 final ArrayList<ProcessRecord> procs = new ArrayList<>(); 5555 final int NP = mProcessNames.getMap().size(); 5556 for (int ip = 0; ip < NP; ip++) { 5557 final SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 5558 final int NA = apps.size(); 5559 for (int ia = 0; ia < NA; ia++) { 5560 final ProcessRecord app = apps.valueAt(ia); 5561 if (app.removed) { 5562 procs.add(app); 5563 } else if ((minTargetSdk < 0 || app.info.targetSdkVersion < minTargetSdk) 5564 && (maxProcState < 0 || app.setProcState > maxProcState)) { 5565 app.removed = true; 5566 procs.add(app); 5567 } 5568 } 5569 } 5570 5571 final int N = procs.size(); 5572 for (int i = 0; i < N; i++) { 5573 removeProcessLocked(procs.get(i), false, true, "kill all background except"); 5574 } 5575 } 5576 } finally { 5577 Binder.restoreCallingIdentity(callingId); 5578 } 5579 } 5580 5581 @Override 5582 public void forceStopPackage(final String packageName, int userId) { 5583 if (checkCallingPermission(android.Manifest.permission.FORCE_STOP_PACKAGES) 5584 != PackageManager.PERMISSION_GRANTED) { 5585 String msg = "Permission Denial: forceStopPackage() from pid=" 5586 + Binder.getCallingPid() 5587 + ", uid=" + Binder.getCallingUid() 5588 + " requires " + android.Manifest.permission.FORCE_STOP_PACKAGES; 5589 Slog.w(TAG, msg); 5590 throw new SecurityException(msg); 5591 } 5592 final int callingPid = Binder.getCallingPid(); 5593 userId = mUserController.handleIncomingUser(callingPid, Binder.getCallingUid(), 5594 userId, true, ALLOW_FULL_ONLY, "forceStopPackage", null); 5595 long callingId = Binder.clearCallingIdentity(); 5596 try { 5597 IPackageManager pm = AppGlobals.getPackageManager(); 5598 synchronized(this) { 5599 int[] users = userId == UserHandle.USER_ALL 5600 ? mUserController.getUsers() : new int[] { userId }; 5601 for (int user : users) { 5602 int pkgUid = -1; 5603 try { 5604 pkgUid = pm.getPackageUid(packageName, MATCH_DEBUG_TRIAGED_MISSING, 5605 user); 5606 } catch (RemoteException e) { 5607 } 5608 if (pkgUid == -1) { 5609 Slog.w(TAG, "Invalid packageName: " + packageName); 5610 continue; 5611 } 5612 try { 5613 pm.setPackageStoppedState(packageName, true, user); 5614 } catch (RemoteException e) { 5615 } catch (IllegalArgumentException e) { 5616 Slog.w(TAG, "Failed trying to unstop package " 5617 + packageName + ": " + e); 5618 } 5619 if (mUserController.isUserRunningLocked(user, 0)) { 5620 forceStopPackageLocked(packageName, pkgUid, "from pid " + callingPid); 5621 finishForceStopPackageLocked(packageName, pkgUid); 5622 } 5623 } 5624 } 5625 } finally { 5626 Binder.restoreCallingIdentity(callingId); 5627 } 5628 } 5629 5630 @Override 5631 public void addPackageDependency(String packageName) { 5632 synchronized (this) { 5633 int callingPid = Binder.getCallingPid(); 5634 if (callingPid == Process.myPid()) { 5635 // Yeah, um, no. 5636 return; 5637 } 5638 ProcessRecord proc; 5639 synchronized (mPidsSelfLocked) { 5640 proc = mPidsSelfLocked.get(Binder.getCallingPid()); 5641 } 5642 if (proc != null) { 5643 if (proc.pkgDeps == null) { 5644 proc.pkgDeps = new ArraySet<String>(1); 5645 } 5646 proc.pkgDeps.add(packageName); 5647 } 5648 } 5649 } 5650 5651 /* 5652 * The pkg name and app id have to be specified. 5653 */ 5654 @Override 5655 public void killApplication(String pkg, int appId, int userId, String reason) { 5656 if (pkg == null) { 5657 return; 5658 } 5659 // Make sure the uid is valid. 5660 if (appId < 0) { 5661 Slog.w(TAG, "Invalid appid specified for pkg : " + pkg); 5662 return; 5663 } 5664 int callerUid = Binder.getCallingUid(); 5665 // Only the system server can kill an application 5666 if (UserHandle.getAppId(callerUid) == Process.SYSTEM_UID) { 5667 // Post an aysnc message to kill the application 5668 Message msg = mHandler.obtainMessage(KILL_APPLICATION_MSG); 5669 msg.arg1 = appId; 5670 msg.arg2 = userId; 5671 Bundle bundle = new Bundle(); 5672 bundle.putString("pkg", pkg); 5673 bundle.putString("reason", reason); 5674 msg.obj = bundle; 5675 mHandler.sendMessage(msg); 5676 } else { 5677 throw new SecurityException(callerUid + " cannot kill pkg: " + 5678 pkg); 5679 } 5680 } 5681 5682 @Override 5683 public void closeSystemDialogs(String reason) { 5684 enforceNotIsolatedCaller("closeSystemDialogs"); 5685 5686 final int pid = Binder.getCallingPid(); 5687 final int uid = Binder.getCallingUid(); 5688 final long origId = Binder.clearCallingIdentity(); 5689 try { 5690 synchronized (this) { 5691 // Only allow this from foreground processes, so that background 5692 // applications can't abuse it to prevent system UI from being shown. 5693 if (uid >= Process.FIRST_APPLICATION_UID) { 5694 ProcessRecord proc; 5695 synchronized (mPidsSelfLocked) { 5696 proc = mPidsSelfLocked.get(pid); 5697 } 5698 if (proc.curRawAdj > ProcessList.PERCEPTIBLE_APP_ADJ) { 5699 Slog.w(TAG, "Ignoring closeSystemDialogs " + reason 5700 + " from background process " + proc); 5701 return; 5702 } 5703 } 5704 closeSystemDialogsLocked(reason); 5705 } 5706 } finally { 5707 Binder.restoreCallingIdentity(origId); 5708 } 5709 } 5710 5711 void closeSystemDialogsLocked(String reason) { 5712 Intent intent = new Intent(Intent.ACTION_CLOSE_SYSTEM_DIALOGS); 5713 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 5714 | Intent.FLAG_RECEIVER_FOREGROUND); 5715 if (reason != null) { 5716 intent.putExtra("reason", reason); 5717 } 5718 mWindowManager.closeSystemDialogs(reason); 5719 5720 mStackSupervisor.closeSystemDialogsLocked(); 5721 5722 broadcastIntentLocked(null, null, intent, null, null, 0, null, null, null, 5723 AppOpsManager.OP_NONE, null, false, false, 5724 -1, Process.SYSTEM_UID, UserHandle.USER_ALL); 5725 } 5726 5727 @Override 5728 public Debug.MemoryInfo[] getProcessMemoryInfo(int[] pids) { 5729 enforceNotIsolatedCaller("getProcessMemoryInfo"); 5730 Debug.MemoryInfo[] infos = new Debug.MemoryInfo[pids.length]; 5731 for (int i=pids.length-1; i>=0; i--) { 5732 ProcessRecord proc; 5733 int oomAdj; 5734 synchronized (this) { 5735 synchronized (mPidsSelfLocked) { 5736 proc = mPidsSelfLocked.get(pids[i]); 5737 oomAdj = proc != null ? proc.setAdj : 0; 5738 } 5739 } 5740 infos[i] = new Debug.MemoryInfo(); 5741 Debug.getMemoryInfo(pids[i], infos[i]); 5742 if (proc != null) { 5743 synchronized (this) { 5744 if (proc.thread != null && proc.setAdj == oomAdj) { 5745 // Record this for posterity if the process has been stable. 5746 proc.baseProcessTracker.addPss(infos[i].getTotalPss(), 5747 infos[i].getTotalUss(), false, proc.pkgList); 5748 } 5749 } 5750 } 5751 } 5752 return infos; 5753 } 5754 5755 @Override 5756 public long[] getProcessPss(int[] pids) { 5757 enforceNotIsolatedCaller("getProcessPss"); 5758 long[] pss = new long[pids.length]; 5759 for (int i=pids.length-1; i>=0; i--) { 5760 ProcessRecord proc; 5761 int oomAdj; 5762 synchronized (this) { 5763 synchronized (mPidsSelfLocked) { 5764 proc = mPidsSelfLocked.get(pids[i]); 5765 oomAdj = proc != null ? proc.setAdj : 0; 5766 } 5767 } 5768 long[] tmpUss = new long[1]; 5769 pss[i] = Debug.getPss(pids[i], tmpUss, null); 5770 if (proc != null) { 5771 synchronized (this) { 5772 if (proc.thread != null && proc.setAdj == oomAdj) { 5773 // Record this for posterity if the process has been stable. 5774 proc.baseProcessTracker.addPss(pss[i], tmpUss[0], false, proc.pkgList); 5775 } 5776 } 5777 } 5778 } 5779 return pss; 5780 } 5781 5782 @Override 5783 public void killApplicationProcess(String processName, int uid) { 5784 if (processName == null) { 5785 return; 5786 } 5787 5788 int callerUid = Binder.getCallingUid(); 5789 // Only the system server can kill an application 5790 if (callerUid == Process.SYSTEM_UID) { 5791 synchronized (this) { 5792 ProcessRecord app = getProcessRecordLocked(processName, uid, true); 5793 if (app != null && app.thread != null) { 5794 try { 5795 app.thread.scheduleSuicide(); 5796 } catch (RemoteException e) { 5797 // If the other end already died, then our work here is done. 5798 } 5799 } else { 5800 Slog.w(TAG, "Process/uid not found attempting kill of " 5801 + processName + " / " + uid); 5802 } 5803 } 5804 } else { 5805 throw new SecurityException(callerUid + " cannot kill app process: " + 5806 processName); 5807 } 5808 } 5809 5810 private void forceStopPackageLocked(final String packageName, int uid, String reason) { 5811 forceStopPackageLocked(packageName, UserHandle.getAppId(uid), false, 5812 false, true, false, false, UserHandle.getUserId(uid), reason); 5813 } 5814 5815 private void finishForceStopPackageLocked(final String packageName, int uid) { 5816 Intent intent = new Intent(Intent.ACTION_PACKAGE_RESTARTED, 5817 Uri.fromParts("package", packageName, null)); 5818 if (!mProcessesReady) { 5819 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 5820 | Intent.FLAG_RECEIVER_FOREGROUND); 5821 } 5822 intent.putExtra(Intent.EXTRA_UID, uid); 5823 intent.putExtra(Intent.EXTRA_USER_HANDLE, UserHandle.getUserId(uid)); 5824 broadcastIntentLocked(null, null, intent, 5825 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 5826 null, false, false, MY_PID, Process.SYSTEM_UID, UserHandle.getUserId(uid)); 5827 } 5828 5829 5830 private final boolean killPackageProcessesLocked(String packageName, int appId, 5831 int userId, int minOomAdj, boolean callerWillRestart, boolean allowRestart, 5832 boolean doit, boolean evenPersistent, String reason) { 5833 ArrayList<ProcessRecord> procs = new ArrayList<>(); 5834 5835 // Remove all processes this package may have touched: all with the 5836 // same UID (except for the system or root user), and all whose name 5837 // matches the package name. 5838 final int NP = mProcessNames.getMap().size(); 5839 for (int ip=0; ip<NP; ip++) { 5840 SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 5841 final int NA = apps.size(); 5842 for (int ia=0; ia<NA; ia++) { 5843 ProcessRecord app = apps.valueAt(ia); 5844 if (app.persistent && !evenPersistent) { 5845 // we don't kill persistent processes 5846 continue; 5847 } 5848 if (app.removed) { 5849 if (doit) { 5850 procs.add(app); 5851 } 5852 continue; 5853 } 5854 5855 // Skip process if it doesn't meet our oom adj requirement. 5856 if (app.setAdj < minOomAdj) { 5857 continue; 5858 } 5859 5860 // If no package is specified, we call all processes under the 5861 // give user id. 5862 if (packageName == null) { 5863 if (userId != UserHandle.USER_ALL && app.userId != userId) { 5864 continue; 5865 } 5866 if (appId >= 0 && UserHandle.getAppId(app.uid) != appId) { 5867 continue; 5868 } 5869 // Package has been specified, we want to hit all processes 5870 // that match it. We need to qualify this by the processes 5871 // that are running under the specified app and user ID. 5872 } else { 5873 final boolean isDep = app.pkgDeps != null 5874 && app.pkgDeps.contains(packageName); 5875 if (!isDep && UserHandle.getAppId(app.uid) != appId) { 5876 continue; 5877 } 5878 if (userId != UserHandle.USER_ALL && app.userId != userId) { 5879 continue; 5880 } 5881 if (!app.pkgList.containsKey(packageName) && !isDep) { 5882 continue; 5883 } 5884 } 5885 5886 // Process has passed all conditions, kill it! 5887 if (!doit) { 5888 return true; 5889 } 5890 app.removed = true; 5891 procs.add(app); 5892 } 5893 } 5894 5895 int N = procs.size(); 5896 for (int i=0; i<N; i++) { 5897 removeProcessLocked(procs.get(i), callerWillRestart, allowRestart, reason); 5898 } 5899 updateOomAdjLocked(); 5900 return N > 0; 5901 } 5902 5903 private void cleanupDisabledPackageComponentsLocked( 5904 String packageName, int userId, boolean killProcess, String[] changedClasses) { 5905 5906 Set<String> disabledClasses = null; 5907 boolean packageDisabled = false; 5908 IPackageManager pm = AppGlobals.getPackageManager(); 5909 5910 if (changedClasses == null) { 5911 // Nothing changed... 5912 return; 5913 } 5914 5915 // Determine enable/disable state of the package and its components. 5916 int enabled = PackageManager.COMPONENT_ENABLED_STATE_DEFAULT; 5917 for (int i = changedClasses.length - 1; i >= 0; i--) { 5918 final String changedClass = changedClasses[i]; 5919 5920 if (changedClass.equals(packageName)) { 5921 try { 5922 // Entire package setting changed 5923 enabled = pm.getApplicationEnabledSetting(packageName, 5924 (userId != UserHandle.USER_ALL) ? userId : UserHandle.USER_SYSTEM); 5925 } catch (Exception e) { 5926 // No such package/component; probably racing with uninstall. In any 5927 // event it means we have nothing further to do here. 5928 return; 5929 } 5930 packageDisabled = enabled != PackageManager.COMPONENT_ENABLED_STATE_ENABLED 5931 && enabled != PackageManager.COMPONENT_ENABLED_STATE_DEFAULT; 5932 if (packageDisabled) { 5933 // Entire package is disabled. 5934 // No need to continue to check component states. 5935 disabledClasses = null; 5936 break; 5937 } 5938 } else { 5939 try { 5940 enabled = pm.getComponentEnabledSetting( 5941 new ComponentName(packageName, changedClass), 5942 (userId != UserHandle.USER_ALL) ? userId : UserHandle.USER_SYSTEM); 5943 } catch (Exception e) { 5944 // As above, probably racing with uninstall. 5945 return; 5946 } 5947 if (enabled != PackageManager.COMPONENT_ENABLED_STATE_ENABLED 5948 && enabled != PackageManager.COMPONENT_ENABLED_STATE_DEFAULT) { 5949 if (disabledClasses == null) { 5950 disabledClasses = new ArraySet<>(changedClasses.length); 5951 } 5952 disabledClasses.add(changedClass); 5953 } 5954 } 5955 } 5956 5957 if (!packageDisabled && disabledClasses == null) { 5958 // Nothing to do here... 5959 return; 5960 } 5961 5962 // Clean-up disabled activities. 5963 if (mStackSupervisor.finishDisabledPackageActivitiesLocked( 5964 packageName, disabledClasses, true, false, userId) && mBooted) { 5965 mStackSupervisor.resumeFocusedStackTopActivityLocked(); 5966 mStackSupervisor.scheduleIdleLocked(); 5967 } 5968 5969 // Clean-up disabled tasks 5970 cleanupDisabledPackageTasksLocked(packageName, disabledClasses, userId); 5971 5972 // Clean-up disabled services. 5973 mServices.bringDownDisabledPackageServicesLocked( 5974 packageName, disabledClasses, userId, false, killProcess, true); 5975 5976 // Clean-up disabled providers. 5977 ArrayList<ContentProviderRecord> providers = new ArrayList<>(); 5978 mProviderMap.collectPackageProvidersLocked( 5979 packageName, disabledClasses, true, false, userId, providers); 5980 for (int i = providers.size() - 1; i >= 0; i--) { 5981 removeDyingProviderLocked(null, providers.get(i), true); 5982 } 5983 5984 // Clean-up disabled broadcast receivers. 5985 for (int i = mBroadcastQueues.length - 1; i >= 0; i--) { 5986 mBroadcastQueues[i].cleanupDisabledPackageReceiversLocked( 5987 packageName, disabledClasses, userId, true); 5988 } 5989 5990 } 5991 5992 final boolean clearBroadcastQueueForUserLocked(int userId) { 5993 boolean didSomething = false; 5994 for (int i = mBroadcastQueues.length - 1; i >= 0; i--) { 5995 didSomething |= mBroadcastQueues[i].cleanupDisabledPackageReceiversLocked( 5996 null, null, userId, true); 5997 } 5998 return didSomething; 5999 } 6000 6001 final boolean forceStopPackageLocked(String packageName, int appId, 6002 boolean callerWillRestart, boolean purgeCache, boolean doit, 6003 boolean evenPersistent, boolean uninstalling, int userId, String reason) { 6004 int i; 6005 6006 if (userId == UserHandle.USER_ALL && packageName == null) { 6007 Slog.w(TAG, "Can't force stop all processes of all users, that is insane!"); 6008 } 6009 6010 if (appId < 0 && packageName != null) { 6011 try { 6012 appId = UserHandle.getAppId(AppGlobals.getPackageManager() 6013 .getPackageUid(packageName, MATCH_DEBUG_TRIAGED_MISSING, 0)); 6014 } catch (RemoteException e) { 6015 } 6016 } 6017 6018 if (doit) { 6019 if (packageName != null) { 6020 Slog.i(TAG, "Force stopping " + packageName + " appid=" + appId 6021 + " user=" + userId + ": " + reason); 6022 } else { 6023 Slog.i(TAG, "Force stopping u" + userId + ": " + reason); 6024 } 6025 6026 mAppErrors.resetProcessCrashTimeLocked(packageName == null, appId, userId); 6027 } 6028 6029 boolean didSomething = killPackageProcessesLocked(packageName, appId, userId, 6030 ProcessList.INVALID_ADJ, callerWillRestart, true, doit, evenPersistent, 6031 packageName == null ? ("stop user " + userId) : ("stop " + packageName)); 6032 6033 didSomething |= mActivityStarter.clearPendingActivityLaunchesLocked(packageName); 6034 6035 if (mStackSupervisor.finishDisabledPackageActivitiesLocked( 6036 packageName, null, doit, evenPersistent, userId)) { 6037 if (!doit) { 6038 return true; 6039 } 6040 didSomething = true; 6041 } 6042 6043 if (mServices.bringDownDisabledPackageServicesLocked( 6044 packageName, null, userId, evenPersistent, true, doit)) { 6045 if (!doit) { 6046 return true; 6047 } 6048 didSomething = true; 6049 } 6050 6051 if (packageName == null) { 6052 // Remove all sticky broadcasts from this user. 6053 mStickyBroadcasts.remove(userId); 6054 } 6055 6056 ArrayList<ContentProviderRecord> providers = new ArrayList<>(); 6057 if (mProviderMap.collectPackageProvidersLocked(packageName, null, doit, evenPersistent, 6058 userId, providers)) { 6059 if (!doit) { 6060 return true; 6061 } 6062 didSomething = true; 6063 } 6064 for (i = providers.size() - 1; i >= 0; i--) { 6065 removeDyingProviderLocked(null, providers.get(i), true); 6066 } 6067 6068 // Remove transient permissions granted from/to this package/user 6069 removeUriPermissionsForPackageLocked(packageName, userId, false); 6070 6071 if (doit) { 6072 for (i = mBroadcastQueues.length - 1; i >= 0; i--) { 6073 didSomething |= mBroadcastQueues[i].cleanupDisabledPackageReceiversLocked( 6074 packageName, null, userId, doit); 6075 } 6076 } 6077 6078 if (packageName == null || uninstalling) { 6079 // Remove pending intents. For now we only do this when force 6080 // stopping users, because we have some problems when doing this 6081 // for packages -- app widgets are not currently cleaned up for 6082 // such packages, so they can be left with bad pending intents. 6083 if (mIntentSenderRecords.size() > 0) { 6084 Iterator<WeakReference<PendingIntentRecord>> it 6085 = mIntentSenderRecords.values().iterator(); 6086 while (it.hasNext()) { 6087 WeakReference<PendingIntentRecord> wpir = it.next(); 6088 if (wpir == null) { 6089 it.remove(); 6090 continue; 6091 } 6092 PendingIntentRecord pir = wpir.get(); 6093 if (pir == null) { 6094 it.remove(); 6095 continue; 6096 } 6097 if (packageName == null) { 6098 // Stopping user, remove all objects for the user. 6099 if (pir.key.userId != userId) { 6100 // Not the same user, skip it. 6101 continue; 6102 } 6103 } else { 6104 if (UserHandle.getAppId(pir.uid) != appId) { 6105 // Different app id, skip it. 6106 continue; 6107 } 6108 if (userId != UserHandle.USER_ALL && pir.key.userId != userId) { 6109 // Different user, skip it. 6110 continue; 6111 } 6112 if (!pir.key.packageName.equals(packageName)) { 6113 // Different package, skip it. 6114 continue; 6115 } 6116 } 6117 if (!doit) { 6118 return true; 6119 } 6120 didSomething = true; 6121 it.remove(); 6122 pir.canceled = true; 6123 if (pir.key.activity != null && pir.key.activity.pendingResults != null) { 6124 pir.key.activity.pendingResults.remove(pir.ref); 6125 } 6126 } 6127 } 6128 } 6129 6130 if (doit) { 6131 if (purgeCache && packageName != null) { 6132 AttributeCache ac = AttributeCache.instance(); 6133 if (ac != null) { 6134 ac.removePackage(packageName); 6135 } 6136 } 6137 if (mBooted) { 6138 mStackSupervisor.resumeFocusedStackTopActivityLocked(); 6139 mStackSupervisor.scheduleIdleLocked(); 6140 } 6141 } 6142 6143 return didSomething; 6144 } 6145 6146 private final ProcessRecord removeProcessNameLocked(final String name, final int uid) { 6147 ProcessRecord old = mProcessNames.remove(name, uid); 6148 if (old != null) { 6149 old.uidRecord.numProcs--; 6150 if (old.uidRecord.numProcs == 0) { 6151 // No more processes using this uid, tell clients it is gone. 6152 if (DEBUG_UID_OBSERVERS) Slog.i(TAG_UID_OBSERVERS, 6153 "No more processes in " + old.uidRecord); 6154 enqueueUidChangeLocked(old.uidRecord, -1, UidRecord.CHANGE_GONE); 6155 mActiveUids.remove(uid); 6156 noteUidProcessState(uid, ActivityManager.PROCESS_STATE_NONEXISTENT); 6157 } 6158 old.uidRecord = null; 6159 } 6160 mIsolatedProcesses.remove(uid); 6161 return old; 6162 } 6163 6164 private final void addProcessNameLocked(ProcessRecord proc) { 6165 // We shouldn't already have a process under this name, but just in case we 6166 // need to clean up whatever may be there now. 6167 ProcessRecord old = removeProcessNameLocked(proc.processName, proc.uid); 6168 if (old == proc && proc.persistent) { 6169 // We are re-adding a persistent process. Whatevs! Just leave it there. 6170 Slog.w(TAG, "Re-adding persistent process " + proc); 6171 } else if (old != null) { 6172 Slog.wtf(TAG, "Already have existing proc " + old + " when adding " + proc); 6173 } 6174 UidRecord uidRec = mActiveUids.get(proc.uid); 6175 if (uidRec == null) { 6176 uidRec = new UidRecord(proc.uid); 6177 // This is the first appearance of the uid, report it now! 6178 if (DEBUG_UID_OBSERVERS) Slog.i(TAG_UID_OBSERVERS, 6179 "Creating new process uid: " + uidRec); 6180 mActiveUids.put(proc.uid, uidRec); 6181 noteUidProcessState(uidRec.uid, uidRec.curProcState); 6182 enqueueUidChangeLocked(uidRec, -1, UidRecord.CHANGE_ACTIVE); 6183 } 6184 proc.uidRecord = uidRec; 6185 6186 // Reset render thread tid if it was already set, so new process can set it again. 6187 proc.renderThreadTid = 0; 6188 uidRec.numProcs++; 6189 mProcessNames.put(proc.processName, proc.uid, proc); 6190 if (proc.isolated) { 6191 mIsolatedProcesses.put(proc.uid, proc); 6192 } 6193 } 6194 6195 boolean removeProcessLocked(ProcessRecord app, 6196 boolean callerWillRestart, boolean allowRestart, String reason) { 6197 final String name = app.processName; 6198 final int uid = app.uid; 6199 if (DEBUG_PROCESSES) Slog.d(TAG_PROCESSES, 6200 "Force removing proc " + app.toShortString() + " (" + name + "/" + uid + ")"); 6201 6202 ProcessRecord old = mProcessNames.get(name, uid); 6203 if (old != app) { 6204 // This process is no longer active, so nothing to do. 6205 Slog.w(TAG, "Ignoring remove of inactive process: " + app); 6206 return false; 6207 } 6208 removeProcessNameLocked(name, uid); 6209 if (mHeavyWeightProcess == app) { 6210 mHandler.sendMessage(mHandler.obtainMessage(CANCEL_HEAVY_NOTIFICATION_MSG, 6211 mHeavyWeightProcess.userId, 0)); 6212 mHeavyWeightProcess = null; 6213 } 6214 boolean needRestart = false; 6215 if (app.pid > 0 && app.pid != MY_PID) { 6216 int pid = app.pid; 6217 synchronized (mPidsSelfLocked) { 6218 mPidsSelfLocked.remove(pid); 6219 mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app); 6220 } 6221 mBatteryStatsService.noteProcessFinish(app.processName, app.info.uid); 6222 if (app.isolated) { 6223 mBatteryStatsService.removeIsolatedUid(app.uid, app.info.uid); 6224 } 6225 boolean willRestart = false; 6226 if (app.persistent && !app.isolated) { 6227 if (!callerWillRestart) { 6228 willRestart = true; 6229 } else { 6230 needRestart = true; 6231 } 6232 } 6233 app.kill(reason, true); 6234 handleAppDiedLocked(app, willRestart, allowRestart); 6235 if (willRestart) { 6236 removeLruProcessLocked(app); 6237 addAppLocked(app.info, false, null /* ABI override */); 6238 } 6239 } else { 6240 mRemovedProcesses.add(app); 6241 } 6242 6243 return needRestart; 6244 } 6245 6246 private final void processContentProviderPublishTimedOutLocked(ProcessRecord app) { 6247 cleanupAppInLaunchingProvidersLocked(app, true); 6248 removeProcessLocked(app, false, true, "timeout publishing content providers"); 6249 } 6250 6251 private final void processStartTimedOutLocked(ProcessRecord app) { 6252 final int pid = app.pid; 6253 boolean gone = false; 6254 synchronized (mPidsSelfLocked) { 6255 ProcessRecord knownApp = mPidsSelfLocked.get(pid); 6256 if (knownApp != null && knownApp.thread == null) { 6257 mPidsSelfLocked.remove(pid); 6258 gone = true; 6259 } 6260 } 6261 6262 if (gone) { 6263 Slog.w(TAG, "Process " + app + " failed to attach"); 6264 EventLog.writeEvent(EventLogTags.AM_PROCESS_START_TIMEOUT, app.userId, 6265 pid, app.uid, app.processName); 6266 removeProcessNameLocked(app.processName, app.uid); 6267 if (mHeavyWeightProcess == app) { 6268 mHandler.sendMessage(mHandler.obtainMessage(CANCEL_HEAVY_NOTIFICATION_MSG, 6269 mHeavyWeightProcess.userId, 0)); 6270 mHeavyWeightProcess = null; 6271 } 6272 mBatteryStatsService.noteProcessFinish(app.processName, app.info.uid); 6273 if (app.isolated) { 6274 mBatteryStatsService.removeIsolatedUid(app.uid, app.info.uid); 6275 } 6276 // Take care of any launching providers waiting for this process. 6277 cleanupAppInLaunchingProvidersLocked(app, true); 6278 // Take care of any services that are waiting for the process. 6279 mServices.processStartTimedOutLocked(app); 6280 app.kill("start timeout", true); 6281 removeLruProcessLocked(app); 6282 if (mBackupTarget != null && mBackupTarget.app.pid == pid) { 6283 Slog.w(TAG, "Unattached app died before backup, skipping"); 6284 try { 6285 IBackupManager bm = IBackupManager.Stub.asInterface( 6286 ServiceManager.getService(Context.BACKUP_SERVICE)); 6287 bm.agentDisconnected(app.info.packageName); 6288 } catch (RemoteException e) { 6289 // Can't happen; the backup manager is local 6290 } 6291 } 6292 if (isPendingBroadcastProcessLocked(pid)) { 6293 Slog.w(TAG, "Unattached app died before broadcast acknowledged, skipping"); 6294 skipPendingBroadcastLocked(pid); 6295 } 6296 } else { 6297 Slog.w(TAG, "Spurious process start timeout - pid not known for " + app); 6298 } 6299 } 6300 6301 private final boolean attachApplicationLocked(IApplicationThread thread, 6302 int pid) { 6303 6304 // Find the application record that is being attached... either via 6305 // the pid if we are running in multiple processes, or just pull the 6306 // next app record if we are emulating process with anonymous threads. 6307 ProcessRecord app; 6308 if (pid != MY_PID && pid >= 0) { 6309 synchronized (mPidsSelfLocked) { 6310 app = mPidsSelfLocked.get(pid); 6311 } 6312 } else { 6313 app = null; 6314 } 6315 6316 if (app == null) { 6317 Slog.w(TAG, "No pending application record for pid " + pid 6318 + " (IApplicationThread " + thread + "); dropping process"); 6319 EventLog.writeEvent(EventLogTags.AM_DROP_PROCESS, pid); 6320 if (pid > 0 && pid != MY_PID) { 6321 Process.killProcessQuiet(pid); 6322 //TODO: killProcessGroup(app.info.uid, pid); 6323 } else { 6324 try { 6325 thread.scheduleExit(); 6326 } catch (Exception e) { 6327 // Ignore exceptions. 6328 } 6329 } 6330 return false; 6331 } 6332 6333 // If this application record is still attached to a previous 6334 // process, clean it up now. 6335 if (app.thread != null) { 6336 handleAppDiedLocked(app, true, true); 6337 } 6338 6339 // Tell the process all about itself. 6340 6341 if (DEBUG_ALL) Slog.v( 6342 TAG, "Binding process pid " + pid + " to record " + app); 6343 6344 final String processName = app.processName; 6345 try { 6346 AppDeathRecipient adr = new AppDeathRecipient( 6347 app, pid, thread); 6348 thread.asBinder().linkToDeath(adr, 0); 6349 app.deathRecipient = adr; 6350 } catch (RemoteException e) { 6351 app.resetPackageList(mProcessStats); 6352 startProcessLocked(app, "link fail", processName); 6353 return false; 6354 } 6355 6356 EventLog.writeEvent(EventLogTags.AM_PROC_BOUND, app.userId, app.pid, app.processName); 6357 6358 app.makeActive(thread, mProcessStats); 6359 app.curAdj = app.setAdj = app.verifiedAdj = ProcessList.INVALID_ADJ; 6360 app.curSchedGroup = app.setSchedGroup = ProcessList.SCHED_GROUP_DEFAULT; 6361 app.forcingToForeground = null; 6362 updateProcessForegroundLocked(app, false, false); 6363 app.hasShownUi = false; 6364 app.debugging = false; 6365 app.cached = false; 6366 app.killedByAm = false; 6367 app.killed = false; 6368 6369 6370 // We carefully use the same state that PackageManager uses for 6371 // filtering, since we use this flag to decide if we need to install 6372 // providers when user is unlocked later 6373 app.unlocked = StorageManager.isUserKeyUnlocked(app.userId); 6374 6375 mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app); 6376 6377 boolean normalMode = mProcessesReady || isAllowedWhileBooting(app.info); 6378 List<ProviderInfo> providers = normalMode ? generateApplicationProvidersLocked(app) : null; 6379 6380 if (providers != null && checkAppInLaunchingProvidersLocked(app)) { 6381 Message msg = mHandler.obtainMessage(CONTENT_PROVIDER_PUBLISH_TIMEOUT_MSG); 6382 msg.obj = app; 6383 mHandler.sendMessageDelayed(msg, CONTENT_PROVIDER_PUBLISH_TIMEOUT); 6384 } 6385 6386 if (!normalMode) { 6387 Slog.i(TAG, "Launching preboot mode app: " + app); 6388 } 6389 6390 if (DEBUG_ALL) Slog.v( 6391 TAG, "New app record " + app 6392 + " thread=" + thread.asBinder() + " pid=" + pid); 6393 try { 6394 int testMode = ApplicationThreadConstants.DEBUG_OFF; 6395 if (mDebugApp != null && mDebugApp.equals(processName)) { 6396 testMode = mWaitForDebugger 6397 ? ApplicationThreadConstants.DEBUG_WAIT 6398 : ApplicationThreadConstants.DEBUG_ON; 6399 app.debugging = true; 6400 if (mDebugTransient) { 6401 mDebugApp = mOrigDebugApp; 6402 mWaitForDebugger = mOrigWaitForDebugger; 6403 } 6404 } 6405 String profileFile = app.instrumentationProfileFile; 6406 ParcelFileDescriptor profileFd = null; 6407 int samplingInterval = 0; 6408 boolean profileAutoStop = false; 6409 if (mProfileApp != null && mProfileApp.equals(processName)) { 6410 mProfileProc = app; 6411 profileFile = mProfileFile; 6412 profileFd = mProfileFd; 6413 samplingInterval = mSamplingInterval; 6414 profileAutoStop = mAutoStopProfiler; 6415 } 6416 boolean enableTrackAllocation = false; 6417 if (mTrackAllocationApp != null && mTrackAllocationApp.equals(processName)) { 6418 enableTrackAllocation = true; 6419 mTrackAllocationApp = null; 6420 } 6421 6422 // If the app is being launched for restore or full backup, set it up specially 6423 boolean isRestrictedBackupMode = false; 6424 if (mBackupTarget != null && mBackupAppName.equals(processName)) { 6425 isRestrictedBackupMode = mBackupTarget.appInfo.uid >= Process.FIRST_APPLICATION_UID 6426 && ((mBackupTarget.backupMode == BackupRecord.RESTORE) 6427 || (mBackupTarget.backupMode == BackupRecord.RESTORE_FULL) 6428 || (mBackupTarget.backupMode == BackupRecord.BACKUP_FULL)); 6429 } 6430 6431 if (app.instrumentationClass != null) { 6432 notifyPackageUse(app.instrumentationClass.getPackageName(), 6433 PackageManager.NOTIFY_PACKAGE_USE_INSTRUMENTATION); 6434 } 6435 if (DEBUG_CONFIGURATION) Slog.v(TAG_CONFIGURATION, "Binding proc " 6436 + processName + " with config " + getGlobalConfiguration()); 6437 ApplicationInfo appInfo = app.instrumentationInfo != null 6438 ? app.instrumentationInfo : app.info; 6439 app.compat = compatibilityInfoForPackageLocked(appInfo); 6440 if (profileFd != null) { 6441 profileFd = profileFd.dup(); 6442 } 6443 ProfilerInfo profilerInfo = profileFile == null ? null 6444 : new ProfilerInfo(profileFile, profileFd, samplingInterval, profileAutoStop); 6445 6446 // We deprecated Build.SERIAL and only apps that target pre NMR1 6447 // SDK can see it. Since access to the serial is now behind a 6448 // permission we push down the value. 6449 String buildSerial = Build.UNKNOWN; 6450 if (appInfo.targetSdkVersion <= Build.VERSION_CODES.N_MR1) { 6451 buildSerial = IDeviceIdentifiersPolicyService.Stub.asInterface( 6452 ServiceManager.getService(Context.DEVICE_IDENTIFIERS_SERVICE)) 6453 .getSerial(); 6454 } 6455 6456 thread.bindApplication(processName, appInfo, providers, app.instrumentationClass, 6457 profilerInfo, app.instrumentationArguments, app.instrumentationWatcher, 6458 app.instrumentationUiAutomationConnection, testMode, 6459 mBinderTransactionTrackingEnabled, enableTrackAllocation, 6460 isRestrictedBackupMode || !normalMode, app.persistent, 6461 new Configuration(getGlobalConfiguration()), app.compat, 6462 getCommonServicesLocked(app.isolated), 6463 mCoreSettingsObserver.getCoreSettingsLocked(), 6464 buildSerial); 6465 6466 updateLruProcessLocked(app, false, null); 6467 app.lastRequestedGc = app.lastLowMemory = SystemClock.uptimeMillis(); 6468 } catch (Exception e) { 6469 // todo: Yikes! What should we do? For now we will try to 6470 // start another process, but that could easily get us in 6471 // an infinite loop of restarting processes... 6472 Slog.wtf(TAG, "Exception thrown during bind of " + app, e); 6473 6474 app.resetPackageList(mProcessStats); 6475 app.unlinkDeathRecipient(); 6476 startProcessLocked(app, "bind fail", processName); 6477 return false; 6478 } 6479 6480 // Remove this record from the list of starting applications. 6481 mPersistentStartingProcesses.remove(app); 6482 if (DEBUG_PROCESSES && mProcessesOnHold.contains(app)) Slog.v(TAG_PROCESSES, 6483 "Attach application locked removing on hold: " + app); 6484 mProcessesOnHold.remove(app); 6485 6486 boolean badApp = false; 6487 boolean didSomething = false; 6488 6489 // See if the top visible activity is waiting to run in this process... 6490 if (normalMode) { 6491 try { 6492 if (mStackSupervisor.attachApplicationLocked(app)) { 6493 didSomething = true; 6494 } 6495 } catch (Exception e) { 6496 Slog.wtf(TAG, "Exception thrown launching activities in " + app, e); 6497 badApp = true; 6498 } 6499 } 6500 6501 // Find any services that should be running in this process... 6502 if (!badApp) { 6503 try { 6504 didSomething |= mServices.attachApplicationLocked(app, processName); 6505 } catch (Exception e) { 6506 Slog.wtf(TAG, "Exception thrown starting services in " + app, e); 6507 badApp = true; 6508 } 6509 } 6510 6511 // Check if a next-broadcast receiver is in this process... 6512 if (!badApp && isPendingBroadcastProcessLocked(pid)) { 6513 try { 6514 didSomething |= sendPendingBroadcastsLocked(app); 6515 } catch (Exception e) { 6516 // If the app died trying to launch the receiver we declare it 'bad' 6517 Slog.wtf(TAG, "Exception thrown dispatching broadcasts in " + app, e); 6518 badApp = true; 6519 } 6520 } 6521 6522 // Check whether the next backup agent is in this process... 6523 if (!badApp && mBackupTarget != null && mBackupTarget.appInfo.uid == app.uid) { 6524 if (DEBUG_BACKUP) Slog.v(TAG_BACKUP, 6525 "New app is backup target, launching agent for " + app); 6526 notifyPackageUse(mBackupTarget.appInfo.packageName, 6527 PackageManager.NOTIFY_PACKAGE_USE_BACKUP); 6528 try { 6529 thread.scheduleCreateBackupAgent(mBackupTarget.appInfo, 6530 compatibilityInfoForPackageLocked(mBackupTarget.appInfo), 6531 mBackupTarget.backupMode); 6532 } catch (Exception e) { 6533 Slog.wtf(TAG, "Exception thrown creating backup agent in " + app, e); 6534 badApp = true; 6535 } 6536 } 6537 6538 if (badApp) { 6539 app.kill("error during init", true); 6540 handleAppDiedLocked(app, false, true); 6541 return false; 6542 } 6543 6544 if (!didSomething) { 6545 updateOomAdjLocked(); 6546 } 6547 6548 return true; 6549 } 6550 6551 @Override 6552 public final void attachApplication(IApplicationThread thread) { 6553 synchronized (this) { 6554 int callingPid = Binder.getCallingPid(); 6555 final long origId = Binder.clearCallingIdentity(); 6556 attachApplicationLocked(thread, callingPid); 6557 Binder.restoreCallingIdentity(origId); 6558 } 6559 } 6560 6561 @Override 6562 public final void activityIdle(IBinder token, Configuration config, boolean stopProfiling) { 6563 final long origId = Binder.clearCallingIdentity(); 6564 synchronized (this) { 6565 ActivityStack stack = ActivityRecord.getStackLocked(token); 6566 if (stack != null) { 6567 ActivityRecord r = 6568 mStackSupervisor.activityIdleInternalLocked(token, false, config); 6569 if (stopProfiling) { 6570 if ((mProfileProc == r.app) && (mProfileFd != null)) { 6571 try { 6572 mProfileFd.close(); 6573 } catch (IOException e) { 6574 } 6575 clearProfilerLocked(); 6576 } 6577 } 6578 } 6579 } 6580 Binder.restoreCallingIdentity(origId); 6581 } 6582 6583 void postFinishBooting(boolean finishBooting, boolean enableScreen) { 6584 mHandler.sendMessage(mHandler.obtainMessage(FINISH_BOOTING_MSG, 6585 finishBooting ? 1 : 0, enableScreen ? 1 : 0)); 6586 } 6587 6588 void enableScreenAfterBoot() { 6589 EventLog.writeEvent(EventLogTags.BOOT_PROGRESS_ENABLE_SCREEN, 6590 SystemClock.uptimeMillis()); 6591 mWindowManager.enableScreenAfterBoot(); 6592 6593 synchronized (this) { 6594 updateEventDispatchingLocked(); 6595 } 6596 } 6597 6598 @Override 6599 public void showBootMessage(final CharSequence msg, final boolean always) { 6600 if (Binder.getCallingUid() != Process.myUid()) { 6601 throw new SecurityException(); 6602 } 6603 mWindowManager.showBootMessage(msg, always); 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 mKeyguardController.keyguardGoingAway(flags); 6613 } 6614 } finally { 6615 Binder.restoreCallingIdentity(token); 6616 } 6617 } 6618 6619 final void finishBooting() { 6620 synchronized (this) { 6621 if (!mBootAnimationComplete) { 6622 mCallFinishBooting = true; 6623 return; 6624 } 6625 mCallFinishBooting = false; 6626 } 6627 6628 ArraySet<String> completedIsas = new ArraySet<String>(); 6629 for (String abi : Build.SUPPORTED_ABIS) { 6630 Process.zygoteProcess.establishZygoteConnectionForAbi(abi); 6631 final String instructionSet = VMRuntime.getInstructionSet(abi); 6632 if (!completedIsas.contains(instructionSet)) { 6633 try { 6634 mInstaller.markBootComplete(VMRuntime.getInstructionSet(abi)); 6635 } catch (InstallerException e) { 6636 Slog.w(TAG, "Unable to mark boot complete for abi: " + abi + " (" + 6637 e.getMessage() +")"); 6638 } 6639 completedIsas.add(instructionSet); 6640 } 6641 } 6642 6643 IntentFilter pkgFilter = new IntentFilter(); 6644 pkgFilter.addAction(Intent.ACTION_QUERY_PACKAGE_RESTART); 6645 pkgFilter.addDataScheme("package"); 6646 mContext.registerReceiver(new BroadcastReceiver() { 6647 @Override 6648 public void onReceive(Context context, Intent intent) { 6649 String[] pkgs = intent.getStringArrayExtra(Intent.EXTRA_PACKAGES); 6650 if (pkgs != null) { 6651 for (String pkg : pkgs) { 6652 synchronized (ActivityManagerService.this) { 6653 if (forceStopPackageLocked(pkg, -1, false, false, false, false, false, 6654 0, "query restart")) { 6655 setResultCode(Activity.RESULT_OK); 6656 return; 6657 } 6658 } 6659 } 6660 } 6661 } 6662 }, pkgFilter); 6663 6664 IntentFilter dumpheapFilter = new IntentFilter(); 6665 dumpheapFilter.addAction(DumpHeapActivity.ACTION_DELETE_DUMPHEAP); 6666 mContext.registerReceiver(new BroadcastReceiver() { 6667 @Override 6668 public void onReceive(Context context, Intent intent) { 6669 if (intent.getBooleanExtra(DumpHeapActivity.EXTRA_DELAY_DELETE, false)) { 6670 mHandler.sendEmptyMessageDelayed(POST_DUMP_HEAP_NOTIFICATION_MSG, 5*60*1000); 6671 } else { 6672 mHandler.sendEmptyMessage(POST_DUMP_HEAP_NOTIFICATION_MSG); 6673 } 6674 } 6675 }, dumpheapFilter); 6676 6677 // Let system services know. 6678 mSystemServiceManager.startBootPhase(SystemService.PHASE_BOOT_COMPLETED); 6679 6680 synchronized (this) { 6681 // Ensure that any processes we had put on hold are now started 6682 // up. 6683 final int NP = mProcessesOnHold.size(); 6684 if (NP > 0) { 6685 ArrayList<ProcessRecord> procs = 6686 new ArrayList<ProcessRecord>(mProcessesOnHold); 6687 for (int ip=0; ip<NP; ip++) { 6688 if (DEBUG_PROCESSES) Slog.v(TAG_PROCESSES, "Starting process on hold: " 6689 + procs.get(ip)); 6690 startProcessLocked(procs.get(ip), "on-hold", null); 6691 } 6692 } 6693 6694 if (mFactoryTest != FactoryTest.FACTORY_TEST_LOW_LEVEL) { 6695 // Start looking for apps that are abusing wake locks. 6696 Message nmsg = mHandler.obtainMessage(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 6697 mHandler.sendMessageDelayed(nmsg, POWER_CHECK_DELAY); 6698 // Tell anyone interested that we are done booting! 6699 SystemProperties.set("sys.boot_completed", "1"); 6700 6701 // And trigger dev.bootcomplete if we are not showing encryption progress 6702 if (!"trigger_restart_min_framework".equals(SystemProperties.get("vold.decrypt")) 6703 || "".equals(SystemProperties.get("vold.encrypt_progress"))) { 6704 SystemProperties.set("dev.bootcomplete", "1"); 6705 } 6706 mUserController.sendBootCompletedLocked( 6707 new IIntentReceiver.Stub() { 6708 @Override 6709 public void performReceive(Intent intent, int resultCode, 6710 String data, Bundle extras, boolean ordered, 6711 boolean sticky, int sendingUser) { 6712 synchronized (ActivityManagerService.this) { 6713 requestPssAllProcsLocked(SystemClock.uptimeMillis(), 6714 true, false); 6715 } 6716 } 6717 }); 6718 scheduleStartProfilesLocked(); 6719 } 6720 } 6721 } 6722 6723 @Override 6724 public void bootAnimationComplete() { 6725 final boolean callFinishBooting; 6726 synchronized (this) { 6727 callFinishBooting = mCallFinishBooting; 6728 mBootAnimationComplete = true; 6729 } 6730 if (callFinishBooting) { 6731 Trace.traceBegin(Trace.TRACE_TAG_ACTIVITY_MANAGER, "FinishBooting"); 6732 finishBooting(); 6733 Trace.traceEnd(Trace.TRACE_TAG_ACTIVITY_MANAGER); 6734 } 6735 } 6736 6737 final void ensureBootCompleted() { 6738 boolean booting; 6739 boolean enableScreen; 6740 synchronized (this) { 6741 booting = mBooting; 6742 mBooting = false; 6743 enableScreen = !mBooted; 6744 mBooted = true; 6745 } 6746 6747 if (booting) { 6748 Trace.traceBegin(Trace.TRACE_TAG_ACTIVITY_MANAGER, "FinishBooting"); 6749 finishBooting(); 6750 Trace.traceEnd(Trace.TRACE_TAG_ACTIVITY_MANAGER); 6751 } 6752 6753 if (enableScreen) { 6754 enableScreenAfterBoot(); 6755 } 6756 } 6757 6758 @Override 6759 public final void activityResumed(IBinder token) { 6760 final long origId = Binder.clearCallingIdentity(); 6761 synchronized(this) { 6762 ActivityRecord.activityResumedLocked(token); 6763 mWindowManager.notifyAppResumedFinished(token); 6764 } 6765 Binder.restoreCallingIdentity(origId); 6766 } 6767 6768 @Override 6769 public final void activityPaused(IBinder token) { 6770 final long origId = Binder.clearCallingIdentity(); 6771 synchronized(this) { 6772 ActivityStack stack = ActivityRecord.getStackLocked(token); 6773 if (stack != null) { 6774 stack.activityPausedLocked(token, false); 6775 } 6776 } 6777 Binder.restoreCallingIdentity(origId); 6778 } 6779 6780 @Override 6781 public final void activityStopped(IBinder token, Bundle icicle, 6782 PersistableBundle persistentState, CharSequence description) { 6783 if (DEBUG_ALL) Slog.v(TAG, "Activity stopped: token=" + token); 6784 6785 // Refuse possible leaked file descriptors 6786 if (icicle != null && icicle.hasFileDescriptors()) { 6787 throw new IllegalArgumentException("File descriptors passed in Bundle"); 6788 } 6789 6790 final long origId = Binder.clearCallingIdentity(); 6791 6792 synchronized (this) { 6793 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 6794 if (r != null) { 6795 r.activityStoppedLocked(icicle, persistentState, description); 6796 } 6797 } 6798 6799 trimApplications(); 6800 6801 Binder.restoreCallingIdentity(origId); 6802 } 6803 6804 @Override 6805 public final void activityDestroyed(IBinder token) { 6806 if (DEBUG_SWITCH) Slog.v(TAG_SWITCH, "ACTIVITY DESTROYED: " + token); 6807 synchronized (this) { 6808 ActivityStack stack = ActivityRecord.getStackLocked(token); 6809 if (stack != null) { 6810 stack.activityDestroyedLocked(token, "activityDestroyed"); 6811 } 6812 } 6813 } 6814 6815 @Override 6816 public final void activityRelaunched(IBinder token) { 6817 final long origId = Binder.clearCallingIdentity(); 6818 synchronized (this) { 6819 mStackSupervisor.activityRelaunchedLocked(token); 6820 } 6821 Binder.restoreCallingIdentity(origId); 6822 } 6823 6824 @Override 6825 public void reportSizeConfigurations(IBinder token, int[] horizontalSizeConfiguration, 6826 int[] verticalSizeConfigurations, int[] smallestSizeConfigurations) { 6827 if (DEBUG_CONFIGURATION) Slog.v(TAG, "Report configuration: " + token + " " 6828 + horizontalSizeConfiguration + " " + verticalSizeConfigurations); 6829 synchronized (this) { 6830 ActivityRecord record = ActivityRecord.isInStackLocked(token); 6831 if (record == null) { 6832 throw new IllegalArgumentException("reportSizeConfigurations: ActivityRecord not " 6833 + "found for: " + token); 6834 } 6835 record.setSizeConfigurations(horizontalSizeConfiguration, 6836 verticalSizeConfigurations, smallestSizeConfigurations); 6837 } 6838 } 6839 6840 @Override 6841 public final void backgroundResourcesReleased(IBinder token) { 6842 final long origId = Binder.clearCallingIdentity(); 6843 try { 6844 synchronized (this) { 6845 ActivityStack stack = ActivityRecord.getStackLocked(token); 6846 if (stack != null) { 6847 stack.backgroundResourcesReleased(); 6848 } 6849 } 6850 } finally { 6851 Binder.restoreCallingIdentity(origId); 6852 } 6853 } 6854 6855 @Override 6856 public final void notifyLaunchTaskBehindComplete(IBinder token) { 6857 mStackSupervisor.scheduleLaunchTaskBehindComplete(token); 6858 } 6859 6860 @Override 6861 public final void notifyEnterAnimationComplete(IBinder token) { 6862 mHandler.sendMessage(mHandler.obtainMessage(ENTER_ANIMATION_COMPLETE_MSG, token)); 6863 } 6864 6865 @Override 6866 public String getCallingPackage(IBinder token) { 6867 synchronized (this) { 6868 ActivityRecord r = getCallingRecordLocked(token); 6869 return r != null ? r.info.packageName : null; 6870 } 6871 } 6872 6873 @Override 6874 public ComponentName getCallingActivity(IBinder token) { 6875 synchronized (this) { 6876 ActivityRecord r = getCallingRecordLocked(token); 6877 return r != null ? r.intent.getComponent() : null; 6878 } 6879 } 6880 6881 private ActivityRecord getCallingRecordLocked(IBinder token) { 6882 ActivityRecord r = ActivityRecord.isInStackLocked(token); 6883 if (r == null) { 6884 return null; 6885 } 6886 return r.resultTo; 6887 } 6888 6889 @Override 6890 public ComponentName getActivityClassForToken(IBinder token) { 6891 synchronized(this) { 6892 ActivityRecord r = ActivityRecord.isInStackLocked(token); 6893 if (r == null) { 6894 return null; 6895 } 6896 return r.intent.getComponent(); 6897 } 6898 } 6899 6900 @Override 6901 public String getPackageForToken(IBinder token) { 6902 synchronized(this) { 6903 ActivityRecord r = ActivityRecord.isInStackLocked(token); 6904 if (r == null) { 6905 return null; 6906 } 6907 return r.packageName; 6908 } 6909 } 6910 6911 @Override 6912 public boolean isRootVoiceInteraction(IBinder token) { 6913 synchronized(this) { 6914 ActivityRecord r = ActivityRecord.isInStackLocked(token); 6915 if (r == null) { 6916 return false; 6917 } 6918 return r.rootVoiceInteraction; 6919 } 6920 } 6921 6922 @Override 6923 public IIntentSender getIntentSender(int type, 6924 String packageName, IBinder token, String resultWho, 6925 int requestCode, Intent[] intents, String[] resolvedTypes, 6926 int flags, Bundle bOptions, int userId) { 6927 enforceNotIsolatedCaller("getIntentSender"); 6928 // Refuse possible leaked file descriptors 6929 if (intents != null) { 6930 if (intents.length < 1) { 6931 throw new IllegalArgumentException("Intents array length must be >= 1"); 6932 } 6933 for (int i=0; i<intents.length; i++) { 6934 Intent intent = intents[i]; 6935 if (intent != null) { 6936 if (intent.hasFileDescriptors()) { 6937 throw new IllegalArgumentException("File descriptors passed in Intent"); 6938 } 6939 if (type == ActivityManager.INTENT_SENDER_BROADCAST && 6940 (intent.getFlags()&Intent.FLAG_RECEIVER_BOOT_UPGRADE) != 0) { 6941 throw new IllegalArgumentException( 6942 "Can't use FLAG_RECEIVER_BOOT_UPGRADE here"); 6943 } 6944 intents[i] = new Intent(intent); 6945 } 6946 } 6947 if (resolvedTypes != null && resolvedTypes.length != intents.length) { 6948 throw new IllegalArgumentException( 6949 "Intent array length does not match resolvedTypes length"); 6950 } 6951 } 6952 if (bOptions != null) { 6953 if (bOptions.hasFileDescriptors()) { 6954 throw new IllegalArgumentException("File descriptors passed in options"); 6955 } 6956 } 6957 6958 synchronized(this) { 6959 int callingUid = Binder.getCallingUid(); 6960 int origUserId = userId; 6961 userId = mUserController.handleIncomingUser(Binder.getCallingPid(), callingUid, userId, 6962 type == ActivityManager.INTENT_SENDER_BROADCAST, 6963 ALLOW_NON_FULL, "getIntentSender", null); 6964 if (origUserId == UserHandle.USER_CURRENT) { 6965 // We don't want to evaluate this until the pending intent is 6966 // actually executed. However, we do want to always do the 6967 // security checking for it above. 6968 userId = UserHandle.USER_CURRENT; 6969 } 6970 try { 6971 if (callingUid != 0 && callingUid != Process.SYSTEM_UID) { 6972 final int uid = AppGlobals.getPackageManager().getPackageUid(packageName, 6973 MATCH_DEBUG_TRIAGED_MISSING, UserHandle.getUserId(callingUid)); 6974 if (!UserHandle.isSameApp(callingUid, uid)) { 6975 String msg = "Permission Denial: getIntentSender() from pid=" 6976 + Binder.getCallingPid() 6977 + ", uid=" + Binder.getCallingUid() 6978 + ", (need uid=" + uid + ")" 6979 + " is not allowed to send as package " + packageName; 6980 Slog.w(TAG, msg); 6981 throw new SecurityException(msg); 6982 } 6983 } 6984 6985 return getIntentSenderLocked(type, packageName, callingUid, userId, 6986 token, resultWho, requestCode, intents, resolvedTypes, flags, bOptions); 6987 6988 } catch (RemoteException e) { 6989 throw new SecurityException(e); 6990 } 6991 } 6992 } 6993 6994 IIntentSender getIntentSenderLocked(int type, String packageName, 6995 int callingUid, int userId, IBinder token, String resultWho, 6996 int requestCode, Intent[] intents, String[] resolvedTypes, int flags, 6997 Bundle bOptions) { 6998 if (DEBUG_MU) Slog.v(TAG_MU, "getIntentSenderLocked(): uid=" + callingUid); 6999 ActivityRecord activity = null; 7000 if (type == ActivityManager.INTENT_SENDER_ACTIVITY_RESULT) { 7001 activity = ActivityRecord.isInStackLocked(token); 7002 if (activity == null) { 7003 Slog.w(TAG, "Failed createPendingResult: activity " + token + " not in any stack"); 7004 return null; 7005 } 7006 if (activity.finishing) { 7007 Slog.w(TAG, "Failed createPendingResult: activity " + activity + " is finishing"); 7008 return null; 7009 } 7010 } 7011 7012 // We're going to be splicing together extras before sending, so we're 7013 // okay poking into any contained extras. 7014 if (intents != null) { 7015 for (int i = 0; i < intents.length; i++) { 7016 intents[i].setDefusable(true); 7017 } 7018 } 7019 Bundle.setDefusable(bOptions, true); 7020 7021 final boolean noCreate = (flags&PendingIntent.FLAG_NO_CREATE) != 0; 7022 final boolean cancelCurrent = (flags&PendingIntent.FLAG_CANCEL_CURRENT) != 0; 7023 final boolean updateCurrent = (flags&PendingIntent.FLAG_UPDATE_CURRENT) != 0; 7024 flags &= ~(PendingIntent.FLAG_NO_CREATE|PendingIntent.FLAG_CANCEL_CURRENT 7025 |PendingIntent.FLAG_UPDATE_CURRENT); 7026 7027 PendingIntentRecord.Key key = new PendingIntentRecord.Key( 7028 type, packageName, activity, resultWho, 7029 requestCode, intents, resolvedTypes, flags, bOptions, userId); 7030 WeakReference<PendingIntentRecord> ref; 7031 ref = mIntentSenderRecords.get(key); 7032 PendingIntentRecord rec = ref != null ? ref.get() : null; 7033 if (rec != null) { 7034 if (!cancelCurrent) { 7035 if (updateCurrent) { 7036 if (rec.key.requestIntent != null) { 7037 rec.key.requestIntent.replaceExtras(intents != null ? 7038 intents[intents.length - 1] : null); 7039 } 7040 if (intents != null) { 7041 intents[intents.length-1] = rec.key.requestIntent; 7042 rec.key.allIntents = intents; 7043 rec.key.allResolvedTypes = resolvedTypes; 7044 } else { 7045 rec.key.allIntents = null; 7046 rec.key.allResolvedTypes = null; 7047 } 7048 } 7049 return rec; 7050 } 7051 rec.canceled = true; 7052 mIntentSenderRecords.remove(key); 7053 } 7054 if (noCreate) { 7055 return rec; 7056 } 7057 rec = new PendingIntentRecord(this, key, callingUid); 7058 mIntentSenderRecords.put(key, rec.ref); 7059 if (type == ActivityManager.INTENT_SENDER_ACTIVITY_RESULT) { 7060 if (activity.pendingResults == null) { 7061 activity.pendingResults 7062 = new HashSet<WeakReference<PendingIntentRecord>>(); 7063 } 7064 activity.pendingResults.add(rec.ref); 7065 } 7066 return rec; 7067 } 7068 7069 @Override 7070 public int sendIntentSender(IIntentSender target, int code, Intent intent, String resolvedType, 7071 IIntentReceiver finishedReceiver, String requiredPermission, Bundle options) { 7072 if (target instanceof PendingIntentRecord) { 7073 return ((PendingIntentRecord)target).sendWithResult(code, intent, resolvedType, 7074 finishedReceiver, requiredPermission, options); 7075 } else { 7076 if (intent == null) { 7077 // Weird case: someone has given us their own custom IIntentSender, and now 7078 // they have someone else trying to send to it but of course this isn't 7079 // really a PendingIntent, so there is no base Intent, and the caller isn't 7080 // supplying an Intent... but we never want to dispatch a null Intent to 7081 // a receiver, so um... let's make something up. 7082 Slog.wtf(TAG, "Can't use null intent with direct IIntentSender call"); 7083 intent = new Intent(Intent.ACTION_MAIN); 7084 } 7085 try { 7086 target.send(code, intent, resolvedType, null, requiredPermission, options); 7087 } catch (RemoteException e) { 7088 } 7089 // Platform code can rely on getting a result back when the send is done, but if 7090 // this intent sender is from outside of the system we can't rely on it doing that. 7091 // So instead we don't give it the result receiver, and instead just directly 7092 // report the finish immediately. 7093 if (finishedReceiver != null) { 7094 try { 7095 finishedReceiver.performReceive(intent, 0, 7096 null, null, false, false, UserHandle.getCallingUserId()); 7097 } catch (RemoteException e) { 7098 } 7099 } 7100 return 0; 7101 } 7102 } 7103 7104 /** 7105 * Whitelists {@code targetUid} to temporarily bypass Power Save mode. 7106 * 7107 * <p>{@code callerUid} must be allowed to request such whitelist by calling 7108 * {@link #addTempPowerSaveWhitelistGrantorUid(int)}. 7109 */ 7110 void tempWhitelistAppForPowerSave(int callerPid, int callerUid, int targetUid, long duration) { 7111 if (DEBUG_WHITELISTS) { 7112 Slog.d(TAG, "tempWhitelistAppForPowerSave(" + callerPid + ", " + callerUid + ", " 7113 + targetUid + ", " + duration + ")"); 7114 } 7115 synchronized (mPidsSelfLocked) { 7116 final ProcessRecord pr = mPidsSelfLocked.get(callerPid); 7117 if (pr == null) { 7118 Slog.w(TAG, "tempWhitelistAppForPowerSave() no ProcessRecord for pid " + callerPid); 7119 return; 7120 } 7121 if (!pr.whitelistManager) { 7122 if (DEBUG_WHITELISTS) { 7123 Slog.d(TAG, "tempWhitelistAppForPowerSave() for target " + targetUid + ": pid " 7124 + callerPid + " is not allowed"); 7125 } 7126 return; 7127 } 7128 } 7129 7130 final long token = Binder.clearCallingIdentity(); 7131 try { 7132 mLocalDeviceIdleController.addPowerSaveTempWhitelistAppDirect(targetUid, duration, 7133 true, "pe from uid:" + callerUid); 7134 } finally { 7135 Binder.restoreCallingIdentity(token); 7136 } 7137 } 7138 7139 @Override 7140 public void cancelIntentSender(IIntentSender sender) { 7141 if (!(sender instanceof PendingIntentRecord)) { 7142 return; 7143 } 7144 synchronized(this) { 7145 PendingIntentRecord rec = (PendingIntentRecord)sender; 7146 try { 7147 final int uid = AppGlobals.getPackageManager().getPackageUid(rec.key.packageName, 7148 MATCH_DEBUG_TRIAGED_MISSING, UserHandle.getCallingUserId()); 7149 if (!UserHandle.isSameApp(uid, Binder.getCallingUid())) { 7150 String msg = "Permission Denial: cancelIntentSender() from pid=" 7151 + Binder.getCallingPid() 7152 + ", uid=" + Binder.getCallingUid() 7153 + " is not allowed to cancel packges " 7154 + rec.key.packageName; 7155 Slog.w(TAG, msg); 7156 throw new SecurityException(msg); 7157 } 7158 } catch (RemoteException e) { 7159 throw new SecurityException(e); 7160 } 7161 cancelIntentSenderLocked(rec, true); 7162 } 7163 } 7164 7165 void cancelIntentSenderLocked(PendingIntentRecord rec, boolean cleanActivity) { 7166 rec.canceled = true; 7167 mIntentSenderRecords.remove(rec.key); 7168 if (cleanActivity && rec.key.activity != null) { 7169 rec.key.activity.pendingResults.remove(rec.ref); 7170 } 7171 } 7172 7173 @Override 7174 public String getPackageForIntentSender(IIntentSender pendingResult) { 7175 if (!(pendingResult instanceof PendingIntentRecord)) { 7176 return null; 7177 } 7178 try { 7179 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 7180 return res.key.packageName; 7181 } catch (ClassCastException e) { 7182 } 7183 return null; 7184 } 7185 7186 @Override 7187 public int getUidForIntentSender(IIntentSender sender) { 7188 if (sender instanceof PendingIntentRecord) { 7189 try { 7190 PendingIntentRecord res = (PendingIntentRecord)sender; 7191 return res.uid; 7192 } catch (ClassCastException e) { 7193 } 7194 } 7195 return -1; 7196 } 7197 7198 @Override 7199 public boolean isIntentSenderTargetedToPackage(IIntentSender pendingResult) { 7200 if (!(pendingResult instanceof PendingIntentRecord)) { 7201 return false; 7202 } 7203 try { 7204 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 7205 if (res.key.allIntents == null) { 7206 return false; 7207 } 7208 for (int i=0; i<res.key.allIntents.length; i++) { 7209 Intent intent = res.key.allIntents[i]; 7210 if (intent.getPackage() != null && intent.getComponent() != null) { 7211 return false; 7212 } 7213 } 7214 return true; 7215 } catch (ClassCastException e) { 7216 } 7217 return false; 7218 } 7219 7220 @Override 7221 public boolean isIntentSenderAnActivity(IIntentSender pendingResult) { 7222 if (!(pendingResult instanceof PendingIntentRecord)) { 7223 return false; 7224 } 7225 try { 7226 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 7227 if (res.key.type == ActivityManager.INTENT_SENDER_ACTIVITY) { 7228 return true; 7229 } 7230 return false; 7231 } catch (ClassCastException e) { 7232 } 7233 return false; 7234 } 7235 7236 @Override 7237 public Intent getIntentForIntentSender(IIntentSender pendingResult) { 7238 enforceCallingPermission(Manifest.permission.GET_INTENT_SENDER_INTENT, 7239 "getIntentForIntentSender()"); 7240 if (!(pendingResult instanceof PendingIntentRecord)) { 7241 return null; 7242 } 7243 try { 7244 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 7245 return res.key.requestIntent != null ? new Intent(res.key.requestIntent) : null; 7246 } catch (ClassCastException e) { 7247 } 7248 return null; 7249 } 7250 7251 @Override 7252 public String getTagForIntentSender(IIntentSender pendingResult, String prefix) { 7253 if (!(pendingResult instanceof PendingIntentRecord)) { 7254 return null; 7255 } 7256 try { 7257 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 7258 synchronized (this) { 7259 return getTagForIntentSenderLocked(res, prefix); 7260 } 7261 } catch (ClassCastException e) { 7262 } 7263 return null; 7264 } 7265 7266 String getTagForIntentSenderLocked(PendingIntentRecord res, String prefix) { 7267 final Intent intent = res.key.requestIntent; 7268 if (intent != null) { 7269 if (res.lastTag != null && res.lastTagPrefix == prefix && (res.lastTagPrefix == null 7270 || res.lastTagPrefix.equals(prefix))) { 7271 return res.lastTag; 7272 } 7273 res.lastTagPrefix = prefix; 7274 final StringBuilder sb = new StringBuilder(128); 7275 if (prefix != null) { 7276 sb.append(prefix); 7277 } 7278 if (intent.getAction() != null) { 7279 sb.append(intent.getAction()); 7280 } else if (intent.getComponent() != null) { 7281 intent.getComponent().appendShortString(sb); 7282 } else { 7283 sb.append("?"); 7284 } 7285 return res.lastTag = sb.toString(); 7286 } 7287 return null; 7288 } 7289 7290 @Override 7291 public void setProcessLimit(int max) { 7292 enforceCallingPermission(android.Manifest.permission.SET_PROCESS_LIMIT, 7293 "setProcessLimit()"); 7294 synchronized (this) { 7295 mProcessLimit = max < 0 ? ProcessList.MAX_CACHED_APPS : max; 7296 mProcessLimitOverride = max; 7297 } 7298 trimApplications(); 7299 } 7300 7301 @Override 7302 public int getProcessLimit() { 7303 synchronized (this) { 7304 return mProcessLimitOverride; 7305 } 7306 } 7307 7308 void foregroundTokenDied(ForegroundToken token) { 7309 synchronized (ActivityManagerService.this) { 7310 synchronized (mPidsSelfLocked) { 7311 ForegroundToken cur 7312 = mForegroundProcesses.get(token.pid); 7313 if (cur != token) { 7314 return; 7315 } 7316 mForegroundProcesses.remove(token.pid); 7317 ProcessRecord pr = mPidsSelfLocked.get(token.pid); 7318 if (pr == null) { 7319 return; 7320 } 7321 pr.forcingToForeground = null; 7322 updateProcessForegroundLocked(pr, false, false); 7323 } 7324 updateOomAdjLocked(); 7325 } 7326 } 7327 7328 @Override 7329 public void setProcessForeground(IBinder token, int pid, boolean isForeground) { 7330 enforceCallingPermission(android.Manifest.permission.SET_PROCESS_LIMIT, 7331 "setProcessForeground()"); 7332 synchronized(this) { 7333 boolean changed = false; 7334 7335 synchronized (mPidsSelfLocked) { 7336 ProcessRecord pr = mPidsSelfLocked.get(pid); 7337 if (pr == null && isForeground) { 7338 Slog.w(TAG, "setProcessForeground called on unknown pid: " + pid); 7339 return; 7340 } 7341 ForegroundToken oldToken = mForegroundProcesses.get(pid); 7342 if (oldToken != null) { 7343 oldToken.token.unlinkToDeath(oldToken, 0); 7344 mForegroundProcesses.remove(pid); 7345 if (pr != null) { 7346 pr.forcingToForeground = null; 7347 } 7348 changed = true; 7349 } 7350 if (isForeground && token != null) { 7351 ForegroundToken newToken = new ForegroundToken() { 7352 @Override 7353 public void binderDied() { 7354 foregroundTokenDied(this); 7355 } 7356 }; 7357 newToken.pid = pid; 7358 newToken.token = token; 7359 try { 7360 token.linkToDeath(newToken, 0); 7361 mForegroundProcesses.put(pid, newToken); 7362 pr.forcingToForeground = token; 7363 changed = true; 7364 } catch (RemoteException e) { 7365 // If the process died while doing this, we will later 7366 // do the cleanup with the process death link. 7367 } 7368 } 7369 } 7370 7371 if (changed) { 7372 updateOomAdjLocked(); 7373 } 7374 } 7375 } 7376 7377 @Override 7378 public boolean isAppForeground(int uid) throws RemoteException { 7379 synchronized (this) { 7380 UidRecord uidRec = mActiveUids.get(uid); 7381 if (uidRec == null || uidRec.idle) { 7382 return false; 7383 } 7384 return uidRec.curProcState <= ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 7385 } 7386 } 7387 7388 // NOTE: this is an internal method used by the OnShellCommand implementation only and should 7389 // be guarded by permission checking. 7390 int getUidState(int uid) { 7391 synchronized (this) { 7392 UidRecord uidRec = mActiveUids.get(uid); 7393 return uidRec == null ? ActivityManager.PROCESS_STATE_NONEXISTENT : uidRec.curProcState; 7394 } 7395 } 7396 7397 @Override 7398 public boolean isInMultiWindowMode(IBinder token) { 7399 final long origId = Binder.clearCallingIdentity(); 7400 try { 7401 synchronized(this) { 7402 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 7403 if (r == null) { 7404 return false; 7405 } 7406 // An activity is consider to be in multi-window mode if its task isn't fullscreen. 7407 return !r.task.mFullscreen; 7408 } 7409 } finally { 7410 Binder.restoreCallingIdentity(origId); 7411 } 7412 } 7413 7414 @Override 7415 public boolean isInPictureInPictureMode(IBinder token) { 7416 final long origId = Binder.clearCallingIdentity(); 7417 try { 7418 synchronized(this) { 7419 final ActivityStack stack = ActivityRecord.getStackLocked(token); 7420 if (stack == null) { 7421 return false; 7422 } 7423 return stack.mStackId == PINNED_STACK_ID; 7424 } 7425 } finally { 7426 Binder.restoreCallingIdentity(origId); 7427 } 7428 } 7429 7430 @Override 7431 public void enterPictureInPictureMode(IBinder token) { 7432 final long origId = Binder.clearCallingIdentity(); 7433 try { 7434 synchronized(this) { 7435 if (!mSupportsPictureInPicture) { 7436 throw new IllegalStateException("enterPictureInPictureMode: " 7437 + "Device doesn't support picture-in-picture mode."); 7438 } 7439 7440 final ActivityRecord r = ActivityRecord.forTokenLocked(token); 7441 7442 if (r == null) { 7443 throw new IllegalStateException("enterPictureInPictureMode: " 7444 + "Can't find activity for token=" + token); 7445 } 7446 7447 if (!r.supportsPictureInPicture()) { 7448 throw new IllegalArgumentException("enterPictureInPictureMode: " 7449 + "Picture-In-Picture not supported for r=" + r); 7450 } 7451 7452 // Use the default launch bounds for pinned stack if it doesn't exist yet or use the 7453 // current bounds. 7454 final ActivityStack pinnedStack = mStackSupervisor.getStack(PINNED_STACK_ID); 7455 final Rect bounds = (pinnedStack != null) 7456 ? pinnedStack.mBounds 7457 : mWindowManager.getPictureInPictureDefaultBounds(DEFAULT_DISPLAY); 7458 7459 mStackSupervisor.moveActivityToPinnedStackLocked( 7460 r, "enterPictureInPictureMode", bounds); 7461 } 7462 } finally { 7463 Binder.restoreCallingIdentity(origId); 7464 } 7465 } 7466 7467 // ========================================================= 7468 // PROCESS INFO 7469 // ========================================================= 7470 7471 static class ProcessInfoService extends IProcessInfoService.Stub { 7472 final ActivityManagerService mActivityManagerService; 7473 ProcessInfoService(ActivityManagerService activityManagerService) { 7474 mActivityManagerService = activityManagerService; 7475 } 7476 7477 @Override 7478 public void getProcessStatesFromPids(/*in*/ int[] pids, /*out*/ int[] states) { 7479 mActivityManagerService.getProcessStatesAndOomScoresForPIDs( 7480 /*in*/ pids, /*out*/ states, null); 7481 } 7482 7483 @Override 7484 public void getProcessStatesAndOomScoresFromPids( 7485 /*in*/ int[] pids, /*out*/ int[] states, /*out*/ int[] scores) { 7486 mActivityManagerService.getProcessStatesAndOomScoresForPIDs( 7487 /*in*/ pids, /*out*/ states, /*out*/ scores); 7488 } 7489 } 7490 7491 /** 7492 * For each PID in the given input array, write the current process state 7493 * for that process into the states array, or -1 to indicate that no 7494 * process with the given PID exists. If scores array is provided, write 7495 * the oom score for the process into the scores array, with INVALID_ADJ 7496 * indicating the PID doesn't exist. 7497 */ 7498 public void getProcessStatesAndOomScoresForPIDs( 7499 /*in*/ int[] pids, /*out*/ int[] states, /*out*/ int[] scores) { 7500 if (scores != null) { 7501 enforceCallingPermission(android.Manifest.permission.GET_PROCESS_STATE_AND_OOM_SCORE, 7502 "getProcessStatesAndOomScoresForPIDs()"); 7503 } 7504 7505 if (pids == null) { 7506 throw new NullPointerException("pids"); 7507 } else if (states == null) { 7508 throw new NullPointerException("states"); 7509 } else if (pids.length != states.length) { 7510 throw new IllegalArgumentException("pids and states arrays have different lengths!"); 7511 } else if (scores != null && pids.length != scores.length) { 7512 throw new IllegalArgumentException("pids and scores arrays have different lengths!"); 7513 } 7514 7515 synchronized (mPidsSelfLocked) { 7516 for (int i = 0; i < pids.length; i++) { 7517 ProcessRecord pr = mPidsSelfLocked.get(pids[i]); 7518 states[i] = (pr == null) ? ActivityManager.PROCESS_STATE_NONEXISTENT : 7519 pr.curProcState; 7520 if (scores != null) { 7521 scores[i] = (pr == null) ? ProcessList.INVALID_ADJ : pr.curAdj; 7522 } 7523 } 7524 } 7525 } 7526 7527 // ========================================================= 7528 // PERMISSIONS 7529 // ========================================================= 7530 7531 static class PermissionController extends IPermissionController.Stub { 7532 ActivityManagerService mActivityManagerService; 7533 PermissionController(ActivityManagerService activityManagerService) { 7534 mActivityManagerService = activityManagerService; 7535 } 7536 7537 @Override 7538 public boolean checkPermission(String permission, int pid, int uid) { 7539 return mActivityManagerService.checkPermission(permission, pid, 7540 uid) == PackageManager.PERMISSION_GRANTED; 7541 } 7542 7543 @Override 7544 public String[] getPackagesForUid(int uid) { 7545 return mActivityManagerService.mContext.getPackageManager() 7546 .getPackagesForUid(uid); 7547 } 7548 7549 @Override 7550 public boolean isRuntimePermission(String permission) { 7551 try { 7552 PermissionInfo info = mActivityManagerService.mContext.getPackageManager() 7553 .getPermissionInfo(permission, 0); 7554 return (info.protectionLevel & PermissionInfo.PROTECTION_MASK_BASE) 7555 == PermissionInfo.PROTECTION_DANGEROUS; 7556 } catch (NameNotFoundException nnfe) { 7557 Slog.e(TAG, "No such permission: "+ permission, nnfe); 7558 } 7559 return false; 7560 } 7561 } 7562 7563 class IntentFirewallInterface implements IntentFirewall.AMSInterface { 7564 @Override 7565 public int checkComponentPermission(String permission, int pid, int uid, 7566 int owningUid, boolean exported) { 7567 return ActivityManagerService.this.checkComponentPermission(permission, pid, uid, 7568 owningUid, exported); 7569 } 7570 7571 @Override 7572 public Object getAMSLock() { 7573 return ActivityManagerService.this; 7574 } 7575 } 7576 7577 /** 7578 * This can be called with or without the global lock held. 7579 */ 7580 int checkComponentPermission(String permission, int pid, int uid, 7581 int owningUid, boolean exported) { 7582 if (pid == MY_PID) { 7583 return PackageManager.PERMISSION_GRANTED; 7584 } 7585 return ActivityManager.checkComponentPermission(permission, uid, 7586 owningUid, exported); 7587 } 7588 7589 /** 7590 * As the only public entry point for permissions checking, this method 7591 * can enforce the semantic that requesting a check on a null global 7592 * permission is automatically denied. (Internally a null permission 7593 * string is used when calling {@link #checkComponentPermission} in cases 7594 * when only uid-based security is needed.) 7595 * 7596 * This can be called with or without the global lock held. 7597 */ 7598 @Override 7599 public int checkPermission(String permission, int pid, int uid) { 7600 if (permission == null) { 7601 return PackageManager.PERMISSION_DENIED; 7602 } 7603 return checkComponentPermission(permission, pid, uid, -1, true); 7604 } 7605 7606 @Override 7607 public int checkPermissionWithToken(String permission, int pid, int uid, IBinder callerToken) { 7608 if (permission == null) { 7609 return PackageManager.PERMISSION_DENIED; 7610 } 7611 7612 // We might be performing an operation on behalf of an indirect binder 7613 // invocation, e.g. via {@link #openContentUri}. Check and adjust the 7614 // client identity accordingly before proceeding. 7615 Identity tlsIdentity = sCallerIdentity.get(); 7616 if (tlsIdentity != null && tlsIdentity.token == callerToken) { 7617 Slog.d(TAG, "checkComponentPermission() adjusting {pid,uid} to {" 7618 + tlsIdentity.pid + "," + tlsIdentity.uid + "}"); 7619 uid = tlsIdentity.uid; 7620 pid = tlsIdentity.pid; 7621 } 7622 7623 return checkComponentPermission(permission, pid, uid, -1, true); 7624 } 7625 7626 /** 7627 * Binder IPC calls go through the public entry point. 7628 * This can be called with or without the global lock held. 7629 */ 7630 int checkCallingPermission(String permission) { 7631 return checkPermission(permission, 7632 Binder.getCallingPid(), 7633 UserHandle.getAppId(Binder.getCallingUid())); 7634 } 7635 7636 /** 7637 * This can be called with or without the global lock held. 7638 */ 7639 void enforceCallingPermission(String permission, String func) { 7640 if (checkCallingPermission(permission) 7641 == PackageManager.PERMISSION_GRANTED) { 7642 return; 7643 } 7644 7645 String msg = "Permission Denial: " + func + " from pid=" 7646 + Binder.getCallingPid() 7647 + ", uid=" + Binder.getCallingUid() 7648 + " requires " + permission; 7649 Slog.w(TAG, msg); 7650 throw new SecurityException(msg); 7651 } 7652 7653 /** 7654 * Determine if UID is holding permissions required to access {@link Uri} in 7655 * the given {@link ProviderInfo}. Final permission checking is always done 7656 * in {@link ContentProvider}. 7657 */ 7658 private final boolean checkHoldingPermissionsLocked( 7659 IPackageManager pm, ProviderInfo pi, GrantUri grantUri, int uid, final int modeFlags) { 7660 if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION, 7661 "checkHoldingPermissionsLocked: uri=" + grantUri + " uid=" + uid); 7662 if (UserHandle.getUserId(uid) != grantUri.sourceUserId) { 7663 if (ActivityManager.checkComponentPermission(INTERACT_ACROSS_USERS, uid, -1, true) 7664 != PERMISSION_GRANTED) { 7665 return false; 7666 } 7667 } 7668 return checkHoldingPermissionsInternalLocked(pm, pi, grantUri, uid, modeFlags, true); 7669 } 7670 7671 private final boolean checkHoldingPermissionsInternalLocked(IPackageManager pm, ProviderInfo pi, 7672 GrantUri grantUri, int uid, final int modeFlags, boolean considerUidPermissions) { 7673 if (pi.applicationInfo.uid == uid) { 7674 return true; 7675 } else if (!pi.exported) { 7676 return false; 7677 } 7678 7679 boolean readMet = (modeFlags & Intent.FLAG_GRANT_READ_URI_PERMISSION) == 0; 7680 boolean writeMet = (modeFlags & Intent.FLAG_GRANT_WRITE_URI_PERMISSION) == 0; 7681 try { 7682 // check if target holds top-level <provider> permissions 7683 if (!readMet && pi.readPermission != null && considerUidPermissions 7684 && (pm.checkUidPermission(pi.readPermission, uid) == PERMISSION_GRANTED)) { 7685 readMet = true; 7686 } 7687 if (!writeMet && pi.writePermission != null && considerUidPermissions 7688 && (pm.checkUidPermission(pi.writePermission, uid) == PERMISSION_GRANTED)) { 7689 writeMet = true; 7690 } 7691 7692 // track if unprotected read/write is allowed; any denied 7693 // <path-permission> below removes this ability 7694 boolean allowDefaultRead = pi.readPermission == null; 7695 boolean allowDefaultWrite = pi.writePermission == null; 7696 7697 // check if target holds any <path-permission> that match uri 7698 final PathPermission[] pps = pi.pathPermissions; 7699 if (pps != null) { 7700 final String path = grantUri.uri.getPath(); 7701 int i = pps.length; 7702 while (i > 0 && (!readMet || !writeMet)) { 7703 i--; 7704 PathPermission pp = pps[i]; 7705 if (pp.match(path)) { 7706 if (!readMet) { 7707 final String pprperm = pp.getReadPermission(); 7708 if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION, 7709 "Checking read perm for " + pprperm + " for " + pp.getPath() 7710 + ": match=" + pp.match(path) 7711 + " check=" + pm.checkUidPermission(pprperm, uid)); 7712 if (pprperm != null) { 7713 if (considerUidPermissions && pm.checkUidPermission(pprperm, uid) 7714 == PERMISSION_GRANTED) { 7715 readMet = true; 7716 } else { 7717 allowDefaultRead = false; 7718 } 7719 } 7720 } 7721 if (!writeMet) { 7722 final String ppwperm = pp.getWritePermission(); 7723 if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION, 7724 "Checking write perm " + ppwperm + " for " + pp.getPath() 7725 + ": match=" + pp.match(path) 7726 + " check=" + pm.checkUidPermission(ppwperm, uid)); 7727 if (ppwperm != null) { 7728 if (considerUidPermissions && pm.checkUidPermission(ppwperm, uid) 7729 == PERMISSION_GRANTED) { 7730 writeMet = true; 7731 } else { 7732 allowDefaultWrite = false; 7733 } 7734 } 7735 } 7736 } 7737 } 7738 } 7739 7740 // grant unprotected <provider> read/write, if not blocked by 7741 // <path-permission> above 7742 if (allowDefaultRead) readMet = true; 7743 if (allowDefaultWrite) writeMet = true; 7744 7745 } catch (RemoteException e) { 7746 return false; 7747 } 7748 7749 return readMet && writeMet; 7750 } 7751 7752 public int getAppStartMode(int uid, String packageName) { 7753 synchronized (this) { 7754 return checkAllowBackgroundLocked(uid, packageName, -1, true); 7755 } 7756 } 7757 7758 int checkAllowBackgroundLocked(int uid, String packageName, int callingPid, 7759 boolean allowWhenForeground) { 7760 UidRecord uidRec = mActiveUids.get(uid); 7761 if (!mLenientBackgroundCheck) { 7762 if (!allowWhenForeground || uidRec == null 7763 || uidRec.curProcState >= ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND) { 7764 if (mAppOpsService.noteOperation(AppOpsManager.OP_RUN_IN_BACKGROUND, uid, 7765 packageName) != AppOpsManager.MODE_ALLOWED) { 7766 return ActivityManager.APP_START_MODE_DELAYED; 7767 } 7768 } 7769 7770 } else if (uidRec == null || uidRec.idle) { 7771 if (callingPid >= 0) { 7772 ProcessRecord proc; 7773 synchronized (mPidsSelfLocked) { 7774 proc = mPidsSelfLocked.get(callingPid); 7775 } 7776 if (proc != null && proc.curProcState < ActivityManager.PROCESS_STATE_RECEIVER) { 7777 // Whoever is instigating this is in the foreground, so we will allow it 7778 // to go through. 7779 return ActivityManager.APP_START_MODE_NORMAL; 7780 } 7781 } 7782 if (mAppOpsService.noteOperation(AppOpsManager.OP_RUN_IN_BACKGROUND, uid, packageName) 7783 != AppOpsManager.MODE_ALLOWED) { 7784 return ActivityManager.APP_START_MODE_DELAYED; 7785 } 7786 } 7787 return ActivityManager.APP_START_MODE_NORMAL; 7788 } 7789 7790 private ProviderInfo getProviderInfoLocked(String authority, int userHandle, int pmFlags) { 7791 ProviderInfo pi = null; 7792 ContentProviderRecord cpr = mProviderMap.getProviderByName(authority, userHandle); 7793 if (cpr != null) { 7794 pi = cpr.info; 7795 } else { 7796 try { 7797 pi = AppGlobals.getPackageManager().resolveContentProvider( 7798 authority, PackageManager.GET_URI_PERMISSION_PATTERNS | pmFlags, 7799 userHandle); 7800 } catch (RemoteException ex) { 7801 } 7802 } 7803 return pi; 7804 } 7805 7806 private UriPermission findUriPermissionLocked(int targetUid, GrantUri grantUri) { 7807 final ArrayMap<GrantUri, UriPermission> targetUris = mGrantedUriPermissions.get(targetUid); 7808 if (targetUris != null) { 7809 return targetUris.get(grantUri); 7810 } 7811 return null; 7812 } 7813 7814 private UriPermission findOrCreateUriPermissionLocked(String sourcePkg, 7815 String targetPkg, int targetUid, GrantUri grantUri) { 7816 ArrayMap<GrantUri, UriPermission> targetUris = mGrantedUriPermissions.get(targetUid); 7817 if (targetUris == null) { 7818 targetUris = Maps.newArrayMap(); 7819 mGrantedUriPermissions.put(targetUid, targetUris); 7820 } 7821 7822 UriPermission perm = targetUris.get(grantUri); 7823 if (perm == null) { 7824 perm = new UriPermission(sourcePkg, targetPkg, targetUid, grantUri); 7825 targetUris.put(grantUri, perm); 7826 } 7827 7828 return perm; 7829 } 7830 7831 private final boolean checkUriPermissionLocked(GrantUri grantUri, int uid, 7832 final int modeFlags) { 7833 final boolean persistable = (modeFlags & Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION) != 0; 7834 final int minStrength = persistable ? UriPermission.STRENGTH_PERSISTABLE 7835 : UriPermission.STRENGTH_OWNED; 7836 7837 // Root gets to do everything. 7838 if (uid == 0) { 7839 return true; 7840 } 7841 7842 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get(uid); 7843 if (perms == null) return false; 7844 7845 // First look for exact match 7846 final UriPermission exactPerm = perms.get(grantUri); 7847 if (exactPerm != null && exactPerm.getStrength(modeFlags) >= minStrength) { 7848 return true; 7849 } 7850 7851 // No exact match, look for prefixes 7852 final int N = perms.size(); 7853 for (int i = 0; i < N; i++) { 7854 final UriPermission perm = perms.valueAt(i); 7855 if (perm.uri.prefix && grantUri.uri.isPathPrefixMatch(perm.uri.uri) 7856 && perm.getStrength(modeFlags) >= minStrength) { 7857 return true; 7858 } 7859 } 7860 7861 return false; 7862 } 7863 7864 /** 7865 * @param uri This uri must NOT contain an embedded userId. 7866 * @param userId The userId in which the uri is to be resolved. 7867 */ 7868 @Override 7869 public int checkUriPermission(Uri uri, int pid, int uid, 7870 final int modeFlags, int userId, IBinder callerToken) { 7871 enforceNotIsolatedCaller("checkUriPermission"); 7872 7873 // Another redirected-binder-call permissions check as in 7874 // {@link checkPermissionWithToken}. 7875 Identity tlsIdentity = sCallerIdentity.get(); 7876 if (tlsIdentity != null && tlsIdentity.token == callerToken) { 7877 uid = tlsIdentity.uid; 7878 pid = tlsIdentity.pid; 7879 } 7880 7881 // Our own process gets to do everything. 7882 if (pid == MY_PID) { 7883 return PackageManager.PERMISSION_GRANTED; 7884 } 7885 synchronized (this) { 7886 return checkUriPermissionLocked(new GrantUri(userId, uri, false), uid, modeFlags) 7887 ? PackageManager.PERMISSION_GRANTED 7888 : PackageManager.PERMISSION_DENIED; 7889 } 7890 } 7891 7892 /** 7893 * Check if the targetPkg can be granted permission to access uri by 7894 * the callingUid using the given modeFlags. Throws a security exception 7895 * if callingUid is not allowed to do this. Returns the uid of the target 7896 * if the URI permission grant should be performed; returns -1 if it is not 7897 * needed (for example targetPkg already has permission to access the URI). 7898 * If you already know the uid of the target, you can supply it in 7899 * lastTargetUid else set that to -1. 7900 */ 7901 int checkGrantUriPermissionLocked(int callingUid, String targetPkg, GrantUri grantUri, 7902 final int modeFlags, int lastTargetUid) { 7903 if (!Intent.isAccessUriMode(modeFlags)) { 7904 return -1; 7905 } 7906 7907 if (targetPkg != null) { 7908 if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION, 7909 "Checking grant " + targetPkg + " permission to " + grantUri); 7910 } 7911 7912 final IPackageManager pm = AppGlobals.getPackageManager(); 7913 7914 // If this is not a content: uri, we can't do anything with it. 7915 if (!ContentResolver.SCHEME_CONTENT.equals(grantUri.uri.getScheme())) { 7916 if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION, 7917 "Can't grant URI permission for non-content URI: " + grantUri); 7918 return -1; 7919 } 7920 7921 final String authority = grantUri.uri.getAuthority(); 7922 final ProviderInfo pi = getProviderInfoLocked(authority, grantUri.sourceUserId, 7923 MATCH_DEBUG_TRIAGED_MISSING); 7924 if (pi == null) { 7925 Slog.w(TAG, "No content provider found for permission check: " + 7926 grantUri.uri.toSafeString()); 7927 return -1; 7928 } 7929 7930 int targetUid = lastTargetUid; 7931 if (targetUid < 0 && targetPkg != null) { 7932 try { 7933 targetUid = pm.getPackageUid(targetPkg, MATCH_DEBUG_TRIAGED_MISSING, 7934 UserHandle.getUserId(callingUid)); 7935 if (targetUid < 0) { 7936 if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION, 7937 "Can't grant URI permission no uid for: " + targetPkg); 7938 return -1; 7939 } 7940 } catch (RemoteException ex) { 7941 return -1; 7942 } 7943 } 7944 7945 if (targetUid >= 0) { 7946 // First... does the target actually need this permission? 7947 if (checkHoldingPermissionsLocked(pm, pi, grantUri, targetUid, modeFlags)) { 7948 // No need to grant the target this permission. 7949 if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION, 7950 "Target " + targetPkg + " already has full permission to " + grantUri); 7951 return -1; 7952 } 7953 } else { 7954 // First... there is no target package, so can anyone access it? 7955 boolean allowed = pi.exported; 7956 if ((modeFlags&Intent.FLAG_GRANT_READ_URI_PERMISSION) != 0) { 7957 if (pi.readPermission != null) { 7958 allowed = false; 7959 } 7960 } 7961 if ((modeFlags&Intent.FLAG_GRANT_WRITE_URI_PERMISSION) != 0) { 7962 if (pi.writePermission != null) { 7963 allowed = false; 7964 } 7965 } 7966 if (allowed) { 7967 return -1; 7968 } 7969 } 7970 7971 /* There is a special cross user grant if: 7972 * - The target is on another user. 7973 * - Apps on the current user can access the uri without any uid permissions. 7974 * In this case, we grant a uri permission, even if the ContentProvider does not normally 7975 * grant uri permissions. 7976 */ 7977 boolean specialCrossUserGrant = UserHandle.getUserId(targetUid) != grantUri.sourceUserId 7978 && checkHoldingPermissionsInternalLocked(pm, pi, grantUri, callingUid, 7979 modeFlags, false /*without considering the uid permissions*/); 7980 7981 // Second... is the provider allowing granting of URI permissions? 7982 if (!specialCrossUserGrant) { 7983 if (!pi.grantUriPermissions) { 7984 throw new SecurityException("Provider " + pi.packageName 7985 + "/" + pi.name 7986 + " does not allow granting of Uri permissions (uri " 7987 + grantUri + ")"); 7988 } 7989 if (pi.uriPermissionPatterns != null) { 7990 final int N = pi.uriPermissionPatterns.length; 7991 boolean allowed = false; 7992 for (int i=0; i<N; i++) { 7993 if (pi.uriPermissionPatterns[i] != null 7994 && pi.uriPermissionPatterns[i].match(grantUri.uri.getPath())) { 7995 allowed = true; 7996 break; 7997 } 7998 } 7999 if (!allowed) { 8000 throw new SecurityException("Provider " + pi.packageName 8001 + "/" + pi.name 8002 + " does not allow granting of permission to path of Uri " 8003 + grantUri); 8004 } 8005 } 8006 } 8007 8008 // Third... does the caller itself have permission to access 8009 // this uri? 8010 if (UserHandle.getAppId(callingUid) != Process.SYSTEM_UID) { 8011 if (!checkHoldingPermissionsLocked(pm, pi, grantUri, callingUid, modeFlags)) { 8012 // Require they hold a strong enough Uri permission 8013 if (!checkUriPermissionLocked(grantUri, callingUid, modeFlags)) { 8014 throw new SecurityException("Uid " + callingUid 8015 + " does not have permission to uri " + grantUri); 8016 } 8017 } 8018 } 8019 return targetUid; 8020 } 8021 8022 /** 8023 * @param uri This uri must NOT contain an embedded userId. 8024 * @param userId The userId in which the uri is to be resolved. 8025 */ 8026 @Override 8027 public int checkGrantUriPermission(int callingUid, String targetPkg, Uri uri, 8028 final int modeFlags, int userId) { 8029 enforceNotIsolatedCaller("checkGrantUriPermission"); 8030 synchronized(this) { 8031 return checkGrantUriPermissionLocked(callingUid, targetPkg, 8032 new GrantUri(userId, uri, false), modeFlags, -1); 8033 } 8034 } 8035 8036 void grantUriPermissionUncheckedLocked(int targetUid, String targetPkg, GrantUri grantUri, 8037 final int modeFlags, UriPermissionOwner owner) { 8038 if (!Intent.isAccessUriMode(modeFlags)) { 8039 return; 8040 } 8041 8042 // So here we are: the caller has the assumed permission 8043 // to the uri, and the target doesn't. Let's now give this to 8044 // the target. 8045 8046 if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION, 8047 "Granting " + targetPkg + "/" + targetUid + " permission to " + grantUri); 8048 8049 final String authority = grantUri.uri.getAuthority(); 8050 final ProviderInfo pi = getProviderInfoLocked(authority, grantUri.sourceUserId, 8051 MATCH_DEBUG_TRIAGED_MISSING); 8052 if (pi == null) { 8053 Slog.w(TAG, "No content provider found for grant: " + grantUri.toSafeString()); 8054 return; 8055 } 8056 8057 if ((modeFlags & Intent.FLAG_GRANT_PREFIX_URI_PERMISSION) != 0) { 8058 grantUri.prefix = true; 8059 } 8060 final UriPermission perm = findOrCreateUriPermissionLocked( 8061 pi.packageName, targetPkg, targetUid, grantUri); 8062 perm.grantModes(modeFlags, owner); 8063 } 8064 8065 void grantUriPermissionLocked(int callingUid, String targetPkg, GrantUri grantUri, 8066 final int modeFlags, UriPermissionOwner owner, int targetUserId) { 8067 if (targetPkg == null) { 8068 throw new NullPointerException("targetPkg"); 8069 } 8070 int targetUid; 8071 final IPackageManager pm = AppGlobals.getPackageManager(); 8072 try { 8073 targetUid = pm.getPackageUid(targetPkg, MATCH_DEBUG_TRIAGED_MISSING, targetUserId); 8074 } catch (RemoteException ex) { 8075 return; 8076 } 8077 8078 targetUid = checkGrantUriPermissionLocked(callingUid, targetPkg, grantUri, modeFlags, 8079 targetUid); 8080 if (targetUid < 0) { 8081 return; 8082 } 8083 8084 grantUriPermissionUncheckedLocked(targetUid, targetPkg, grantUri, modeFlags, 8085 owner); 8086 } 8087 8088 static class NeededUriGrants extends ArrayList<GrantUri> { 8089 final String targetPkg; 8090 final int targetUid; 8091 final int flags; 8092 8093 NeededUriGrants(String targetPkg, int targetUid, int flags) { 8094 this.targetPkg = targetPkg; 8095 this.targetUid = targetUid; 8096 this.flags = flags; 8097 } 8098 } 8099 8100 /** 8101 * Like checkGrantUriPermissionLocked, but takes an Intent. 8102 */ 8103 NeededUriGrants checkGrantUriPermissionFromIntentLocked(int callingUid, 8104 String targetPkg, Intent intent, int mode, NeededUriGrants needed, int targetUserId) { 8105 if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION, 8106 "Checking URI perm to data=" + (intent != null ? intent.getData() : null) 8107 + " clip=" + (intent != null ? intent.getClipData() : null) 8108 + " from " + intent + "; flags=0x" 8109 + Integer.toHexString(intent != null ? intent.getFlags() : 0)); 8110 8111 if (targetPkg == null) { 8112 throw new NullPointerException("targetPkg"); 8113 } 8114 8115 if (intent == null) { 8116 return null; 8117 } 8118 Uri data = intent.getData(); 8119 ClipData clip = intent.getClipData(); 8120 if (data == null && clip == null) { 8121 return null; 8122 } 8123 // Default userId for uris in the intent (if they don't specify it themselves) 8124 int contentUserHint = intent.getContentUserHint(); 8125 if (contentUserHint == UserHandle.USER_CURRENT) { 8126 contentUserHint = UserHandle.getUserId(callingUid); 8127 } 8128 final IPackageManager pm = AppGlobals.getPackageManager(); 8129 int targetUid; 8130 if (needed != null) { 8131 targetUid = needed.targetUid; 8132 } else { 8133 try { 8134 targetUid = pm.getPackageUid(targetPkg, MATCH_DEBUG_TRIAGED_MISSING, 8135 targetUserId); 8136 } catch (RemoteException ex) { 8137 return null; 8138 } 8139 if (targetUid < 0) { 8140 if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION, 8141 "Can't grant URI permission no uid for: " + targetPkg 8142 + " on user " + targetUserId); 8143 return null; 8144 } 8145 } 8146 if (data != null) { 8147 GrantUri grantUri = GrantUri.resolve(contentUserHint, data); 8148 targetUid = checkGrantUriPermissionLocked(callingUid, targetPkg, grantUri, mode, 8149 targetUid); 8150 if (targetUid > 0) { 8151 if (needed == null) { 8152 needed = new NeededUriGrants(targetPkg, targetUid, mode); 8153 } 8154 needed.add(grantUri); 8155 } 8156 } 8157 if (clip != null) { 8158 for (int i=0; i<clip.getItemCount(); i++) { 8159 Uri uri = clip.getItemAt(i).getUri(); 8160 if (uri != null) { 8161 GrantUri grantUri = GrantUri.resolve(contentUserHint, uri); 8162 targetUid = checkGrantUriPermissionLocked(callingUid, targetPkg, grantUri, mode, 8163 targetUid); 8164 if (targetUid > 0) { 8165 if (needed == null) { 8166 needed = new NeededUriGrants(targetPkg, targetUid, mode); 8167 } 8168 needed.add(grantUri); 8169 } 8170 } else { 8171 Intent clipIntent = clip.getItemAt(i).getIntent(); 8172 if (clipIntent != null) { 8173 NeededUriGrants newNeeded = checkGrantUriPermissionFromIntentLocked( 8174 callingUid, targetPkg, clipIntent, mode, needed, targetUserId); 8175 if (newNeeded != null) { 8176 needed = newNeeded; 8177 } 8178 } 8179 } 8180 } 8181 } 8182 8183 return needed; 8184 } 8185 8186 /** 8187 * Like grantUriPermissionUncheckedLocked, but takes an Intent. 8188 */ 8189 void grantUriPermissionUncheckedFromIntentLocked(NeededUriGrants needed, 8190 UriPermissionOwner owner) { 8191 if (needed != null) { 8192 for (int i=0; i<needed.size(); i++) { 8193 GrantUri grantUri = needed.get(i); 8194 grantUriPermissionUncheckedLocked(needed.targetUid, needed.targetPkg, 8195 grantUri, needed.flags, owner); 8196 } 8197 } 8198 } 8199 8200 void grantUriPermissionFromIntentLocked(int callingUid, 8201 String targetPkg, Intent intent, UriPermissionOwner owner, int targetUserId) { 8202 NeededUriGrants needed = checkGrantUriPermissionFromIntentLocked(callingUid, targetPkg, 8203 intent, intent != null ? intent.getFlags() : 0, null, targetUserId); 8204 if (needed == null) { 8205 return; 8206 } 8207 8208 grantUriPermissionUncheckedFromIntentLocked(needed, owner); 8209 } 8210 8211 /** 8212 * @param uri This uri must NOT contain an embedded userId. 8213 * @param userId The userId in which the uri is to be resolved. 8214 */ 8215 @Override 8216 public void grantUriPermission(IApplicationThread caller, String targetPkg, Uri uri, 8217 final int modeFlags, int userId) { 8218 enforceNotIsolatedCaller("grantUriPermission"); 8219 GrantUri grantUri = new GrantUri(userId, uri, false); 8220 synchronized(this) { 8221 final ProcessRecord r = getRecordForAppLocked(caller); 8222 if (r == null) { 8223 throw new SecurityException("Unable to find app for caller " 8224 + caller 8225 + " when granting permission to uri " + grantUri); 8226 } 8227 if (targetPkg == null) { 8228 throw new IllegalArgumentException("null target"); 8229 } 8230 if (grantUri == null) { 8231 throw new IllegalArgumentException("null uri"); 8232 } 8233 8234 Preconditions.checkFlagsArgument(modeFlags, Intent.FLAG_GRANT_READ_URI_PERMISSION 8235 | Intent.FLAG_GRANT_WRITE_URI_PERMISSION 8236 | Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION 8237 | Intent.FLAG_GRANT_PREFIX_URI_PERMISSION); 8238 8239 grantUriPermissionLocked(r.uid, targetPkg, grantUri, modeFlags, null, 8240 UserHandle.getUserId(r.uid)); 8241 } 8242 } 8243 8244 void removeUriPermissionIfNeededLocked(UriPermission perm) { 8245 if (perm.modeFlags == 0) { 8246 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get( 8247 perm.targetUid); 8248 if (perms != null) { 8249 if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION, 8250 "Removing " + perm.targetUid + " permission to " + perm.uri); 8251 8252 perms.remove(perm.uri); 8253 if (perms.isEmpty()) { 8254 mGrantedUriPermissions.remove(perm.targetUid); 8255 } 8256 } 8257 } 8258 } 8259 8260 private void revokeUriPermissionLocked(int callingUid, GrantUri grantUri, final int modeFlags) { 8261 if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION, 8262 "Revoking all granted permissions to " + grantUri); 8263 8264 final IPackageManager pm = AppGlobals.getPackageManager(); 8265 final String authority = grantUri.uri.getAuthority(); 8266 final ProviderInfo pi = getProviderInfoLocked(authority, grantUri.sourceUserId, 8267 MATCH_DIRECT_BOOT_AWARE | MATCH_DIRECT_BOOT_UNAWARE); 8268 if (pi == null) { 8269 Slog.w(TAG, "No content provider found for permission revoke: " 8270 + grantUri.toSafeString()); 8271 return; 8272 } 8273 8274 // Does the caller have this permission on the URI? 8275 if (!checkHoldingPermissionsLocked(pm, pi, grantUri, callingUid, modeFlags)) { 8276 // If they don't have direct access to the URI, then revoke any 8277 // ownerless URI permissions that have been granted to them. 8278 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get(callingUid); 8279 if (perms != null) { 8280 boolean persistChanged = false; 8281 for (Iterator<UriPermission> it = perms.values().iterator(); it.hasNext();) { 8282 final UriPermission perm = it.next(); 8283 if (perm.uri.sourceUserId == grantUri.sourceUserId 8284 && perm.uri.uri.isPathPrefixMatch(grantUri.uri)) { 8285 if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION, 8286 "Revoking non-owned " + perm.targetUid 8287 + " permission to " + perm.uri); 8288 persistChanged |= perm.revokeModes( 8289 modeFlags | Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION, false); 8290 if (perm.modeFlags == 0) { 8291 it.remove(); 8292 } 8293 } 8294 } 8295 if (perms.isEmpty()) { 8296 mGrantedUriPermissions.remove(callingUid); 8297 } 8298 if (persistChanged) { 8299 schedulePersistUriGrants(); 8300 } 8301 } 8302 return; 8303 } 8304 8305 boolean persistChanged = false; 8306 8307 // Go through all of the permissions and remove any that match. 8308 int N = mGrantedUriPermissions.size(); 8309 for (int i = 0; i < N; i++) { 8310 final int targetUid = mGrantedUriPermissions.keyAt(i); 8311 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i); 8312 8313 for (Iterator<UriPermission> it = perms.values().iterator(); it.hasNext();) { 8314 final UriPermission perm = it.next(); 8315 if (perm.uri.sourceUserId == grantUri.sourceUserId 8316 && perm.uri.uri.isPathPrefixMatch(grantUri.uri)) { 8317 if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION, 8318 "Revoking " + perm.targetUid + " permission to " + perm.uri); 8319 persistChanged |= perm.revokeModes( 8320 modeFlags | Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION, true); 8321 if (perm.modeFlags == 0) { 8322 it.remove(); 8323 } 8324 } 8325 } 8326 8327 if (perms.isEmpty()) { 8328 mGrantedUriPermissions.remove(targetUid); 8329 N--; 8330 i--; 8331 } 8332 } 8333 8334 if (persistChanged) { 8335 schedulePersistUriGrants(); 8336 } 8337 } 8338 8339 /** 8340 * @param uri This uri must NOT contain an embedded userId. 8341 * @param userId The userId in which the uri is to be resolved. 8342 */ 8343 @Override 8344 public void revokeUriPermission(IApplicationThread caller, Uri uri, final int modeFlags, 8345 int userId) { 8346 enforceNotIsolatedCaller("revokeUriPermission"); 8347 synchronized(this) { 8348 final ProcessRecord r = getRecordForAppLocked(caller); 8349 if (r == null) { 8350 throw new SecurityException("Unable to find app for caller " 8351 + caller 8352 + " when revoking permission to uri " + uri); 8353 } 8354 if (uri == null) { 8355 Slog.w(TAG, "revokeUriPermission: null uri"); 8356 return; 8357 } 8358 8359 if (!Intent.isAccessUriMode(modeFlags)) { 8360 return; 8361 } 8362 8363 final String authority = uri.getAuthority(); 8364 final ProviderInfo pi = getProviderInfoLocked(authority, userId, 8365 MATCH_DIRECT_BOOT_AWARE | MATCH_DIRECT_BOOT_UNAWARE); 8366 if (pi == null) { 8367 Slog.w(TAG, "No content provider found for permission revoke: " 8368 + uri.toSafeString()); 8369 return; 8370 } 8371 8372 revokeUriPermissionLocked(r.uid, new GrantUri(userId, uri, false), modeFlags); 8373 } 8374 } 8375 8376 /** 8377 * Remove any {@link UriPermission} granted <em>from</em> or <em>to</em> the 8378 * given package. 8379 * 8380 * @param packageName Package name to match, or {@code null} to apply to all 8381 * packages. 8382 * @param userHandle User to match, or {@link UserHandle#USER_ALL} to apply 8383 * to all users. 8384 * @param persistable If persistable grants should be removed. 8385 */ 8386 private void removeUriPermissionsForPackageLocked( 8387 String packageName, int userHandle, boolean persistable) { 8388 if (userHandle == UserHandle.USER_ALL && packageName == null) { 8389 throw new IllegalArgumentException("Must narrow by either package or user"); 8390 } 8391 8392 boolean persistChanged = false; 8393 8394 int N = mGrantedUriPermissions.size(); 8395 for (int i = 0; i < N; i++) { 8396 final int targetUid = mGrantedUriPermissions.keyAt(i); 8397 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i); 8398 8399 // Only inspect grants matching user 8400 if (userHandle == UserHandle.USER_ALL 8401 || userHandle == UserHandle.getUserId(targetUid)) { 8402 for (Iterator<UriPermission> it = perms.values().iterator(); it.hasNext();) { 8403 final UriPermission perm = it.next(); 8404 8405 // Only inspect grants matching package 8406 if (packageName == null || perm.sourcePkg.equals(packageName) 8407 || perm.targetPkg.equals(packageName)) { 8408 persistChanged |= perm.revokeModes(persistable 8409 ? ~0 : ~Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION, true); 8410 8411 // Only remove when no modes remain; any persisted grants 8412 // will keep this alive. 8413 if (perm.modeFlags == 0) { 8414 it.remove(); 8415 } 8416 } 8417 } 8418 8419 if (perms.isEmpty()) { 8420 mGrantedUriPermissions.remove(targetUid); 8421 N--; 8422 i--; 8423 } 8424 } 8425 } 8426 8427 if (persistChanged) { 8428 schedulePersistUriGrants(); 8429 } 8430 } 8431 8432 @Override 8433 public IBinder newUriPermissionOwner(String name) { 8434 enforceNotIsolatedCaller("newUriPermissionOwner"); 8435 synchronized(this) { 8436 UriPermissionOwner owner = new UriPermissionOwner(this, name); 8437 return owner.getExternalTokenLocked(); 8438 } 8439 } 8440 8441 @Override 8442 public IBinder getUriPermissionOwnerForActivity(IBinder activityToken) { 8443 enforceNotIsolatedCaller("getUriPermissionOwnerForActivity"); 8444 synchronized(this) { 8445 ActivityRecord r = ActivityRecord.isInStackLocked(activityToken); 8446 if (r == null) { 8447 throw new IllegalArgumentException("Activity does not exist; token=" 8448 + activityToken); 8449 } 8450 return r.getUriPermissionsLocked().getExternalTokenLocked(); 8451 } 8452 } 8453 /** 8454 * @param uri This uri must NOT contain an embedded userId. 8455 * @param sourceUserId The userId in which the uri is to be resolved. 8456 * @param targetUserId The userId of the app that receives the grant. 8457 */ 8458 @Override 8459 public void grantUriPermissionFromOwner(IBinder token, int fromUid, String targetPkg, Uri uri, 8460 final int modeFlags, int sourceUserId, int targetUserId) { 8461 targetUserId = mUserController.handleIncomingUser(Binder.getCallingPid(), 8462 Binder.getCallingUid(), targetUserId, false, ALLOW_FULL_ONLY, 8463 "grantUriPermissionFromOwner", null); 8464 synchronized(this) { 8465 UriPermissionOwner owner = UriPermissionOwner.fromExternalToken(token); 8466 if (owner == null) { 8467 throw new IllegalArgumentException("Unknown owner: " + token); 8468 } 8469 if (fromUid != Binder.getCallingUid()) { 8470 if (Binder.getCallingUid() != Process.myUid()) { 8471 // Only system code can grant URI permissions on behalf 8472 // of other users. 8473 throw new SecurityException("nice try"); 8474 } 8475 } 8476 if (targetPkg == null) { 8477 throw new IllegalArgumentException("null target"); 8478 } 8479 if (uri == null) { 8480 throw new IllegalArgumentException("null uri"); 8481 } 8482 8483 grantUriPermissionLocked(fromUid, targetPkg, new GrantUri(sourceUserId, uri, false), 8484 modeFlags, owner, targetUserId); 8485 } 8486 } 8487 8488 /** 8489 * @param uri This uri must NOT contain an embedded userId. 8490 * @param userId The userId in which the uri is to be resolved. 8491 */ 8492 @Override 8493 public void revokeUriPermissionFromOwner(IBinder token, Uri uri, int mode, int userId) { 8494 synchronized(this) { 8495 UriPermissionOwner owner = UriPermissionOwner.fromExternalToken(token); 8496 if (owner == null) { 8497 throw new IllegalArgumentException("Unknown owner: " + token); 8498 } 8499 8500 if (uri == null) { 8501 owner.removeUriPermissionsLocked(mode); 8502 } else { 8503 final boolean prefix = (mode & Intent.FLAG_GRANT_PREFIX_URI_PERMISSION) != 0; 8504 owner.removeUriPermissionLocked(new GrantUri(userId, uri, prefix), mode); 8505 } 8506 } 8507 } 8508 8509 private void schedulePersistUriGrants() { 8510 if (!mHandler.hasMessages(PERSIST_URI_GRANTS_MSG)) { 8511 mHandler.sendMessageDelayed(mHandler.obtainMessage(PERSIST_URI_GRANTS_MSG), 8512 10 * DateUtils.SECOND_IN_MILLIS); 8513 } 8514 } 8515 8516 private void writeGrantedUriPermissions() { 8517 if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION, "writeGrantedUriPermissions()"); 8518 8519 // Snapshot permissions so we can persist without lock 8520 ArrayList<UriPermission.Snapshot> persist = Lists.newArrayList(); 8521 synchronized (this) { 8522 final int size = mGrantedUriPermissions.size(); 8523 for (int i = 0; i < size; i++) { 8524 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i); 8525 for (UriPermission perm : perms.values()) { 8526 if (perm.persistedModeFlags != 0) { 8527 persist.add(perm.snapshot()); 8528 } 8529 } 8530 } 8531 } 8532 8533 FileOutputStream fos = null; 8534 try { 8535 fos = mGrantFile.startWrite(); 8536 8537 XmlSerializer out = new FastXmlSerializer(); 8538 out.setOutput(fos, StandardCharsets.UTF_8.name()); 8539 out.startDocument(null, true); 8540 out.startTag(null, TAG_URI_GRANTS); 8541 for (UriPermission.Snapshot perm : persist) { 8542 out.startTag(null, TAG_URI_GRANT); 8543 writeIntAttribute(out, ATTR_SOURCE_USER_ID, perm.uri.sourceUserId); 8544 writeIntAttribute(out, ATTR_TARGET_USER_ID, perm.targetUserId); 8545 out.attribute(null, ATTR_SOURCE_PKG, perm.sourcePkg); 8546 out.attribute(null, ATTR_TARGET_PKG, perm.targetPkg); 8547 out.attribute(null, ATTR_URI, String.valueOf(perm.uri.uri)); 8548 writeBooleanAttribute(out, ATTR_PREFIX, perm.uri.prefix); 8549 writeIntAttribute(out, ATTR_MODE_FLAGS, perm.persistedModeFlags); 8550 writeLongAttribute(out, ATTR_CREATED_TIME, perm.persistedCreateTime); 8551 out.endTag(null, TAG_URI_GRANT); 8552 } 8553 out.endTag(null, TAG_URI_GRANTS); 8554 out.endDocument(); 8555 8556 mGrantFile.finishWrite(fos); 8557 } catch (IOException e) { 8558 if (fos != null) { 8559 mGrantFile.failWrite(fos); 8560 } 8561 } 8562 } 8563 8564 private void readGrantedUriPermissionsLocked() { 8565 if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION, "readGrantedUriPermissions()"); 8566 8567 final long now = System.currentTimeMillis(); 8568 8569 FileInputStream fis = null; 8570 try { 8571 fis = mGrantFile.openRead(); 8572 final XmlPullParser in = Xml.newPullParser(); 8573 in.setInput(fis, StandardCharsets.UTF_8.name()); 8574 8575 int type; 8576 while ((type = in.next()) != END_DOCUMENT) { 8577 final String tag = in.getName(); 8578 if (type == START_TAG) { 8579 if (TAG_URI_GRANT.equals(tag)) { 8580 final int sourceUserId; 8581 final int targetUserId; 8582 final int userHandle = readIntAttribute(in, 8583 ATTR_USER_HANDLE, UserHandle.USER_NULL); 8584 if (userHandle != UserHandle.USER_NULL) { 8585 // For backwards compatibility. 8586 sourceUserId = userHandle; 8587 targetUserId = userHandle; 8588 } else { 8589 sourceUserId = readIntAttribute(in, ATTR_SOURCE_USER_ID); 8590 targetUserId = readIntAttribute(in, ATTR_TARGET_USER_ID); 8591 } 8592 final String sourcePkg = in.getAttributeValue(null, ATTR_SOURCE_PKG); 8593 final String targetPkg = in.getAttributeValue(null, ATTR_TARGET_PKG); 8594 final Uri uri = Uri.parse(in.getAttributeValue(null, ATTR_URI)); 8595 final boolean prefix = readBooleanAttribute(in, ATTR_PREFIX); 8596 final int modeFlags = readIntAttribute(in, ATTR_MODE_FLAGS); 8597 final long createdTime = readLongAttribute(in, ATTR_CREATED_TIME, now); 8598 8599 // Sanity check that provider still belongs to source package 8600 // Both direct boot aware and unaware packages are fine as we 8601 // will do filtering at query time to avoid multiple parsing. 8602 final ProviderInfo pi = getProviderInfoLocked( 8603 uri.getAuthority(), sourceUserId, MATCH_DIRECT_BOOT_AWARE 8604 | MATCH_DIRECT_BOOT_UNAWARE); 8605 if (pi != null && sourcePkg.equals(pi.packageName)) { 8606 int targetUid = -1; 8607 try { 8608 targetUid = AppGlobals.getPackageManager().getPackageUid( 8609 targetPkg, MATCH_UNINSTALLED_PACKAGES, targetUserId); 8610 } catch (RemoteException e) { 8611 } 8612 if (targetUid != -1) { 8613 final UriPermission perm = findOrCreateUriPermissionLocked( 8614 sourcePkg, targetPkg, targetUid, 8615 new GrantUri(sourceUserId, uri, prefix)); 8616 perm.initPersistedModes(modeFlags, createdTime); 8617 } 8618 } else { 8619 Slog.w(TAG, "Persisted grant for " + uri + " had source " + sourcePkg 8620 + " but instead found " + pi); 8621 } 8622 } 8623 } 8624 } 8625 } catch (FileNotFoundException e) { 8626 // Missing grants is okay 8627 } catch (IOException e) { 8628 Slog.wtf(TAG, "Failed reading Uri grants", e); 8629 } catch (XmlPullParserException e) { 8630 Slog.wtf(TAG, "Failed reading Uri grants", e); 8631 } finally { 8632 IoUtils.closeQuietly(fis); 8633 } 8634 } 8635 8636 /** 8637 * @param uri This uri must NOT contain an embedded userId. 8638 * @param userId The userId in which the uri is to be resolved. 8639 */ 8640 @Override 8641 public void takePersistableUriPermission(Uri uri, final int modeFlags, int userId) { 8642 enforceNotIsolatedCaller("takePersistableUriPermission"); 8643 8644 Preconditions.checkFlagsArgument(modeFlags, 8645 Intent.FLAG_GRANT_READ_URI_PERMISSION | Intent.FLAG_GRANT_WRITE_URI_PERMISSION); 8646 8647 synchronized (this) { 8648 final int callingUid = Binder.getCallingUid(); 8649 boolean persistChanged = false; 8650 GrantUri grantUri = new GrantUri(userId, uri, false); 8651 8652 UriPermission exactPerm = findUriPermissionLocked(callingUid, 8653 new GrantUri(userId, uri, false)); 8654 UriPermission prefixPerm = findUriPermissionLocked(callingUid, 8655 new GrantUri(userId, uri, true)); 8656 8657 final boolean exactValid = (exactPerm != null) 8658 && ((modeFlags & exactPerm.persistableModeFlags) == modeFlags); 8659 final boolean prefixValid = (prefixPerm != null) 8660 && ((modeFlags & prefixPerm.persistableModeFlags) == modeFlags); 8661 8662 if (!(exactValid || prefixValid)) { 8663 throw new SecurityException("No persistable permission grants found for UID " 8664 + callingUid + " and Uri " + grantUri.toSafeString()); 8665 } 8666 8667 if (exactValid) { 8668 persistChanged |= exactPerm.takePersistableModes(modeFlags); 8669 } 8670 if (prefixValid) { 8671 persistChanged |= prefixPerm.takePersistableModes(modeFlags); 8672 } 8673 8674 persistChanged |= maybePrunePersistedUriGrantsLocked(callingUid); 8675 8676 if (persistChanged) { 8677 schedulePersistUriGrants(); 8678 } 8679 } 8680 } 8681 8682 /** 8683 * @param uri This uri must NOT contain an embedded userId. 8684 * @param userId The userId in which the uri is to be resolved. 8685 */ 8686 @Override 8687 public void releasePersistableUriPermission(Uri uri, final int modeFlags, int userId) { 8688 enforceNotIsolatedCaller("releasePersistableUriPermission"); 8689 8690 Preconditions.checkFlagsArgument(modeFlags, 8691 Intent.FLAG_GRANT_READ_URI_PERMISSION | Intent.FLAG_GRANT_WRITE_URI_PERMISSION); 8692 8693 synchronized (this) { 8694 final int callingUid = Binder.getCallingUid(); 8695 boolean persistChanged = false; 8696 8697 UriPermission exactPerm = findUriPermissionLocked(callingUid, 8698 new GrantUri(userId, uri, false)); 8699 UriPermission prefixPerm = findUriPermissionLocked(callingUid, 8700 new GrantUri(userId, uri, true)); 8701 if (exactPerm == null && prefixPerm == null) { 8702 throw new SecurityException("No permission grants found for UID " + callingUid 8703 + " and Uri " + uri.toSafeString()); 8704 } 8705 8706 if (exactPerm != null) { 8707 persistChanged |= exactPerm.releasePersistableModes(modeFlags); 8708 removeUriPermissionIfNeededLocked(exactPerm); 8709 } 8710 if (prefixPerm != null) { 8711 persistChanged |= prefixPerm.releasePersistableModes(modeFlags); 8712 removeUriPermissionIfNeededLocked(prefixPerm); 8713 } 8714 8715 if (persistChanged) { 8716 schedulePersistUriGrants(); 8717 } 8718 } 8719 } 8720 8721 /** 8722 * Prune any older {@link UriPermission} for the given UID until outstanding 8723 * persisted grants are below {@link #MAX_PERSISTED_URI_GRANTS}. 8724 * 8725 * @return if any mutations occured that require persisting. 8726 */ 8727 private boolean maybePrunePersistedUriGrantsLocked(int uid) { 8728 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get(uid); 8729 if (perms == null) return false; 8730 if (perms.size() < MAX_PERSISTED_URI_GRANTS) return false; 8731 8732 final ArrayList<UriPermission> persisted = Lists.newArrayList(); 8733 for (UriPermission perm : perms.values()) { 8734 if (perm.persistedModeFlags != 0) { 8735 persisted.add(perm); 8736 } 8737 } 8738 8739 final int trimCount = persisted.size() - MAX_PERSISTED_URI_GRANTS; 8740 if (trimCount <= 0) return false; 8741 8742 Collections.sort(persisted, new UriPermission.PersistedTimeComparator()); 8743 for (int i = 0; i < trimCount; i++) { 8744 final UriPermission perm = persisted.get(i); 8745 8746 if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION, 8747 "Trimming grant created at " + perm.persistedCreateTime); 8748 8749 perm.releasePersistableModes(~0); 8750 removeUriPermissionIfNeededLocked(perm); 8751 } 8752 8753 return true; 8754 } 8755 8756 @Override 8757 public ParceledListSlice<android.content.UriPermission> getPersistedUriPermissions( 8758 String packageName, boolean incoming) { 8759 enforceNotIsolatedCaller("getPersistedUriPermissions"); 8760 Preconditions.checkNotNull(packageName, "packageName"); 8761 8762 final int callingUid = Binder.getCallingUid(); 8763 final int callingUserId = UserHandle.getUserId(callingUid); 8764 final IPackageManager pm = AppGlobals.getPackageManager(); 8765 try { 8766 final int packageUid = pm.getPackageUid(packageName, 8767 MATCH_DIRECT_BOOT_AWARE | MATCH_DIRECT_BOOT_UNAWARE, callingUserId); 8768 if (packageUid != callingUid) { 8769 throw new SecurityException( 8770 "Package " + packageName + " does not belong to calling UID " + callingUid); 8771 } 8772 } catch (RemoteException e) { 8773 throw new SecurityException("Failed to verify package name ownership"); 8774 } 8775 8776 final ArrayList<android.content.UriPermission> result = Lists.newArrayList(); 8777 synchronized (this) { 8778 if (incoming) { 8779 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get( 8780 callingUid); 8781 if (perms == null) { 8782 Slog.w(TAG, "No permission grants found for " + packageName); 8783 } else { 8784 for (UriPermission perm : perms.values()) { 8785 if (packageName.equals(perm.targetPkg) && perm.persistedModeFlags != 0) { 8786 result.add(perm.buildPersistedPublicApiObject()); 8787 } 8788 } 8789 } 8790 } else { 8791 final int size = mGrantedUriPermissions.size(); 8792 for (int i = 0; i < size; i++) { 8793 final ArrayMap<GrantUri, UriPermission> perms = 8794 mGrantedUriPermissions.valueAt(i); 8795 for (UriPermission perm : perms.values()) { 8796 if (packageName.equals(perm.sourcePkg) && perm.persistedModeFlags != 0) { 8797 result.add(perm.buildPersistedPublicApiObject()); 8798 } 8799 } 8800 } 8801 } 8802 } 8803 return new ParceledListSlice<android.content.UriPermission>(result); 8804 } 8805 8806 @Override 8807 public ParceledListSlice<android.content.UriPermission> getGrantedUriPermissions( 8808 String packageName, int userId) { 8809 enforceCallingPermission(android.Manifest.permission.GET_APP_GRANTED_URI_PERMISSIONS, 8810 "getGrantedUriPermissions"); 8811 8812 final ArrayList<android.content.UriPermission> result = Lists.newArrayList(); 8813 synchronized (this) { 8814 final int size = mGrantedUriPermissions.size(); 8815 for (int i = 0; i < size; i++) { 8816 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i); 8817 for (UriPermission perm : perms.values()) { 8818 if (packageName.equals(perm.targetPkg) && perm.targetUserId == userId 8819 && perm.persistedModeFlags != 0) { 8820 result.add(perm.buildPersistedPublicApiObject()); 8821 } 8822 } 8823 } 8824 } 8825 return new ParceledListSlice<android.content.UriPermission>(result); 8826 } 8827 8828 @Override 8829 public void clearGrantedUriPermissions(String packageName, int userId) { 8830 enforceCallingPermission(android.Manifest.permission.CLEAR_APP_GRANTED_URI_PERMISSIONS, 8831 "clearGrantedUriPermissions"); 8832 removeUriPermissionsForPackageLocked(packageName, userId, true); 8833 } 8834 8835 @Override 8836 public void showWaitingForDebugger(IApplicationThread who, boolean waiting) { 8837 synchronized (this) { 8838 ProcessRecord app = 8839 who != null ? getRecordForAppLocked(who) : null; 8840 if (app == null) return; 8841 8842 Message msg = Message.obtain(); 8843 msg.what = WAIT_FOR_DEBUGGER_UI_MSG; 8844 msg.obj = app; 8845 msg.arg1 = waiting ? 1 : 0; 8846 mUiHandler.sendMessage(msg); 8847 } 8848 } 8849 8850 @Override 8851 public void getMemoryInfo(ActivityManager.MemoryInfo outInfo) { 8852 final long homeAppMem = mProcessList.getMemLevel(ProcessList.HOME_APP_ADJ); 8853 final long cachedAppMem = mProcessList.getMemLevel(ProcessList.CACHED_APP_MIN_ADJ); 8854 outInfo.availMem = Process.getFreeMemory(); 8855 outInfo.totalMem = Process.getTotalMemory(); 8856 outInfo.threshold = homeAppMem; 8857 outInfo.lowMemory = outInfo.availMem < (homeAppMem + ((cachedAppMem-homeAppMem)/2)); 8858 outInfo.hiddenAppThreshold = cachedAppMem; 8859 outInfo.secondaryServerThreshold = mProcessList.getMemLevel( 8860 ProcessList.SERVICE_ADJ); 8861 outInfo.visibleAppThreshold = mProcessList.getMemLevel( 8862 ProcessList.VISIBLE_APP_ADJ); 8863 outInfo.foregroundAppThreshold = mProcessList.getMemLevel( 8864 ProcessList.FOREGROUND_APP_ADJ); 8865 } 8866 8867 // ========================================================= 8868 // TASK MANAGEMENT 8869 // ========================================================= 8870 8871 @Override 8872 public List<IBinder> getAppTasks(String callingPackage) { 8873 int callingUid = Binder.getCallingUid(); 8874 long ident = Binder.clearCallingIdentity(); 8875 8876 synchronized(this) { 8877 ArrayList<IBinder> list = new ArrayList<IBinder>(); 8878 try { 8879 if (DEBUG_ALL) Slog.v(TAG, "getAppTasks"); 8880 8881 final int N = mRecentTasks.size(); 8882 for (int i = 0; i < N; i++) { 8883 TaskRecord tr = mRecentTasks.get(i); 8884 // Skip tasks that do not match the caller. We don't need to verify 8885 // callingPackage, because we are also limiting to callingUid and know 8886 // that will limit to the correct security sandbox. 8887 if (tr.effectiveUid != callingUid) { 8888 continue; 8889 } 8890 Intent intent = tr.getBaseIntent(); 8891 if (intent == null || 8892 !callingPackage.equals(intent.getComponent().getPackageName())) { 8893 continue; 8894 } 8895 ActivityManager.RecentTaskInfo taskInfo = 8896 createRecentTaskInfoFromTaskRecord(tr); 8897 AppTaskImpl taskImpl = new AppTaskImpl(taskInfo.persistentId, callingUid); 8898 list.add(taskImpl.asBinder()); 8899 } 8900 } finally { 8901 Binder.restoreCallingIdentity(ident); 8902 } 8903 return list; 8904 } 8905 } 8906 8907 @Override 8908 public List<RunningTaskInfo> getTasks(int maxNum, int flags) { 8909 final int callingUid = Binder.getCallingUid(); 8910 ArrayList<RunningTaskInfo> list = new ArrayList<RunningTaskInfo>(); 8911 8912 synchronized(this) { 8913 if (DEBUG_ALL) Slog.v( 8914 TAG, "getTasks: max=" + maxNum + ", flags=" + flags); 8915 8916 final boolean allowed = isGetTasksAllowed("getTasks", Binder.getCallingPid(), 8917 callingUid); 8918 8919 // TODO: Improve with MRU list from all ActivityStacks. 8920 mStackSupervisor.getTasksLocked(maxNum, list, callingUid, allowed); 8921 } 8922 8923 return list; 8924 } 8925 8926 /** 8927 * Creates a new RecentTaskInfo from a TaskRecord. 8928 */ 8929 private ActivityManager.RecentTaskInfo createRecentTaskInfoFromTaskRecord(TaskRecord tr) { 8930 // Update the task description to reflect any changes in the task stack 8931 tr.updateTaskDescription(); 8932 8933 // Compose the recent task info 8934 ActivityManager.RecentTaskInfo rti = new ActivityManager.RecentTaskInfo(); 8935 rti.id = tr.getTopActivity() == null ? INVALID_TASK_ID : tr.taskId; 8936 rti.persistentId = tr.taskId; 8937 rti.baseIntent = new Intent(tr.getBaseIntent()); 8938 rti.origActivity = tr.origActivity; 8939 rti.realActivity = tr.realActivity; 8940 rti.description = tr.lastDescription; 8941 rti.stackId = tr.getStackId(); 8942 rti.userId = tr.userId; 8943 rti.taskDescription = new ActivityManager.TaskDescription(tr.lastTaskDescription); 8944 rti.firstActiveTime = tr.firstActiveTime; 8945 rti.lastActiveTime = tr.lastActiveTime; 8946 rti.affiliatedTaskId = tr.mAffiliatedTaskId; 8947 rti.affiliatedTaskColor = tr.mAffiliatedTaskColor; 8948 rti.numActivities = 0; 8949 if (tr.mBounds != null) { 8950 rti.bounds = new Rect(tr.mBounds); 8951 } 8952 rti.isDockable = tr.canGoInDockedStack(); 8953 rti.resizeMode = tr.mResizeMode; 8954 8955 ActivityRecord base = null; 8956 ActivityRecord top = null; 8957 ActivityRecord tmp; 8958 8959 for (int i = tr.mActivities.size() - 1; i >= 0; --i) { 8960 tmp = tr.mActivities.get(i); 8961 if (tmp.finishing) { 8962 continue; 8963 } 8964 base = tmp; 8965 if (top == null || (top.state == ActivityState.INITIALIZING)) { 8966 top = base; 8967 } 8968 rti.numActivities++; 8969 } 8970 8971 rti.baseActivity = (base != null) ? base.intent.getComponent() : null; 8972 rti.topActivity = (top != null) ? top.intent.getComponent() : null; 8973 8974 return rti; 8975 } 8976 8977 private boolean isGetTasksAllowed(String caller, int callingPid, int callingUid) { 8978 boolean allowed = checkPermission(android.Manifest.permission.REAL_GET_TASKS, 8979 callingPid, callingUid) == PackageManager.PERMISSION_GRANTED; 8980 if (!allowed) { 8981 if (checkPermission(android.Manifest.permission.GET_TASKS, 8982 callingPid, callingUid) == PackageManager.PERMISSION_GRANTED) { 8983 // Temporary compatibility: some existing apps on the system image may 8984 // still be requesting the old permission and not switched to the new 8985 // one; if so, we'll still allow them full access. This means we need 8986 // to see if they are holding the old permission and are a system app. 8987 try { 8988 if (AppGlobals.getPackageManager().isUidPrivileged(callingUid)) { 8989 allowed = true; 8990 if (DEBUG_TASKS) Slog.w(TAG, caller + ": caller " + callingUid 8991 + " is using old GET_TASKS but privileged; allowing"); 8992 } 8993 } catch (RemoteException e) { 8994 } 8995 } 8996 } 8997 if (!allowed) { 8998 if (DEBUG_TASKS) Slog.w(TAG, caller + ": caller " + callingUid 8999 + " does not hold REAL_GET_TASKS; limiting output"); 9000 } 9001 return allowed; 9002 } 9003 9004 @Override 9005 public ParceledListSlice<ActivityManager.RecentTaskInfo> getRecentTasks(int maxNum, int flags, 9006 int userId) { 9007 final int callingUid = Binder.getCallingUid(); 9008 userId = mUserController.handleIncomingUser(Binder.getCallingPid(), callingUid, userId, 9009 false, ALLOW_FULL_ONLY, "getRecentTasks", null); 9010 9011 final boolean includeProfiles = (flags & ActivityManager.RECENT_INCLUDE_PROFILES) != 0; 9012 final boolean withExcluded = (flags&ActivityManager.RECENT_WITH_EXCLUDED) != 0; 9013 synchronized (this) { 9014 final boolean allowed = isGetTasksAllowed("getRecentTasks", Binder.getCallingPid(), 9015 callingUid); 9016 final boolean detailed = checkCallingPermission( 9017 android.Manifest.permission.GET_DETAILED_TASKS) 9018 == PackageManager.PERMISSION_GRANTED; 9019 9020 if (!isUserRunning(userId, ActivityManager.FLAG_AND_UNLOCKED)) { 9021 Slog.i(TAG, "user " + userId + " is still locked. Cannot load recents"); 9022 return ParceledListSlice.emptyList(); 9023 } 9024 mRecentTasks.loadUserRecentsLocked(userId); 9025 9026 final int recentsCount = mRecentTasks.size(); 9027 ArrayList<ActivityManager.RecentTaskInfo> res = 9028 new ArrayList<>(maxNum < recentsCount ? maxNum : recentsCount); 9029 9030 final Set<Integer> includedUsers; 9031 if (includeProfiles) { 9032 includedUsers = mUserController.getProfileIds(userId); 9033 } else { 9034 includedUsers = new HashSet<>(); 9035 } 9036 includedUsers.add(Integer.valueOf(userId)); 9037 9038 for (int i = 0; i < recentsCount && maxNum > 0; i++) { 9039 TaskRecord tr = mRecentTasks.get(i); 9040 // Only add calling user or related users recent tasks 9041 if (!includedUsers.contains(Integer.valueOf(tr.userId))) { 9042 if (DEBUG_RECENTS) Slog.d(TAG_RECENTS, "Skipping, not user: " + tr); 9043 continue; 9044 } 9045 9046 if (tr.realActivitySuspended) { 9047 if (DEBUG_RECENTS) Slog.d(TAG_RECENTS, "Skipping, activity suspended: " + tr); 9048 continue; 9049 } 9050 9051 // Return the entry if desired by the caller. We always return 9052 // the first entry, because callers always expect this to be the 9053 // foreground app. We may filter others if the caller has 9054 // not supplied RECENT_WITH_EXCLUDED and there is some reason 9055 // we should exclude the entry. 9056 9057 if (i == 0 9058 || withExcluded 9059 || (tr.intent == null) 9060 || ((tr.intent.getFlags() & Intent.FLAG_ACTIVITY_EXCLUDE_FROM_RECENTS) 9061 == 0)) { 9062 if (!allowed) { 9063 // If the caller doesn't have the GET_TASKS permission, then only 9064 // allow them to see a small subset of tasks -- their own and home. 9065 if (!tr.isHomeTask() && tr.effectiveUid != callingUid) { 9066 if (DEBUG_RECENTS) Slog.d(TAG_RECENTS, "Skipping, not allowed: " + tr); 9067 continue; 9068 } 9069 } 9070 final ActivityStack stack = tr.getStack(); 9071 if ((flags & ActivityManager.RECENT_IGNORE_HOME_STACK_TASKS) != 0) { 9072 if (stack != null && stack.isHomeStack()) { 9073 if (DEBUG_RECENTS) Slog.d(TAG_RECENTS, 9074 "Skipping, home stack task: " + tr); 9075 continue; 9076 } 9077 } 9078 if ((flags & ActivityManager.RECENT_INGORE_DOCKED_STACK_TOP_TASK) != 0) { 9079 if (stack != null && stack.isDockedStack() && stack.topTask() == tr) { 9080 if (DEBUG_RECENTS) Slog.d(TAG_RECENTS, 9081 "Skipping, top task in docked stack: " + tr); 9082 continue; 9083 } 9084 } 9085 if ((flags & ActivityManager.RECENT_INGORE_PINNED_STACK_TASKS) != 0) { 9086 if (stack != null && stack.isPinnedStack()) { 9087 if (DEBUG_RECENTS) Slog.d(TAG_RECENTS, 9088 "Skipping, pinned stack task: " + tr); 9089 continue; 9090 } 9091 } 9092 if (tr.autoRemoveRecents && tr.getTopActivity() == null) { 9093 // Don't include auto remove tasks that are finished or finishing. 9094 if (DEBUG_RECENTS) Slog.d(TAG_RECENTS, 9095 "Skipping, auto-remove without activity: " + tr); 9096 continue; 9097 } 9098 if ((flags&ActivityManager.RECENT_IGNORE_UNAVAILABLE) != 0 9099 && !tr.isAvailable) { 9100 if (DEBUG_RECENTS) Slog.d(TAG_RECENTS, 9101 "Skipping, unavail real act: " + tr); 9102 continue; 9103 } 9104 9105 if (!tr.mUserSetupComplete) { 9106 // Don't include task launched while user is not done setting-up. 9107 if (DEBUG_RECENTS) Slog.d(TAG_RECENTS, 9108 "Skipping, user setup not complete: " + tr); 9109 continue; 9110 } 9111 9112 ActivityManager.RecentTaskInfo rti = createRecentTaskInfoFromTaskRecord(tr); 9113 if (!detailed) { 9114 rti.baseIntent.replaceExtras((Bundle)null); 9115 } 9116 9117 res.add(rti); 9118 maxNum--; 9119 } 9120 } 9121 return new ParceledListSlice<>(res); 9122 } 9123 } 9124 9125 @Override 9126 public ActivityManager.TaskThumbnail getTaskThumbnail(int id) { 9127 synchronized (this) { 9128 enforceCallingPermission(android.Manifest.permission.READ_FRAME_BUFFER, 9129 "getTaskThumbnail()"); 9130 final TaskRecord tr = mStackSupervisor.anyTaskForIdLocked( 9131 id, !RESTORE_FROM_RECENTS, INVALID_STACK_ID); 9132 if (tr != null) { 9133 return tr.getTaskThumbnailLocked(); 9134 } 9135 } 9136 return null; 9137 } 9138 9139 @Override 9140 public int addAppTask(IBinder activityToken, Intent intent, 9141 ActivityManager.TaskDescription description, Bitmap thumbnail) throws RemoteException { 9142 final int callingUid = Binder.getCallingUid(); 9143 final long callingIdent = Binder.clearCallingIdentity(); 9144 9145 try { 9146 synchronized (this) { 9147 ActivityRecord r = ActivityRecord.isInStackLocked(activityToken); 9148 if (r == null) { 9149 throw new IllegalArgumentException("Activity does not exist; token=" 9150 + activityToken); 9151 } 9152 ComponentName comp = intent.getComponent(); 9153 if (comp == null) { 9154 throw new IllegalArgumentException("Intent " + intent 9155 + " must specify explicit component"); 9156 } 9157 if (thumbnail.getWidth() != mThumbnailWidth 9158 || thumbnail.getHeight() != mThumbnailHeight) { 9159 throw new IllegalArgumentException("Bad thumbnail size: got " 9160 + thumbnail.getWidth() + "x" + thumbnail.getHeight() + ", require " 9161 + mThumbnailWidth + "x" + mThumbnailHeight); 9162 } 9163 if (intent.getSelector() != null) { 9164 intent.setSelector(null); 9165 } 9166 if (intent.getSourceBounds() != null) { 9167 intent.setSourceBounds(null); 9168 } 9169 if ((intent.getFlags()&Intent.FLAG_ACTIVITY_NEW_DOCUMENT) != 0) { 9170 if ((intent.getFlags()&Intent.FLAG_ACTIVITY_RETAIN_IN_RECENTS) == 0) { 9171 // The caller has added this as an auto-remove task... that makes no 9172 // sense, so turn off auto-remove. 9173 intent.addFlags(Intent.FLAG_ACTIVITY_RETAIN_IN_RECENTS); 9174 } 9175 } 9176 if (!comp.equals(mLastAddedTaskComponent) || callingUid != mLastAddedTaskUid) { 9177 mLastAddedTaskActivity = null; 9178 } 9179 ActivityInfo ainfo = mLastAddedTaskActivity; 9180 if (ainfo == null) { 9181 ainfo = mLastAddedTaskActivity = AppGlobals.getPackageManager().getActivityInfo( 9182 comp, 0, UserHandle.getUserId(callingUid)); 9183 if (ainfo.applicationInfo.uid != callingUid) { 9184 throw new SecurityException( 9185 "Can't add task for another application: target uid=" 9186 + ainfo.applicationInfo.uid + ", calling uid=" + callingUid); 9187 } 9188 } 9189 9190 TaskRecord task = new TaskRecord(this, 9191 mStackSupervisor.getNextTaskIdForUserLocked(r.userId), 9192 ainfo, intent, description, new TaskThumbnailInfo()); 9193 9194 int trimIdx = mRecentTasks.trimForTaskLocked(task, false); 9195 if (trimIdx >= 0) { 9196 // If this would have caused a trim, then we'll abort because that 9197 // means it would be added at the end of the list but then just removed. 9198 return INVALID_TASK_ID; 9199 } 9200 9201 final int N = mRecentTasks.size(); 9202 if (N >= (ActivityManager.getMaxRecentTasksStatic()-1)) { 9203 final TaskRecord tr = mRecentTasks.remove(N - 1); 9204 tr.removedFromRecents(); 9205 } 9206 9207 task.inRecents = true; 9208 mRecentTasks.add(task); 9209 r.getStack().addTask(task, false, "addAppTask"); 9210 9211 task.setLastThumbnailLocked(thumbnail); 9212 task.freeLastThumbnail(); 9213 return task.taskId; 9214 } 9215 } finally { 9216 Binder.restoreCallingIdentity(callingIdent); 9217 } 9218 } 9219 9220 @Override 9221 public Point getAppTaskThumbnailSize() { 9222 synchronized (this) { 9223 return new Point(mThumbnailWidth, mThumbnailHeight); 9224 } 9225 } 9226 9227 @Override 9228 public void setTaskDescription(IBinder token, ActivityManager.TaskDescription td) { 9229 synchronized (this) { 9230 ActivityRecord r = ActivityRecord.isInStackLocked(token); 9231 if (r != null) { 9232 r.setTaskDescription(td); 9233 r.task.updateTaskDescription(); 9234 mTaskChangeNotificationController.notifyTaskDescriptionChanged(r.task.taskId, td); 9235 } 9236 } 9237 } 9238 9239 @Override 9240 public void setTaskResizeable(int taskId, int resizeableMode) { 9241 synchronized (this) { 9242 final TaskRecord task = mStackSupervisor.anyTaskForIdLocked( 9243 taskId, !RESTORE_FROM_RECENTS, INVALID_STACK_ID); 9244 if (task == null) { 9245 Slog.w(TAG, "setTaskResizeable: taskId=" + taskId + " not found"); 9246 return; 9247 } 9248 if (task.mResizeMode != resizeableMode) { 9249 task.mResizeMode = resizeableMode; 9250 mWindowManager.setTaskResizeable(taskId, resizeableMode); 9251 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0, !PRESERVE_WINDOWS); 9252 mStackSupervisor.resumeFocusedStackTopActivityLocked(); 9253 } 9254 } 9255 } 9256 9257 @Override 9258 public void resizeTask(int taskId, Rect bounds, int resizeMode) { 9259 enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "resizeTask()"); 9260 long ident = Binder.clearCallingIdentity(); 9261 try { 9262 synchronized (this) { 9263 TaskRecord task = mStackSupervisor.anyTaskForIdLocked(taskId); 9264 if (task == null) { 9265 Slog.w(TAG, "resizeTask: taskId=" + taskId + " not found"); 9266 return; 9267 } 9268 // Place the task in the right stack if it isn't there already based on 9269 // the requested bounds. 9270 // The stack transition logic is: 9271 // - a null bounds on a freeform task moves that task to fullscreen 9272 // - a non-null bounds on a non-freeform (fullscreen OR docked) task moves 9273 // that task to freeform 9274 // - otherwise the task is not moved 9275 int stackId = task.getStackId(); 9276 if (!StackId.isTaskResizeAllowed(stackId)) { 9277 throw new IllegalArgumentException("resizeTask not allowed on task=" + task); 9278 } 9279 if (bounds == null && stackId == FREEFORM_WORKSPACE_STACK_ID) { 9280 stackId = FULLSCREEN_WORKSPACE_STACK_ID; 9281 } else if (bounds != null && stackId != FREEFORM_WORKSPACE_STACK_ID ) { 9282 stackId = FREEFORM_WORKSPACE_STACK_ID; 9283 } 9284 boolean preserveWindow = (resizeMode & RESIZE_MODE_PRESERVE_WINDOW) != 0; 9285 if (stackId != task.getStackId()) { 9286 mStackSupervisor.moveTaskToStackUncheckedLocked( 9287 task, stackId, ON_TOP, !FORCE_FOCUS, "resizeTask"); 9288 preserveWindow = false; 9289 } 9290 9291 mStackSupervisor.resizeTaskLocked(task, bounds, resizeMode, preserveWindow, 9292 false /* deferResume */); 9293 } 9294 } finally { 9295 Binder.restoreCallingIdentity(ident); 9296 } 9297 } 9298 9299 @Override 9300 public Rect getTaskBounds(int taskId) { 9301 enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "getTaskBounds()"); 9302 long ident = Binder.clearCallingIdentity(); 9303 Rect rect = new Rect(); 9304 try { 9305 synchronized (this) { 9306 final TaskRecord task = mStackSupervisor.anyTaskForIdLocked( 9307 taskId, !RESTORE_FROM_RECENTS, INVALID_STACK_ID); 9308 if (task == null) { 9309 Slog.w(TAG, "getTaskBounds: taskId=" + taskId + " not found"); 9310 return rect; 9311 } 9312 if (task.getStack() != null) { 9313 // Return the bounds from window manager since it will be adjusted for various 9314 // things like the presense of a docked stack for tasks that aren't resizeable. 9315 mWindowManager.getTaskBounds(task.taskId, rect); 9316 } else { 9317 // Task isn't in window manager yet since it isn't associated with a stack. 9318 // Return the persist value from activity manager 9319 if (task.mBounds != null) { 9320 rect.set(task.mBounds); 9321 } else if (task.mLastNonFullscreenBounds != null) { 9322 rect.set(task.mLastNonFullscreenBounds); 9323 } 9324 } 9325 } 9326 } finally { 9327 Binder.restoreCallingIdentity(ident); 9328 } 9329 return rect; 9330 } 9331 9332 @Override 9333 public Bitmap getTaskDescriptionIcon(String filePath, int userId) { 9334 if (userId != UserHandle.getCallingUserId()) { 9335 enforceCallingPermission(android.Manifest.permission.INTERACT_ACROSS_USERS_FULL, 9336 "getTaskDescriptionIcon"); 9337 } 9338 final File passedIconFile = new File(filePath); 9339 final File legitIconFile = new File(TaskPersister.getUserImagesDir(userId), 9340 passedIconFile.getName()); 9341 if (!legitIconFile.getPath().equals(filePath) 9342 || !filePath.contains(ActivityRecord.ACTIVITY_ICON_SUFFIX)) { 9343 throw new IllegalArgumentException("Bad file path: " + filePath 9344 + " passed for userId " + userId); 9345 } 9346 return mRecentTasks.getTaskDescriptionIcon(filePath); 9347 } 9348 9349 @Override 9350 public void startInPlaceAnimationOnFrontMostApplication(Bundle opts) 9351 throws RemoteException { 9352 final ActivityOptions activityOptions = ActivityOptions.fromBundle(opts); 9353 if (activityOptions.getAnimationType() != ActivityOptions.ANIM_CUSTOM_IN_PLACE || 9354 activityOptions.getCustomInPlaceResId() == 0) { 9355 throw new IllegalArgumentException("Expected in-place ActivityOption " + 9356 "with valid animation"); 9357 } 9358 mWindowManager.prepareAppTransition(TRANSIT_TASK_IN_PLACE, false); 9359 mWindowManager.overridePendingAppTransitionInPlace(activityOptions.getPackageName(), 9360 activityOptions.getCustomInPlaceResId()); 9361 mWindowManager.executeAppTransition(); 9362 } 9363 9364 private void cleanUpRemovedTaskLocked(TaskRecord tr, boolean killProcess, 9365 boolean removeFromRecents) { 9366 if (removeFromRecents) { 9367 mRecentTasks.remove(tr); 9368 tr.removedFromRecents(); 9369 } 9370 ComponentName component = tr.getBaseIntent().getComponent(); 9371 if (component == null) { 9372 Slog.w(TAG, "No component for base intent of task: " + tr); 9373 return; 9374 } 9375 9376 // Find any running services associated with this app and stop if needed. 9377 mServices.cleanUpRemovedTaskLocked(tr, component, new Intent(tr.getBaseIntent())); 9378 9379 if (!killProcess) { 9380 return; 9381 } 9382 9383 // Determine if the process(es) for this task should be killed. 9384 final String pkg = component.getPackageName(); 9385 ArrayList<ProcessRecord> procsToKill = new ArrayList<>(); 9386 ArrayMap<String, SparseArray<ProcessRecord>> pmap = mProcessNames.getMap(); 9387 for (int i = 0; i < pmap.size(); i++) { 9388 9389 SparseArray<ProcessRecord> uids = pmap.valueAt(i); 9390 for (int j = 0; j < uids.size(); j++) { 9391 ProcessRecord proc = uids.valueAt(j); 9392 if (proc.userId != tr.userId) { 9393 // Don't kill process for a different user. 9394 continue; 9395 } 9396 if (proc == mHomeProcess) { 9397 // Don't kill the home process along with tasks from the same package. 9398 continue; 9399 } 9400 if (!proc.pkgList.containsKey(pkg)) { 9401 // Don't kill process that is not associated with this task. 9402 continue; 9403 } 9404 9405 for (int k = 0; k < proc.activities.size(); k++) { 9406 TaskRecord otherTask = proc.activities.get(k).task; 9407 if (tr.taskId != otherTask.taskId && otherTask.inRecents) { 9408 // Don't kill process(es) that has an activity in a different task that is 9409 // also in recents. 9410 return; 9411 } 9412 } 9413 9414 if (proc.foregroundServices) { 9415 // Don't kill process(es) with foreground service. 9416 return; 9417 } 9418 9419 // Add process to kill list. 9420 procsToKill.add(proc); 9421 } 9422 } 9423 9424 // Kill the running processes. 9425 for (int i = 0; i < procsToKill.size(); i++) { 9426 ProcessRecord pr = procsToKill.get(i); 9427 if (pr.setSchedGroup == ProcessList.SCHED_GROUP_BACKGROUND 9428 && pr.curReceivers.isEmpty()) { 9429 pr.kill("remove task", true); 9430 } else { 9431 // We delay killing processes that are not in the background or running a receiver. 9432 pr.waitingToKill = "remove task"; 9433 } 9434 } 9435 } 9436 9437 private void removeTasksByPackageNameLocked(String packageName, int userId) { 9438 // Remove all tasks with activities in the specified package from the list of recent tasks 9439 for (int i = mRecentTasks.size() - 1; i >= 0; i--) { 9440 TaskRecord tr = mRecentTasks.get(i); 9441 if (tr.userId != userId) continue; 9442 9443 ComponentName cn = tr.intent.getComponent(); 9444 if (cn != null && cn.getPackageName().equals(packageName)) { 9445 // If the package name matches, remove the task. 9446 removeTaskByIdLocked(tr.taskId, true, REMOVE_FROM_RECENTS); 9447 } 9448 } 9449 } 9450 9451 private void cleanupDisabledPackageTasksLocked(String packageName, Set<String> filterByClasses, 9452 int userId) { 9453 9454 for (int i = mRecentTasks.size() - 1; i >= 0; i--) { 9455 TaskRecord tr = mRecentTasks.get(i); 9456 if (userId != UserHandle.USER_ALL && tr.userId != userId) { 9457 continue; 9458 } 9459 9460 ComponentName cn = tr.intent.getComponent(); 9461 final boolean sameComponent = cn != null && cn.getPackageName().equals(packageName) 9462 && (filterByClasses == null || filterByClasses.contains(cn.getClassName())); 9463 if (sameComponent) { 9464 removeTaskByIdLocked(tr.taskId, false, REMOVE_FROM_RECENTS); 9465 } 9466 } 9467 } 9468 9469 /** 9470 * Removes the task with the specified task id. 9471 * 9472 * @param taskId Identifier of the task to be removed. 9473 * @param killProcess Kill any process associated with the task if possible. 9474 * @param removeFromRecents Whether to also remove the task from recents. 9475 * @return Returns true if the given task was found and removed. 9476 */ 9477 private boolean removeTaskByIdLocked(int taskId, boolean killProcess, 9478 boolean removeFromRecents) { 9479 final TaskRecord tr = mStackSupervisor.anyTaskForIdLocked( 9480 taskId, !RESTORE_FROM_RECENTS, INVALID_STACK_ID); 9481 if (tr != null) { 9482 tr.removeTaskActivitiesLocked(); 9483 cleanUpRemovedTaskLocked(tr, killProcess, removeFromRecents); 9484 if (tr.isPersistable) { 9485 notifyTaskPersisterLocked(null, true); 9486 } 9487 return true; 9488 } 9489 Slog.w(TAG, "Request to remove task ignored for non-existent task " + taskId); 9490 return false; 9491 } 9492 9493 @Override 9494 public void removeStack(int stackId) { 9495 enforceCallingPermission(Manifest.permission.MANAGE_ACTIVITY_STACKS, "removeStack()"); 9496 if (stackId == HOME_STACK_ID) { 9497 throw new IllegalArgumentException("Removing home stack is not allowed."); 9498 } 9499 9500 synchronized (this) { 9501 final long ident = Binder.clearCallingIdentity(); 9502 try { 9503 final ActivityStack stack = mStackSupervisor.getStack(stackId); 9504 if (stack == null) { 9505 return; 9506 } 9507 final ArrayList<TaskRecord> tasks = stack.getAllTasks(); 9508 for (int i = tasks.size() - 1; i >= 0; i--) { 9509 removeTaskByIdLocked( 9510 tasks.get(i).taskId, true /* killProcess */, REMOVE_FROM_RECENTS); 9511 } 9512 } finally { 9513 Binder.restoreCallingIdentity(ident); 9514 } 9515 } 9516 } 9517 9518 @Override 9519 public void moveStackToDisplay(int stackId, int displayId) { 9520 enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "moveStackToDisplay()"); 9521 9522 synchronized (this) { 9523 final long ident = Binder.clearCallingIdentity(); 9524 try { 9525 if (DEBUG_STACK) Slog.d(TAG_STACK, "moveStackToDisplay: moving stackId=" + stackId 9526 + " to displayId=" + displayId); 9527 mStackSupervisor.moveStackToDisplayLocked(stackId, displayId); 9528 } finally { 9529 Binder.restoreCallingIdentity(ident); 9530 } 9531 } 9532 } 9533 9534 @Override 9535 public boolean removeTask(int taskId) { 9536 enforceCallingPermission(android.Manifest.permission.REMOVE_TASKS, "removeTask()"); 9537 synchronized (this) { 9538 final long ident = Binder.clearCallingIdentity(); 9539 try { 9540 return removeTaskByIdLocked(taskId, true, REMOVE_FROM_RECENTS); 9541 } finally { 9542 Binder.restoreCallingIdentity(ident); 9543 } 9544 } 9545 } 9546 9547 /** 9548 * TODO: Add mController hook 9549 */ 9550 @Override 9551 public void moveTaskToFront(int taskId, int flags, Bundle bOptions) { 9552 enforceCallingPermission(android.Manifest.permission.REORDER_TASKS, "moveTaskToFront()"); 9553 9554 if (DEBUG_STACK) Slog.d(TAG_STACK, "moveTaskToFront: moving taskId=" + taskId); 9555 synchronized(this) { 9556 moveTaskToFrontLocked(taskId, flags, bOptions); 9557 } 9558 } 9559 9560 void moveTaskToFrontLocked(int taskId, int flags, Bundle bOptions) { 9561 ActivityOptions options = ActivityOptions.fromBundle(bOptions); 9562 9563 if (!checkAppSwitchAllowedLocked(Binder.getCallingPid(), 9564 Binder.getCallingUid(), -1, -1, "Task to front")) { 9565 ActivityOptions.abort(options); 9566 return; 9567 } 9568 final long origId = Binder.clearCallingIdentity(); 9569 try { 9570 final TaskRecord task = mStackSupervisor.anyTaskForIdLocked(taskId); 9571 if (task == null) { 9572 Slog.d(TAG, "Could not find task for id: "+ taskId); 9573 return; 9574 } 9575 if (mStackSupervisor.isLockTaskModeViolation(task)) { 9576 mStackSupervisor.showLockTaskToast(); 9577 Slog.e(TAG, "moveTaskToFront: Attempt to violate Lock Task Mode"); 9578 return; 9579 } 9580 final ActivityRecord prev = mStackSupervisor.topRunningActivityLocked(); 9581 if (prev != null && prev.isRecentsActivity()) { 9582 task.setTaskToReturnTo(ActivityRecord.RECENTS_ACTIVITY_TYPE); 9583 } 9584 mStackSupervisor.findTaskToMoveToFrontLocked(task, flags, options, "moveTaskToFront", 9585 false /* forceNonResizable */); 9586 } finally { 9587 Binder.restoreCallingIdentity(origId); 9588 } 9589 ActivityOptions.abort(options); 9590 } 9591 9592 /** 9593 * Moves an activity, and all of the other activities within the same task, to the bottom 9594 * of the history stack. The activity's order within the task is unchanged. 9595 * 9596 * @param token A reference to the activity we wish to move 9597 * @param nonRoot If false then this only works if the activity is the root 9598 * of a task; if true it will work for any activity in a task. 9599 * @return Returns true if the move completed, false if not. 9600 */ 9601 @Override 9602 public boolean moveActivityTaskToBack(IBinder token, boolean nonRoot) { 9603 enforceNotIsolatedCaller("moveActivityTaskToBack"); 9604 synchronized(this) { 9605 final long origId = Binder.clearCallingIdentity(); 9606 try { 9607 int taskId = ActivityRecord.getTaskForActivityLocked(token, !nonRoot); 9608 final TaskRecord task = mStackSupervisor.anyTaskForIdLocked(taskId); 9609 if (task != null) { 9610 if (mStackSupervisor.isLockedTask(task)) { 9611 mStackSupervisor.showLockTaskToast(); 9612 return false; 9613 } 9614 return ActivityRecord.getStackLocked(token).moveTaskToBackLocked(taskId); 9615 } 9616 } finally { 9617 Binder.restoreCallingIdentity(origId); 9618 } 9619 } 9620 return false; 9621 } 9622 9623 @Override 9624 public void moveTaskBackwards(int task) { 9625 enforceCallingPermission(android.Manifest.permission.REORDER_TASKS, 9626 "moveTaskBackwards()"); 9627 9628 synchronized(this) { 9629 if (!checkAppSwitchAllowedLocked(Binder.getCallingPid(), 9630 Binder.getCallingUid(), -1, -1, "Task backwards")) { 9631 return; 9632 } 9633 final long origId = Binder.clearCallingIdentity(); 9634 moveTaskBackwardsLocked(task); 9635 Binder.restoreCallingIdentity(origId); 9636 } 9637 } 9638 9639 private final void moveTaskBackwardsLocked(int task) { 9640 Slog.e(TAG, "moveTaskBackwards not yet implemented!"); 9641 } 9642 9643 @Override 9644 public IActivityContainer createVirtualActivityContainer(IBinder parentActivityToken, 9645 IActivityContainerCallback callback) throws RemoteException { 9646 enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "createActivityContainer()"); 9647 synchronized (this) { 9648 if (parentActivityToken == null) { 9649 throw new IllegalArgumentException("parent token must not be null"); 9650 } 9651 ActivityRecord r = ActivityRecord.forTokenLocked(parentActivityToken); 9652 if (r == null) { 9653 return null; 9654 } 9655 if (callback == null) { 9656 throw new IllegalArgumentException("callback must not be null"); 9657 } 9658 return mStackSupervisor.createVirtualActivityContainer(r, callback); 9659 } 9660 } 9661 9662 @Override 9663 public IActivityContainer createStackOnDisplay(int displayId) throws RemoteException { 9664 enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "createStackOnDisplay()"); 9665 synchronized (this) { 9666 final int stackId = mStackSupervisor.getNextStackId(); 9667 final ActivityStack stack = 9668 mStackSupervisor.createStackOnDisplay(stackId, displayId, true /*onTop*/); 9669 if (stack == null) { 9670 return null; 9671 } 9672 return stack.mActivityContainer; 9673 } 9674 } 9675 9676 @Override 9677 public int getActivityDisplayId(IBinder activityToken) throws RemoteException { 9678 synchronized (this) { 9679 ActivityStack stack = ActivityRecord.getStackLocked(activityToken); 9680 if (stack != null && stack.mActivityContainer.isAttachedLocked()) { 9681 return stack.mActivityContainer.getDisplayId(); 9682 } 9683 return DEFAULT_DISPLAY; 9684 } 9685 } 9686 9687 @Override 9688 public int getActivityStackId(IBinder token) throws RemoteException { 9689 synchronized (this) { 9690 ActivityStack stack = ActivityRecord.getStackLocked(token); 9691 if (stack == null) { 9692 return INVALID_STACK_ID; 9693 } 9694 return stack.mStackId; 9695 } 9696 } 9697 9698 @Override 9699 public void exitFreeformMode(IBinder token) throws RemoteException { 9700 synchronized (this) { 9701 long ident = Binder.clearCallingIdentity(); 9702 try { 9703 final ActivityRecord r = ActivityRecord.forTokenLocked(token); 9704 if (r == null) { 9705 throw new IllegalArgumentException( 9706 "exitFreeformMode: No activity record matching token=" + token); 9707 } 9708 final ActivityStack stack = r.getStackLocked(token); 9709 if (stack == null || stack.mStackId != FREEFORM_WORKSPACE_STACK_ID) { 9710 throw new IllegalStateException( 9711 "exitFreeformMode: You can only go fullscreen from freeform."); 9712 } 9713 if (DEBUG_STACK) Slog.d(TAG_STACK, "exitFreeformMode: " + r); 9714 mStackSupervisor.moveTaskToStackLocked(r.task.taskId, FULLSCREEN_WORKSPACE_STACK_ID, 9715 ON_TOP, !FORCE_FOCUS, "exitFreeformMode", ANIMATE); 9716 } finally { 9717 Binder.restoreCallingIdentity(ident); 9718 } 9719 } 9720 } 9721 9722 @Override 9723 public void moveTaskToStack(int taskId, int stackId, boolean toTop) { 9724 enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "moveTaskToStack()"); 9725 if (stackId == HOME_STACK_ID) { 9726 throw new IllegalArgumentException( 9727 "moveTaskToStack: Attempt to move task " + taskId + " to home stack"); 9728 } 9729 synchronized (this) { 9730 long ident = Binder.clearCallingIdentity(); 9731 try { 9732 if (DEBUG_STACK) Slog.d(TAG_STACK, "moveTaskToStack: moving task=" + taskId 9733 + " to stackId=" + stackId + " toTop=" + toTop); 9734 if (stackId == DOCKED_STACK_ID) { 9735 mWindowManager.setDockedStackCreateState(DOCKED_STACK_CREATE_MODE_TOP_OR_LEFT, 9736 null /* initialBounds */); 9737 } 9738 boolean result = mStackSupervisor.moveTaskToStackLocked(taskId, stackId, toTop, 9739 !FORCE_FOCUS, "moveTaskToStack", ANIMATE); 9740 if (result && stackId == DOCKED_STACK_ID) { 9741 // If task moved to docked stack - show recents if needed. 9742 mStackSupervisor.moveHomeStackTaskToTop(RECENTS_ACTIVITY_TYPE, 9743 "moveTaskToDockedStack"); 9744 } 9745 } finally { 9746 Binder.restoreCallingIdentity(ident); 9747 } 9748 } 9749 } 9750 9751 @Override 9752 public void swapDockedAndFullscreenStack() throws RemoteException { 9753 enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "swapDockedAndFullscreenStack()"); 9754 synchronized (this) { 9755 long ident = Binder.clearCallingIdentity(); 9756 try { 9757 final ActivityStack fullscreenStack = mStackSupervisor.getStack( 9758 FULLSCREEN_WORKSPACE_STACK_ID); 9759 final TaskRecord topTask = fullscreenStack != null ? fullscreenStack.topTask() 9760 : null; 9761 final ActivityStack dockedStack = mStackSupervisor.getStack(DOCKED_STACK_ID); 9762 final ArrayList<TaskRecord> tasks = dockedStack != null ? dockedStack.getAllTasks() 9763 : null; 9764 if (topTask == null || tasks == null || tasks.size() == 0) { 9765 Slog.w(TAG, 9766 "Unable to swap tasks, either docked or fullscreen stack is empty."); 9767 return; 9768 } 9769 9770 // TODO: App transition 9771 mWindowManager.prepareAppTransition(TRANSIT_ACTIVITY_RELAUNCH, false); 9772 9773 // Defer the resume so resume/pausing while moving stacks is dangerous. 9774 mStackSupervisor.moveTaskToStackLocked(topTask.taskId, DOCKED_STACK_ID, 9775 false /* toTop */, !FORCE_FOCUS, "swapDockedAndFullscreenStack", 9776 ANIMATE, true /* deferResume */); 9777 final int size = tasks.size(); 9778 for (int i = 0; i < size; i++) { 9779 final int id = tasks.get(i).taskId; 9780 if (id == topTask.taskId) { 9781 continue; 9782 } 9783 mStackSupervisor.moveTaskToStackLocked(id, 9784 FULLSCREEN_WORKSPACE_STACK_ID, true /* toTop */, !FORCE_FOCUS, 9785 "swapDockedAndFullscreenStack", ANIMATE, true /* deferResume */); 9786 } 9787 9788 // Because we deferred the resume, to avoid conflicts with stack switches while 9789 // resuming, we need to do it after all the tasks are moved. 9790 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0, !PRESERVE_WINDOWS); 9791 mStackSupervisor.resumeFocusedStackTopActivityLocked(); 9792 9793 mWindowManager.executeAppTransition(); 9794 } finally { 9795 Binder.restoreCallingIdentity(ident); 9796 } 9797 } 9798 } 9799 9800 /** 9801 * Moves the input task to the docked stack. 9802 * 9803 * @param taskId Id of task to move. 9804 * @param createMode The mode the docked stack should be created in if it doesn't exist 9805 * already. See 9806 * {@link android.app.ActivityManager#DOCKED_STACK_CREATE_MODE_TOP_OR_LEFT} 9807 * and 9808 * {@link android.app.ActivityManager#DOCKED_STACK_CREATE_MODE_BOTTOM_OR_RIGHT} 9809 * @param toTop If the task and stack should be moved to the top. 9810 * @param animate Whether we should play an animation for the moving the task 9811 * @param initialBounds If the docked stack gets created, it will use these bounds for the 9812 * docked stack. Pass {@code null} to use default bounds. 9813 */ 9814 @Override 9815 public boolean moveTaskToDockedStack(int taskId, int createMode, boolean toTop, boolean animate, 9816 Rect initialBounds, boolean moveHomeStackFront) { 9817 enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "moveTaskToDockedStack()"); 9818 synchronized (this) { 9819 long ident = Binder.clearCallingIdentity(); 9820 try { 9821 if (DEBUG_STACK) Slog.d(TAG_STACK, "moveTaskToDockedStack: moving task=" + taskId 9822 + " to createMode=" + createMode + " toTop=" + toTop); 9823 mWindowManager.setDockedStackCreateState(createMode, initialBounds); 9824 final boolean moved = mStackSupervisor.moveTaskToStackLocked( 9825 taskId, DOCKED_STACK_ID, toTop, !FORCE_FOCUS, "moveTaskToDockedStack", 9826 animate, DEFER_RESUME); 9827 if (moved) { 9828 if (moveHomeStackFront) { 9829 mStackSupervisor.moveHomeStackToFront("moveTaskToDockedStack"); 9830 } 9831 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0, !PRESERVE_WINDOWS); 9832 } 9833 return moved; 9834 } finally { 9835 Binder.restoreCallingIdentity(ident); 9836 } 9837 } 9838 } 9839 9840 /** 9841 * Moves the top activity in the input stackId to the pinned stack. 9842 * 9843 * @param stackId Id of stack to move the top activity to pinned stack. 9844 * @param bounds Bounds to use for pinned stack. 9845 * 9846 * @return True if the top activity of the input stack was successfully moved to the pinned 9847 * stack. 9848 */ 9849 @Override 9850 public boolean moveTopActivityToPinnedStack(int stackId, Rect bounds) { 9851 enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "moveTopActivityToPinnedStack()"); 9852 synchronized (this) { 9853 if (!mSupportsPictureInPicture) { 9854 throw new IllegalStateException("moveTopActivityToPinnedStack:" 9855 + "Device doesn't support picture-in-pciture mode"); 9856 } 9857 9858 long ident = Binder.clearCallingIdentity(); 9859 try { 9860 return mStackSupervisor.moveTopStackActivityToPinnedStackLocked(stackId, bounds); 9861 } finally { 9862 Binder.restoreCallingIdentity(ident); 9863 } 9864 } 9865 } 9866 9867 @Override 9868 public void resizeStack(int stackId, Rect bounds, boolean allowResizeInDockedMode, 9869 boolean preserveWindows, boolean animate, int animationDuration) { 9870 enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "resizeStack()"); 9871 long ident = Binder.clearCallingIdentity(); 9872 try { 9873 synchronized (this) { 9874 if (animate) { 9875 if (stackId == PINNED_STACK_ID) { 9876 mWindowManager.animateResizePinnedStack(bounds, animationDuration); 9877 } else { 9878 throw new IllegalArgumentException("Stack: " + stackId 9879 + " doesn't support animated resize."); 9880 } 9881 } else { 9882 mStackSupervisor.resizeStackLocked(stackId, bounds, null /* tempTaskBounds */, 9883 null /* tempTaskInsetBounds */, preserveWindows, 9884 allowResizeInDockedMode, !DEFER_RESUME); 9885 } 9886 } 9887 } finally { 9888 Binder.restoreCallingIdentity(ident); 9889 } 9890 } 9891 9892 @Override 9893 public void resizeDockedStack(Rect dockedBounds, Rect tempDockedTaskBounds, 9894 Rect tempDockedTaskInsetBounds, 9895 Rect tempOtherTaskBounds, Rect tempOtherTaskInsetBounds) { 9896 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 9897 "resizeDockedStack()"); 9898 long ident = Binder.clearCallingIdentity(); 9899 try { 9900 synchronized (this) { 9901 mStackSupervisor.resizeDockedStackLocked(dockedBounds, tempDockedTaskBounds, 9902 tempDockedTaskInsetBounds, tempOtherTaskBounds, tempOtherTaskInsetBounds, 9903 PRESERVE_WINDOWS); 9904 } 9905 } finally { 9906 Binder.restoreCallingIdentity(ident); 9907 } 9908 } 9909 9910 @Override 9911 public void resizePinnedStack(Rect pinnedBounds, Rect tempPinnedTaskBounds) { 9912 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 9913 "resizePinnedStack()"); 9914 final long ident = Binder.clearCallingIdentity(); 9915 try { 9916 synchronized (this) { 9917 mStackSupervisor.resizePinnedStackLocked(pinnedBounds, tempPinnedTaskBounds); 9918 } 9919 } finally { 9920 Binder.restoreCallingIdentity(ident); 9921 } 9922 } 9923 9924 @Override 9925 public void positionTaskInStack(int taskId, int stackId, int position) { 9926 enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "positionTaskInStack()"); 9927 if (stackId == HOME_STACK_ID) { 9928 throw new IllegalArgumentException( 9929 "positionTaskInStack: Attempt to change the position of task " 9930 + taskId + " in/to home stack"); 9931 } 9932 synchronized (this) { 9933 long ident = Binder.clearCallingIdentity(); 9934 try { 9935 if (DEBUG_STACK) Slog.d(TAG_STACK, 9936 "positionTaskInStack: positioning task=" + taskId 9937 + " in stackId=" + stackId + " at position=" + position); 9938 mStackSupervisor.positionTaskInStackLocked(taskId, stackId, position); 9939 } finally { 9940 Binder.restoreCallingIdentity(ident); 9941 } 9942 } 9943 } 9944 9945 @Override 9946 public List<StackInfo> getAllStackInfos() { 9947 enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "getAllStackInfos()"); 9948 long ident = Binder.clearCallingIdentity(); 9949 try { 9950 synchronized (this) { 9951 return mStackSupervisor.getAllStackInfosLocked(); 9952 } 9953 } finally { 9954 Binder.restoreCallingIdentity(ident); 9955 } 9956 } 9957 9958 @Override 9959 public StackInfo getStackInfo(int stackId) { 9960 enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "getStackInfo()"); 9961 long ident = Binder.clearCallingIdentity(); 9962 try { 9963 synchronized (this) { 9964 return mStackSupervisor.getStackInfoLocked(stackId); 9965 } 9966 } finally { 9967 Binder.restoreCallingIdentity(ident); 9968 } 9969 } 9970 9971 @Override 9972 public boolean isInHomeStack(int taskId) { 9973 enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "getStackInfo()"); 9974 long ident = Binder.clearCallingIdentity(); 9975 try { 9976 synchronized (this) { 9977 final TaskRecord tr = mStackSupervisor.anyTaskForIdLocked( 9978 taskId, !RESTORE_FROM_RECENTS, INVALID_STACK_ID); 9979 final ActivityStack stack = tr != null ? tr.getStack() : null; 9980 return stack != null && stack.isHomeStack(); 9981 } 9982 } finally { 9983 Binder.restoreCallingIdentity(ident); 9984 } 9985 } 9986 9987 @Override 9988 public int getTaskForActivity(IBinder token, boolean onlyRoot) { 9989 synchronized(this) { 9990 return ActivityRecord.getTaskForActivityLocked(token, onlyRoot); 9991 } 9992 } 9993 9994 @Override 9995 public void updateDeviceOwner(String packageName) { 9996 final int callingUid = Binder.getCallingUid(); 9997 if (callingUid != 0 && callingUid != Process.SYSTEM_UID) { 9998 throw new SecurityException("updateDeviceOwner called from non-system process"); 9999 } 10000 synchronized (this) { 10001 mDeviceOwnerName = packageName; 10002 } 10003 } 10004 10005 @Override 10006 public void updateLockTaskPackages(int userId, String[] packages) { 10007 final int callingUid = Binder.getCallingUid(); 10008 if (callingUid != 0 && callingUid != Process.SYSTEM_UID) { 10009 enforceCallingPermission(android.Manifest.permission.UPDATE_LOCK_TASK_PACKAGES, 10010 "updateLockTaskPackages()"); 10011 } 10012 synchronized (this) { 10013 if (DEBUG_LOCKTASK) Slog.w(TAG_LOCKTASK, "Whitelisting " + userId + ":" + 10014 Arrays.toString(packages)); 10015 mLockTaskPackages.put(userId, packages); 10016 mStackSupervisor.onLockTaskPackagesUpdatedLocked(); 10017 } 10018 } 10019 10020 10021 void startLockTaskModeLocked(TaskRecord task) { 10022 if (DEBUG_LOCKTASK) Slog.w(TAG_LOCKTASK, "startLockTaskModeLocked: " + task); 10023 if (task.mLockTaskAuth == LOCK_TASK_AUTH_DONT_LOCK) { 10024 return; 10025 } 10026 10027 // isSystemInitiated is used to distinguish between locked and pinned mode, as pinned mode 10028 // is initiated by system after the pinning request was shown and locked mode is initiated 10029 // by an authorized app directly 10030 final int callingUid = Binder.getCallingUid(); 10031 boolean isSystemInitiated = callingUid == Process.SYSTEM_UID; 10032 long ident = Binder.clearCallingIdentity(); 10033 try { 10034 if (!isSystemInitiated) { 10035 task.mLockTaskUid = callingUid; 10036 if (task.mLockTaskAuth == LOCK_TASK_AUTH_PINNABLE) { 10037 // startLockTask() called by app and task mode is lockTaskModeDefault. 10038 if (DEBUG_LOCKTASK) Slog.w(TAG_LOCKTASK, "Mode default, asking user"); 10039 StatusBarManagerInternal statusBarManager = 10040 LocalServices.getService(StatusBarManagerInternal.class); 10041 if (statusBarManager != null) { 10042 statusBarManager.showScreenPinningRequest(task.taskId); 10043 } 10044 return; 10045 } 10046 10047 final ActivityStack stack = mStackSupervisor.getFocusedStack(); 10048 if (stack == null || task != stack.topTask()) { 10049 throw new IllegalArgumentException("Invalid task, not in foreground"); 10050 } 10051 } 10052 if (DEBUG_LOCKTASK) Slog.w(TAG_LOCKTASK, isSystemInitiated ? "Locking pinned" : 10053 "Locking fully"); 10054 mStackSupervisor.setLockTaskModeLocked(task, isSystemInitiated ? 10055 ActivityManager.LOCK_TASK_MODE_PINNED : 10056 ActivityManager.LOCK_TASK_MODE_LOCKED, 10057 "startLockTask", true); 10058 } finally { 10059 Binder.restoreCallingIdentity(ident); 10060 } 10061 } 10062 10063 @Override 10064 public void startLockTaskModeById(int taskId) { 10065 synchronized (this) { 10066 final TaskRecord task = mStackSupervisor.anyTaskForIdLocked(taskId); 10067 if (task != null) { 10068 startLockTaskModeLocked(task); 10069 } 10070 } 10071 } 10072 10073 @Override 10074 public void startLockTaskModeByToken(IBinder token) { 10075 synchronized (this) { 10076 final ActivityRecord r = ActivityRecord.forTokenLocked(token); 10077 if (r == null) { 10078 return; 10079 } 10080 final TaskRecord task = r.task; 10081 if (task != null) { 10082 startLockTaskModeLocked(task); 10083 } 10084 } 10085 } 10086 10087 @Override 10088 public void startSystemLockTaskMode(int taskId) throws RemoteException { 10089 enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "startSystemLockTaskMode"); 10090 // This makes inner call to look as if it was initiated by system. 10091 long ident = Binder.clearCallingIdentity(); 10092 try { 10093 synchronized (this) { 10094 startLockTaskModeById(taskId); 10095 } 10096 } finally { 10097 Binder.restoreCallingIdentity(ident); 10098 } 10099 } 10100 10101 @Override 10102 public void stopLockTaskMode() { 10103 final TaskRecord lockTask = mStackSupervisor.getLockedTaskLocked(); 10104 if (lockTask == null) { 10105 // Our work here is done. 10106 return; 10107 } 10108 10109 final int callingUid = Binder.getCallingUid(); 10110 final int lockTaskUid = lockTask.mLockTaskUid; 10111 final int lockTaskModeState = mStackSupervisor.getLockTaskModeState(); 10112 if (lockTaskModeState == ActivityManager.LOCK_TASK_MODE_NONE) { 10113 // Done. 10114 return; 10115 } else { 10116 // Ensure the same caller for startLockTaskMode and stopLockTaskMode. 10117 // It is possible lockTaskMode was started by the system process because 10118 // android:lockTaskMode is set to a locking value in the application manifest 10119 // instead of the app calling startLockTaskMode. In this case 10120 // {@link TaskRecord.mLockTaskUid} will be 0, so we compare the callingUid to the 10121 // {@link TaskRecord.effectiveUid} instead. Also caller with 10122 // {@link MANAGE_ACTIVITY_STACKS} can stop any lock task. 10123 if (checkCallingPermission(MANAGE_ACTIVITY_STACKS) != PERMISSION_GRANTED 10124 && callingUid != lockTaskUid 10125 && (lockTaskUid != 0 || callingUid != lockTask.effectiveUid)) { 10126 throw new SecurityException("Invalid uid, expected " + lockTaskUid 10127 + " callingUid=" + callingUid + " effectiveUid=" + lockTask.effectiveUid); 10128 } 10129 } 10130 long ident = Binder.clearCallingIdentity(); 10131 try { 10132 Log.d(TAG, "stopLockTaskMode"); 10133 // Stop lock task 10134 synchronized (this) { 10135 mStackSupervisor.setLockTaskModeLocked(null, ActivityManager.LOCK_TASK_MODE_NONE, 10136 "stopLockTask", true); 10137 } 10138 TelecomManager tm = (TelecomManager) mContext.getSystemService(Context.TELECOM_SERVICE); 10139 if (tm != null) { 10140 tm.showInCallScreen(false); 10141 } 10142 } finally { 10143 Binder.restoreCallingIdentity(ident); 10144 } 10145 } 10146 10147 /** 10148 * This API should be called by SystemUI only when user perform certain action to dismiss 10149 * lock task mode. We should only dismiss pinned lock task mode in this case. 10150 */ 10151 @Override 10152 public void stopSystemLockTaskMode() throws RemoteException { 10153 if (mStackSupervisor.getLockTaskModeState() == ActivityManager.LOCK_TASK_MODE_PINNED) { 10154 stopLockTaskMode(); 10155 } else { 10156 mStackSupervisor.showLockTaskToast(); 10157 } 10158 } 10159 10160 @Override 10161 public boolean isInLockTaskMode() { 10162 return getLockTaskModeState() != ActivityManager.LOCK_TASK_MODE_NONE; 10163 } 10164 10165 @Override 10166 public int getLockTaskModeState() { 10167 synchronized (this) { 10168 return mStackSupervisor.getLockTaskModeState(); 10169 } 10170 } 10171 10172 @Override 10173 public void showLockTaskEscapeMessage(IBinder token) { 10174 synchronized (this) { 10175 final ActivityRecord r = ActivityRecord.forTokenLocked(token); 10176 if (r == null) { 10177 return; 10178 } 10179 mStackSupervisor.showLockTaskEscapeMessageLocked(r.task); 10180 } 10181 } 10182 10183 // ========================================================= 10184 // CONTENT PROVIDERS 10185 // ========================================================= 10186 10187 private final List<ProviderInfo> generateApplicationProvidersLocked(ProcessRecord app) { 10188 List<ProviderInfo> providers = null; 10189 try { 10190 providers = AppGlobals.getPackageManager() 10191 .queryContentProviders(app.processName, app.uid, 10192 STOCK_PM_FLAGS | PackageManager.GET_URI_PERMISSION_PATTERNS 10193 | MATCH_DEBUG_TRIAGED_MISSING) 10194 .getList(); 10195 } catch (RemoteException ex) { 10196 } 10197 if (DEBUG_MU) Slog.v(TAG_MU, 10198 "generateApplicationProvidersLocked, app.info.uid = " + app.uid); 10199 int userId = app.userId; 10200 if (providers != null) { 10201 int N = providers.size(); 10202 app.pubProviders.ensureCapacity(N + app.pubProviders.size()); 10203 for (int i=0; i<N; i++) { 10204 // TODO: keep logic in sync with installEncryptionUnawareProviders 10205 ProviderInfo cpi = 10206 (ProviderInfo)providers.get(i); 10207 boolean singleton = isSingleton(cpi.processName, cpi.applicationInfo, 10208 cpi.name, cpi.flags); 10209 if (singleton && UserHandle.getUserId(app.uid) != UserHandle.USER_SYSTEM) { 10210 // This is a singleton provider, but a user besides the 10211 // default user is asking to initialize a process it runs 10212 // in... well, no, it doesn't actually run in this process, 10213 // it runs in the process of the default user. Get rid of it. 10214 providers.remove(i); 10215 N--; 10216 i--; 10217 continue; 10218 } 10219 10220 ComponentName comp = new ComponentName(cpi.packageName, cpi.name); 10221 ContentProviderRecord cpr = mProviderMap.getProviderByClass(comp, userId); 10222 if (cpr == null) { 10223 cpr = new ContentProviderRecord(this, cpi, app.info, comp, singleton); 10224 mProviderMap.putProviderByClass(comp, cpr); 10225 } 10226 if (DEBUG_MU) Slog.v(TAG_MU, 10227 "generateApplicationProvidersLocked, cpi.uid = " + cpr.uid); 10228 app.pubProviders.put(cpi.name, cpr); 10229 if (!cpi.multiprocess || !"android".equals(cpi.packageName)) { 10230 // Don't add this if it is a platform component that is marked 10231 // to run in multiple processes, because this is actually 10232 // part of the framework so doesn't make sense to track as a 10233 // separate apk in the process. 10234 app.addPackage(cpi.applicationInfo.packageName, cpi.applicationInfo.versionCode, 10235 mProcessStats); 10236 } 10237 notifyPackageUse(cpi.applicationInfo.packageName, 10238 PackageManager.NOTIFY_PACKAGE_USE_CONTENT_PROVIDER); 10239 } 10240 } 10241 return providers; 10242 } 10243 10244 /** 10245 * Check if {@link ProcessRecord} has a possible chance at accessing the 10246 * given {@link ProviderInfo}. Final permission checking is always done 10247 * in {@link ContentProvider}. 10248 */ 10249 private final String checkContentProviderPermissionLocked( 10250 ProviderInfo cpi, ProcessRecord r, int userId, boolean checkUser) { 10251 final int callingPid = (r != null) ? r.pid : Binder.getCallingPid(); 10252 final int callingUid = (r != null) ? r.uid : Binder.getCallingUid(); 10253 boolean checkedGrants = false; 10254 if (checkUser) { 10255 // Looking for cross-user grants before enforcing the typical cross-users permissions 10256 int tmpTargetUserId = mUserController.unsafeConvertIncomingUserLocked(userId); 10257 if (tmpTargetUserId != UserHandle.getUserId(callingUid)) { 10258 if (checkAuthorityGrants(callingUid, cpi, tmpTargetUserId, checkUser)) { 10259 return null; 10260 } 10261 checkedGrants = true; 10262 } 10263 userId = mUserController.handleIncomingUser(callingPid, callingUid, userId, false, 10264 ALLOW_NON_FULL, "checkContentProviderPermissionLocked " + cpi.authority, null); 10265 if (userId != tmpTargetUserId) { 10266 // When we actually went to determine the final targer user ID, this ended 10267 // up different than our initial check for the authority. This is because 10268 // they had asked for USER_CURRENT_OR_SELF and we ended up switching to 10269 // SELF. So we need to re-check the grants again. 10270 checkedGrants = false; 10271 } 10272 } 10273 if (checkComponentPermission(cpi.readPermission, callingPid, callingUid, 10274 cpi.applicationInfo.uid, cpi.exported) 10275 == PackageManager.PERMISSION_GRANTED) { 10276 return null; 10277 } 10278 if (checkComponentPermission(cpi.writePermission, callingPid, callingUid, 10279 cpi.applicationInfo.uid, cpi.exported) 10280 == PackageManager.PERMISSION_GRANTED) { 10281 return null; 10282 } 10283 10284 PathPermission[] pps = cpi.pathPermissions; 10285 if (pps != null) { 10286 int i = pps.length; 10287 while (i > 0) { 10288 i--; 10289 PathPermission pp = pps[i]; 10290 String pprperm = pp.getReadPermission(); 10291 if (pprperm != null && checkComponentPermission(pprperm, callingPid, callingUid, 10292 cpi.applicationInfo.uid, cpi.exported) 10293 == PackageManager.PERMISSION_GRANTED) { 10294 return null; 10295 } 10296 String ppwperm = pp.getWritePermission(); 10297 if (ppwperm != null && checkComponentPermission(ppwperm, callingPid, callingUid, 10298 cpi.applicationInfo.uid, cpi.exported) 10299 == PackageManager.PERMISSION_GRANTED) { 10300 return null; 10301 } 10302 } 10303 } 10304 if (!checkedGrants && checkAuthorityGrants(callingUid, cpi, userId, checkUser)) { 10305 return null; 10306 } 10307 10308 String msg; 10309 if (!cpi.exported) { 10310 msg = "Permission Denial: opening provider " + cpi.name 10311 + " from " + (r != null ? r : "(null)") + " (pid=" + callingPid 10312 + ", uid=" + callingUid + ") that is not exported from uid " 10313 + cpi.applicationInfo.uid; 10314 } else { 10315 msg = "Permission Denial: opening provider " + cpi.name 10316 + " from " + (r != null ? r : "(null)") + " (pid=" + callingPid 10317 + ", uid=" + callingUid + ") requires " 10318 + cpi.readPermission + " or " + cpi.writePermission; 10319 } 10320 Slog.w(TAG, msg); 10321 return msg; 10322 } 10323 10324 /** 10325 * Returns if the ContentProvider has granted a uri to callingUid 10326 */ 10327 boolean checkAuthorityGrants(int callingUid, ProviderInfo cpi, int userId, boolean checkUser) { 10328 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get(callingUid); 10329 if (perms != null) { 10330 for (int i=perms.size()-1; i>=0; i--) { 10331 GrantUri grantUri = perms.keyAt(i); 10332 if (grantUri.sourceUserId == userId || !checkUser) { 10333 if (matchesProvider(grantUri.uri, cpi)) { 10334 return true; 10335 } 10336 } 10337 } 10338 } 10339 return false; 10340 } 10341 10342 /** 10343 * Returns true if the uri authority is one of the authorities specified in the provider. 10344 */ 10345 boolean matchesProvider(Uri uri, ProviderInfo cpi) { 10346 String uriAuth = uri.getAuthority(); 10347 String cpiAuth = cpi.authority; 10348 if (cpiAuth.indexOf(';') == -1) { 10349 return cpiAuth.equals(uriAuth); 10350 } 10351 String[] cpiAuths = cpiAuth.split(";"); 10352 int length = cpiAuths.length; 10353 for (int i = 0; i < length; i++) { 10354 if (cpiAuths[i].equals(uriAuth)) return true; 10355 } 10356 return false; 10357 } 10358 10359 ContentProviderConnection incProviderCountLocked(ProcessRecord r, 10360 final ContentProviderRecord cpr, IBinder externalProcessToken, boolean stable) { 10361 if (r != null) { 10362 for (int i=0; i<r.conProviders.size(); i++) { 10363 ContentProviderConnection conn = r.conProviders.get(i); 10364 if (conn.provider == cpr) { 10365 if (DEBUG_PROVIDER) Slog.v(TAG_PROVIDER, 10366 "Adding provider requested by " 10367 + r.processName + " from process " 10368 + cpr.info.processName + ": " + cpr.name.flattenToShortString() 10369 + " scnt=" + conn.stableCount + " uscnt=" + conn.unstableCount); 10370 if (stable) { 10371 conn.stableCount++; 10372 conn.numStableIncs++; 10373 } else { 10374 conn.unstableCount++; 10375 conn.numUnstableIncs++; 10376 } 10377 return conn; 10378 } 10379 } 10380 ContentProviderConnection conn = new ContentProviderConnection(cpr, r); 10381 if (stable) { 10382 conn.stableCount = 1; 10383 conn.numStableIncs = 1; 10384 } else { 10385 conn.unstableCount = 1; 10386 conn.numUnstableIncs = 1; 10387 } 10388 cpr.connections.add(conn); 10389 r.conProviders.add(conn); 10390 startAssociationLocked(r.uid, r.processName, r.curProcState, 10391 cpr.uid, cpr.name, cpr.info.processName); 10392 return conn; 10393 } 10394 cpr.addExternalProcessHandleLocked(externalProcessToken); 10395 return null; 10396 } 10397 10398 boolean decProviderCountLocked(ContentProviderConnection conn, 10399 ContentProviderRecord cpr, IBinder externalProcessToken, boolean stable) { 10400 if (conn != null) { 10401 cpr = conn.provider; 10402 if (DEBUG_PROVIDER) Slog.v(TAG_PROVIDER, 10403 "Removing provider requested by " 10404 + conn.client.processName + " from process " 10405 + cpr.info.processName + ": " + cpr.name.flattenToShortString() 10406 + " scnt=" + conn.stableCount + " uscnt=" + conn.unstableCount); 10407 if (stable) { 10408 conn.stableCount--; 10409 } else { 10410 conn.unstableCount--; 10411 } 10412 if (conn.stableCount == 0 && conn.unstableCount == 0) { 10413 cpr.connections.remove(conn); 10414 conn.client.conProviders.remove(conn); 10415 if (conn.client.setProcState < ActivityManager.PROCESS_STATE_LAST_ACTIVITY) { 10416 // The client is more important than last activity -- note the time this 10417 // is happening, so we keep the old provider process around a bit as last 10418 // activity to avoid thrashing it. 10419 if (cpr.proc != null) { 10420 cpr.proc.lastProviderTime = SystemClock.uptimeMillis(); 10421 } 10422 } 10423 stopAssociationLocked(conn.client.uid, conn.client.processName, cpr.uid, cpr.name); 10424 return true; 10425 } 10426 return false; 10427 } 10428 cpr.removeExternalProcessHandleLocked(externalProcessToken); 10429 return false; 10430 } 10431 10432 private void checkTime(long startTime, String where) { 10433 long now = SystemClock.uptimeMillis(); 10434 if ((now-startTime) > 50) { 10435 // If we are taking more than 50ms, log about it. 10436 Slog.w(TAG, "Slow operation: " + (now-startTime) + "ms so far, now at " + where); 10437 } 10438 } 10439 10440 private static final int[] PROCESS_STATE_STATS_FORMAT = new int[] { 10441 PROC_SPACE_TERM, 10442 PROC_SPACE_TERM|PROC_PARENS, 10443 PROC_SPACE_TERM|PROC_CHAR|PROC_OUT_LONG, // 3: process state 10444 }; 10445 10446 private final long[] mProcessStateStatsLongs = new long[1]; 10447 10448 boolean isProcessAliveLocked(ProcessRecord proc) { 10449 if (proc.procStatFile == null) { 10450 proc.procStatFile = "/proc/" + proc.pid + "/stat"; 10451 } 10452 mProcessStateStatsLongs[0] = 0; 10453 if (!Process.readProcFile(proc.procStatFile, PROCESS_STATE_STATS_FORMAT, null, 10454 mProcessStateStatsLongs, null)) { 10455 if (DEBUG_OOM_ADJ) Slog.d(TAG, "UNABLE TO RETRIEVE STATE FOR " + proc.procStatFile); 10456 return false; 10457 } 10458 final long state = mProcessStateStatsLongs[0]; 10459 if (DEBUG_OOM_ADJ) Slog.d(TAG, "RETRIEVED STATE FOR " + proc.procStatFile + ": " 10460 + (char)state); 10461 return state != 'Z' && state != 'X' && state != 'x' && state != 'K'; 10462 } 10463 10464 private ContentProviderHolder getContentProviderImpl(IApplicationThread caller, 10465 String name, IBinder token, boolean stable, int userId) { 10466 ContentProviderRecord cpr; 10467 ContentProviderConnection conn = null; 10468 ProviderInfo cpi = null; 10469 10470 synchronized(this) { 10471 long startTime = SystemClock.uptimeMillis(); 10472 10473 ProcessRecord r = null; 10474 if (caller != null) { 10475 r = getRecordForAppLocked(caller); 10476 if (r == null) { 10477 throw new SecurityException( 10478 "Unable to find app for caller " + caller 10479 + " (pid=" + Binder.getCallingPid() 10480 + ") when getting content provider " + name); 10481 } 10482 } 10483 10484 boolean checkCrossUser = true; 10485 10486 checkTime(startTime, "getContentProviderImpl: getProviderByName"); 10487 10488 // First check if this content provider has been published... 10489 cpr = mProviderMap.getProviderByName(name, userId); 10490 // If that didn't work, check if it exists for user 0 and then 10491 // verify that it's a singleton provider before using it. 10492 if (cpr == null && userId != UserHandle.USER_SYSTEM) { 10493 cpr = mProviderMap.getProviderByName(name, UserHandle.USER_SYSTEM); 10494 if (cpr != null) { 10495 cpi = cpr.info; 10496 if (isSingleton(cpi.processName, cpi.applicationInfo, 10497 cpi.name, cpi.flags) 10498 && isValidSingletonCall(r.uid, cpi.applicationInfo.uid)) { 10499 userId = UserHandle.USER_SYSTEM; 10500 checkCrossUser = false; 10501 } else { 10502 cpr = null; 10503 cpi = null; 10504 } 10505 } 10506 } 10507 10508 boolean providerRunning = cpr != null && cpr.proc != null && !cpr.proc.killed; 10509 if (providerRunning) { 10510 cpi = cpr.info; 10511 String msg; 10512 checkTime(startTime, "getContentProviderImpl: before checkContentProviderPermission"); 10513 if ((msg = checkContentProviderPermissionLocked(cpi, r, userId, checkCrossUser)) 10514 != null) { 10515 throw new SecurityException(msg); 10516 } 10517 checkTime(startTime, "getContentProviderImpl: after checkContentProviderPermission"); 10518 10519 if (r != null && cpr.canRunHere(r)) { 10520 // This provider has been published or is in the process 10521 // of being published... but it is also allowed to run 10522 // in the caller's process, so don't make a connection 10523 // and just let the caller instantiate its own instance. 10524 ContentProviderHolder holder = cpr.newHolder(null); 10525 // don't give caller the provider object, it needs 10526 // to make its own. 10527 holder.provider = null; 10528 return holder; 10529 } 10530 10531 final long origId = Binder.clearCallingIdentity(); 10532 10533 checkTime(startTime, "getContentProviderImpl: incProviderCountLocked"); 10534 10535 // In this case the provider instance already exists, so we can 10536 // return it right away. 10537 conn = incProviderCountLocked(r, cpr, token, stable); 10538 if (conn != null && (conn.stableCount+conn.unstableCount) == 1) { 10539 if (cpr.proc != null && r.setAdj <= ProcessList.PERCEPTIBLE_APP_ADJ) { 10540 // If this is a perceptible app accessing the provider, 10541 // make sure to count it as being accessed and thus 10542 // back up on the LRU list. This is good because 10543 // content providers are often expensive to start. 10544 checkTime(startTime, "getContentProviderImpl: before updateLruProcess"); 10545 updateLruProcessLocked(cpr.proc, false, null); 10546 checkTime(startTime, "getContentProviderImpl: after updateLruProcess"); 10547 } 10548 } 10549 10550 checkTime(startTime, "getContentProviderImpl: before updateOomAdj"); 10551 final int verifiedAdj = cpr.proc.verifiedAdj; 10552 boolean success = updateOomAdjLocked(cpr.proc); 10553 // XXX things have changed so updateOomAdjLocked doesn't actually tell us 10554 // if the process has been successfully adjusted. So to reduce races with 10555 // it, we will check whether the process still exists. Note that this doesn't 10556 // completely get rid of races with LMK killing the process, but should make 10557 // them much smaller. 10558 if (success && verifiedAdj != cpr.proc.setAdj && !isProcessAliveLocked(cpr.proc)) { 10559 success = false; 10560 } 10561 maybeUpdateProviderUsageStatsLocked(r, cpr.info.packageName, name); 10562 checkTime(startTime, "getContentProviderImpl: after updateOomAdj"); 10563 if (DEBUG_PROVIDER) Slog.i(TAG_PROVIDER, "Adjust success: " + success); 10564 // NOTE: there is still a race here where a signal could be 10565 // pending on the process even though we managed to update its 10566 // adj level. Not sure what to do about this, but at least 10567 // the race is now smaller. 10568 if (!success) { 10569 // Uh oh... it looks like the provider's process 10570 // has been killed on us. We need to wait for a new 10571 // process to be started, and make sure its death 10572 // doesn't kill our process. 10573 Slog.i(TAG, "Existing provider " + cpr.name.flattenToShortString() 10574 + " is crashing; detaching " + r); 10575 boolean lastRef = decProviderCountLocked(conn, cpr, token, stable); 10576 checkTime(startTime, "getContentProviderImpl: before appDied"); 10577 appDiedLocked(cpr.proc); 10578 checkTime(startTime, "getContentProviderImpl: after appDied"); 10579 if (!lastRef) { 10580 // This wasn't the last ref our process had on 10581 // the provider... we have now been killed, bail. 10582 return null; 10583 } 10584 providerRunning = false; 10585 conn = null; 10586 } else { 10587 cpr.proc.verifiedAdj = cpr.proc.setAdj; 10588 } 10589 10590 Binder.restoreCallingIdentity(origId); 10591 } 10592 10593 if (!providerRunning) { 10594 try { 10595 checkTime(startTime, "getContentProviderImpl: before resolveContentProvider"); 10596 cpi = AppGlobals.getPackageManager(). 10597 resolveContentProvider(name, 10598 STOCK_PM_FLAGS | PackageManager.GET_URI_PERMISSION_PATTERNS, userId); 10599 checkTime(startTime, "getContentProviderImpl: after resolveContentProvider"); 10600 } catch (RemoteException ex) { 10601 } 10602 if (cpi == null) { 10603 return null; 10604 } 10605 // If the provider is a singleton AND 10606 // (it's a call within the same user || the provider is a 10607 // privileged app) 10608 // Then allow connecting to the singleton provider 10609 boolean singleton = isSingleton(cpi.processName, cpi.applicationInfo, 10610 cpi.name, cpi.flags) 10611 && isValidSingletonCall(r.uid, cpi.applicationInfo.uid); 10612 if (singleton) { 10613 userId = UserHandle.USER_SYSTEM; 10614 } 10615 cpi.applicationInfo = getAppInfoForUser(cpi.applicationInfo, userId); 10616 checkTime(startTime, "getContentProviderImpl: got app info for user"); 10617 10618 String msg; 10619 checkTime(startTime, "getContentProviderImpl: before checkContentProviderPermission"); 10620 if ((msg = checkContentProviderPermissionLocked(cpi, r, userId, !singleton)) 10621 != null) { 10622 throw new SecurityException(msg); 10623 } 10624 checkTime(startTime, "getContentProviderImpl: after checkContentProviderPermission"); 10625 10626 if (!mProcessesReady 10627 && !cpi.processName.equals("system")) { 10628 // If this content provider does not run in the system 10629 // process, and the system is not yet ready to run other 10630 // processes, then fail fast instead of hanging. 10631 throw new IllegalArgumentException( 10632 "Attempt to launch content provider before system ready"); 10633 } 10634 10635 // Make sure that the user who owns this provider is running. If not, 10636 // we don't want to allow it to run. 10637 if (!mUserController.isUserRunningLocked(userId, 0)) { 10638 Slog.w(TAG, "Unable to launch app " 10639 + cpi.applicationInfo.packageName + "/" 10640 + cpi.applicationInfo.uid + " for provider " 10641 + name + ": user " + userId + " is stopped"); 10642 return null; 10643 } 10644 10645 ComponentName comp = new ComponentName(cpi.packageName, cpi.name); 10646 checkTime(startTime, "getContentProviderImpl: before getProviderByClass"); 10647 cpr = mProviderMap.getProviderByClass(comp, userId); 10648 checkTime(startTime, "getContentProviderImpl: after getProviderByClass"); 10649 final boolean firstClass = cpr == null; 10650 if (firstClass) { 10651 final long ident = Binder.clearCallingIdentity(); 10652 10653 // If permissions need a review before any of the app components can run, 10654 // we return no provider and launch a review activity if the calling app 10655 // is in the foreground. 10656 if (mPermissionReviewRequired) { 10657 if (!requestTargetProviderPermissionsReviewIfNeededLocked(cpi, r, userId)) { 10658 return null; 10659 } 10660 } 10661 10662 try { 10663 checkTime(startTime, "getContentProviderImpl: before getApplicationInfo"); 10664 ApplicationInfo ai = 10665 AppGlobals.getPackageManager(). 10666 getApplicationInfo( 10667 cpi.applicationInfo.packageName, 10668 STOCK_PM_FLAGS, userId); 10669 checkTime(startTime, "getContentProviderImpl: after getApplicationInfo"); 10670 if (ai == null) { 10671 Slog.w(TAG, "No package info for content provider " 10672 + cpi.name); 10673 return null; 10674 } 10675 ai = getAppInfoForUser(ai, userId); 10676 cpr = new ContentProviderRecord(this, cpi, ai, comp, singleton); 10677 } catch (RemoteException ex) { 10678 // pm is in same process, this will never happen. 10679 } finally { 10680 Binder.restoreCallingIdentity(ident); 10681 } 10682 } 10683 10684 checkTime(startTime, "getContentProviderImpl: now have ContentProviderRecord"); 10685 10686 if (r != null && cpr.canRunHere(r)) { 10687 // If this is a multiprocess provider, then just return its 10688 // info and allow the caller to instantiate it. Only do 10689 // this if the provider is the same user as the caller's 10690 // process, or can run as root (so can be in any process). 10691 return cpr.newHolder(null); 10692 } 10693 10694 if (DEBUG_PROVIDER) Slog.w(TAG_PROVIDER, "LAUNCHING REMOTE PROVIDER (myuid " 10695 + (r != null ? r.uid : null) + " pruid " + cpr.appInfo.uid + "): " 10696 + cpr.info.name + " callers=" + Debug.getCallers(6)); 10697 10698 // This is single process, and our app is now connecting to it. 10699 // See if we are already in the process of launching this 10700 // provider. 10701 final int N = mLaunchingProviders.size(); 10702 int i; 10703 for (i = 0; i < N; i++) { 10704 if (mLaunchingProviders.get(i) == cpr) { 10705 break; 10706 } 10707 } 10708 10709 // If the provider is not already being launched, then get it 10710 // started. 10711 if (i >= N) { 10712 final long origId = Binder.clearCallingIdentity(); 10713 10714 try { 10715 // Content provider is now in use, its package can't be stopped. 10716 try { 10717 checkTime(startTime, "getContentProviderImpl: before set stopped state"); 10718 AppGlobals.getPackageManager().setPackageStoppedState( 10719 cpr.appInfo.packageName, false, userId); 10720 checkTime(startTime, "getContentProviderImpl: after set stopped state"); 10721 } catch (RemoteException e) { 10722 } catch (IllegalArgumentException e) { 10723 Slog.w(TAG, "Failed trying to unstop package " 10724 + cpr.appInfo.packageName + ": " + e); 10725 } 10726 10727 // Use existing process if already started 10728 checkTime(startTime, "getContentProviderImpl: looking for process record"); 10729 ProcessRecord proc = getProcessRecordLocked( 10730 cpi.processName, cpr.appInfo.uid, false); 10731 if (proc != null && proc.thread != null && !proc.killed) { 10732 if (DEBUG_PROVIDER) Slog.d(TAG_PROVIDER, 10733 "Installing in existing process " + proc); 10734 if (!proc.pubProviders.containsKey(cpi.name)) { 10735 checkTime(startTime, "getContentProviderImpl: scheduling install"); 10736 proc.pubProviders.put(cpi.name, cpr); 10737 try { 10738 proc.thread.scheduleInstallProvider(cpi); 10739 } catch (RemoteException e) { 10740 } 10741 } 10742 } else { 10743 checkTime(startTime, "getContentProviderImpl: before start process"); 10744 proc = startProcessLocked(cpi.processName, 10745 cpr.appInfo, false, 0, "content provider", 10746 new ComponentName(cpi.applicationInfo.packageName, 10747 cpi.name), false, false, false); 10748 checkTime(startTime, "getContentProviderImpl: after start process"); 10749 if (proc == null) { 10750 Slog.w(TAG, "Unable to launch app " 10751 + cpi.applicationInfo.packageName + "/" 10752 + cpi.applicationInfo.uid + " for provider " 10753 + name + ": process is bad"); 10754 return null; 10755 } 10756 } 10757 cpr.launchingApp = proc; 10758 mLaunchingProviders.add(cpr); 10759 } finally { 10760 Binder.restoreCallingIdentity(origId); 10761 } 10762 } 10763 10764 checkTime(startTime, "getContentProviderImpl: updating data structures"); 10765 10766 // Make sure the provider is published (the same provider class 10767 // may be published under multiple names). 10768 if (firstClass) { 10769 mProviderMap.putProviderByClass(comp, cpr); 10770 } 10771 10772 mProviderMap.putProviderByName(name, cpr); 10773 conn = incProviderCountLocked(r, cpr, token, stable); 10774 if (conn != null) { 10775 conn.waiting = true; 10776 } 10777 } 10778 checkTime(startTime, "getContentProviderImpl: done!"); 10779 } 10780 10781 // Wait for the provider to be published... 10782 synchronized (cpr) { 10783 while (cpr.provider == null) { 10784 if (cpr.launchingApp == null) { 10785 Slog.w(TAG, "Unable to launch app " 10786 + cpi.applicationInfo.packageName + "/" 10787 + cpi.applicationInfo.uid + " for provider " 10788 + name + ": launching app became null"); 10789 EventLog.writeEvent(EventLogTags.AM_PROVIDER_LOST_PROCESS, 10790 UserHandle.getUserId(cpi.applicationInfo.uid), 10791 cpi.applicationInfo.packageName, 10792 cpi.applicationInfo.uid, name); 10793 return null; 10794 } 10795 try { 10796 if (DEBUG_MU) Slog.v(TAG_MU, 10797 "Waiting to start provider " + cpr 10798 + " launchingApp=" + cpr.launchingApp); 10799 if (conn != null) { 10800 conn.waiting = true; 10801 } 10802 cpr.wait(); 10803 } catch (InterruptedException ex) { 10804 } finally { 10805 if (conn != null) { 10806 conn.waiting = false; 10807 } 10808 } 10809 } 10810 } 10811 return cpr != null ? cpr.newHolder(conn) : null; 10812 } 10813 10814 private boolean requestTargetProviderPermissionsReviewIfNeededLocked(ProviderInfo cpi, 10815 ProcessRecord r, final int userId) { 10816 if (getPackageManagerInternalLocked().isPermissionsReviewRequired( 10817 cpi.packageName, userId)) { 10818 10819 final boolean callerForeground = r == null || r.setSchedGroup 10820 != ProcessList.SCHED_GROUP_BACKGROUND; 10821 10822 // Show a permission review UI only for starting from a foreground app 10823 if (!callerForeground) { 10824 Slog.w(TAG, "u" + userId + " Instantiating a provider in package" 10825 + cpi.packageName + " requires a permissions review"); 10826 return false; 10827 } 10828 10829 final Intent intent = new Intent(Intent.ACTION_REVIEW_PERMISSIONS); 10830 intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK 10831 | Intent.FLAG_ACTIVITY_EXCLUDE_FROM_RECENTS); 10832 intent.putExtra(Intent.EXTRA_PACKAGE_NAME, cpi.packageName); 10833 10834 if (DEBUG_PERMISSIONS_REVIEW) { 10835 Slog.i(TAG, "u" + userId + " Launching permission review " 10836 + "for package " + cpi.packageName); 10837 } 10838 10839 final UserHandle userHandle = new UserHandle(userId); 10840 mHandler.post(new Runnable() { 10841 @Override 10842 public void run() { 10843 mContext.startActivityAsUser(intent, userHandle); 10844 } 10845 }); 10846 10847 return false; 10848 } 10849 10850 return true; 10851 } 10852 10853 PackageManagerInternal getPackageManagerInternalLocked() { 10854 if (mPackageManagerInt == null) { 10855 mPackageManagerInt = LocalServices.getService(PackageManagerInternal.class); 10856 } 10857 return mPackageManagerInt; 10858 } 10859 10860 @Override 10861 public final ContentProviderHolder getContentProvider( 10862 IApplicationThread caller, String name, int userId, boolean stable) { 10863 enforceNotIsolatedCaller("getContentProvider"); 10864 if (caller == null) { 10865 String msg = "null IApplicationThread when getting content provider " 10866 + name; 10867 Slog.w(TAG, msg); 10868 throw new SecurityException(msg); 10869 } 10870 // The incoming user check is now handled in checkContentProviderPermissionLocked() to deal 10871 // with cross-user grant. 10872 return getContentProviderImpl(caller, name, null, stable, userId); 10873 } 10874 10875 public ContentProviderHolder getContentProviderExternal( 10876 String name, int userId, IBinder token) { 10877 enforceCallingPermission(android.Manifest.permission.ACCESS_CONTENT_PROVIDERS_EXTERNALLY, 10878 "Do not have permission in call getContentProviderExternal()"); 10879 userId = mUserController.handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 10880 userId, false, ALLOW_FULL_ONLY, "getContentProvider", null); 10881 return getContentProviderExternalUnchecked(name, token, userId); 10882 } 10883 10884 private ContentProviderHolder getContentProviderExternalUnchecked(String name, 10885 IBinder token, int userId) { 10886 return getContentProviderImpl(null, name, token, true, userId); 10887 } 10888 10889 /** 10890 * Drop a content provider from a ProcessRecord's bookkeeping 10891 */ 10892 public void removeContentProvider(IBinder connection, boolean stable) { 10893 enforceNotIsolatedCaller("removeContentProvider"); 10894 long ident = Binder.clearCallingIdentity(); 10895 try { 10896 synchronized (this) { 10897 ContentProviderConnection conn; 10898 try { 10899 conn = (ContentProviderConnection)connection; 10900 } catch (ClassCastException e) { 10901 String msg ="removeContentProvider: " + connection 10902 + " not a ContentProviderConnection"; 10903 Slog.w(TAG, msg); 10904 throw new IllegalArgumentException(msg); 10905 } 10906 if (conn == null) { 10907 throw new NullPointerException("connection is null"); 10908 } 10909 if (decProviderCountLocked(conn, null, null, stable)) { 10910 updateOomAdjLocked(); 10911 } 10912 } 10913 } finally { 10914 Binder.restoreCallingIdentity(ident); 10915 } 10916 } 10917 10918 public void removeContentProviderExternal(String name, IBinder token) { 10919 enforceCallingPermission(android.Manifest.permission.ACCESS_CONTENT_PROVIDERS_EXTERNALLY, 10920 "Do not have permission in call removeContentProviderExternal()"); 10921 int userId = UserHandle.getCallingUserId(); 10922 long ident = Binder.clearCallingIdentity(); 10923 try { 10924 removeContentProviderExternalUnchecked(name, token, userId); 10925 } finally { 10926 Binder.restoreCallingIdentity(ident); 10927 } 10928 } 10929 10930 private void removeContentProviderExternalUnchecked(String name, IBinder token, int userId) { 10931 synchronized (this) { 10932 ContentProviderRecord cpr = mProviderMap.getProviderByName(name, userId); 10933 if(cpr == null) { 10934 //remove from mProvidersByClass 10935 if(DEBUG_ALL) Slog.v(TAG, name+" content provider not found in providers list"); 10936 return; 10937 } 10938 10939 //update content provider record entry info 10940 ComponentName comp = new ComponentName(cpr.info.packageName, cpr.info.name); 10941 ContentProviderRecord localCpr = mProviderMap.getProviderByClass(comp, userId); 10942 if (localCpr.hasExternalProcessHandles()) { 10943 if (localCpr.removeExternalProcessHandleLocked(token)) { 10944 updateOomAdjLocked(); 10945 } else { 10946 Slog.e(TAG, "Attmpt to remove content provider " + localCpr 10947 + " with no external reference for token: " 10948 + token + "."); 10949 } 10950 } else { 10951 Slog.e(TAG, "Attmpt to remove content provider: " + localCpr 10952 + " with no external references."); 10953 } 10954 } 10955 } 10956 10957 public final void publishContentProviders(IApplicationThread caller, 10958 List<ContentProviderHolder> providers) { 10959 if (providers == null) { 10960 return; 10961 } 10962 10963 enforceNotIsolatedCaller("publishContentProviders"); 10964 synchronized (this) { 10965 final ProcessRecord r = getRecordForAppLocked(caller); 10966 if (DEBUG_MU) Slog.v(TAG_MU, "ProcessRecord uid = " + r.uid); 10967 if (r == null) { 10968 throw new SecurityException( 10969 "Unable to find app for caller " + caller 10970 + " (pid=" + Binder.getCallingPid() 10971 + ") when publishing content providers"); 10972 } 10973 10974 final long origId = Binder.clearCallingIdentity(); 10975 10976 final int N = providers.size(); 10977 for (int i = 0; i < N; i++) { 10978 ContentProviderHolder src = providers.get(i); 10979 if (src == null || src.info == null || src.provider == null) { 10980 continue; 10981 } 10982 ContentProviderRecord dst = r.pubProviders.get(src.info.name); 10983 if (DEBUG_MU) Slog.v(TAG_MU, "ContentProviderRecord uid = " + dst.uid); 10984 if (dst != null) { 10985 ComponentName comp = new ComponentName(dst.info.packageName, dst.info.name); 10986 mProviderMap.putProviderByClass(comp, dst); 10987 String names[] = dst.info.authority.split(";"); 10988 for (int j = 0; j < names.length; j++) { 10989 mProviderMap.putProviderByName(names[j], dst); 10990 } 10991 10992 int launchingCount = mLaunchingProviders.size(); 10993 int j; 10994 boolean wasInLaunchingProviders = false; 10995 for (j = 0; j < launchingCount; j++) { 10996 if (mLaunchingProviders.get(j) == dst) { 10997 mLaunchingProviders.remove(j); 10998 wasInLaunchingProviders = true; 10999 j--; 11000 launchingCount--; 11001 } 11002 } 11003 if (wasInLaunchingProviders) { 11004 mHandler.removeMessages(CONTENT_PROVIDER_PUBLISH_TIMEOUT_MSG, r); 11005 } 11006 synchronized (dst) { 11007 dst.provider = src.provider; 11008 dst.proc = r; 11009 dst.notifyAll(); 11010 } 11011 updateOomAdjLocked(r); 11012 maybeUpdateProviderUsageStatsLocked(r, src.info.packageName, 11013 src.info.authority); 11014 } 11015 } 11016 11017 Binder.restoreCallingIdentity(origId); 11018 } 11019 } 11020 11021 public boolean refContentProvider(IBinder connection, int stable, int unstable) { 11022 ContentProviderConnection conn; 11023 try { 11024 conn = (ContentProviderConnection)connection; 11025 } catch (ClassCastException e) { 11026 String msg ="refContentProvider: " + connection 11027 + " not a ContentProviderConnection"; 11028 Slog.w(TAG, msg); 11029 throw new IllegalArgumentException(msg); 11030 } 11031 if (conn == null) { 11032 throw new NullPointerException("connection is null"); 11033 } 11034 11035 synchronized (this) { 11036 if (stable > 0) { 11037 conn.numStableIncs += stable; 11038 } 11039 stable = conn.stableCount + stable; 11040 if (stable < 0) { 11041 throw new IllegalStateException("stableCount < 0: " + stable); 11042 } 11043 11044 if (unstable > 0) { 11045 conn.numUnstableIncs += unstable; 11046 } 11047 unstable = conn.unstableCount + unstable; 11048 if (unstable < 0) { 11049 throw new IllegalStateException("unstableCount < 0: " + unstable); 11050 } 11051 11052 if ((stable+unstable) <= 0) { 11053 throw new IllegalStateException("ref counts can't go to zero here: stable=" 11054 + stable + " unstable=" + unstable); 11055 } 11056 conn.stableCount = stable; 11057 conn.unstableCount = unstable; 11058 return !conn.dead; 11059 } 11060 } 11061 11062 public void unstableProviderDied(IBinder connection) { 11063 ContentProviderConnection conn; 11064 try { 11065 conn = (ContentProviderConnection)connection; 11066 } catch (ClassCastException e) { 11067 String msg ="refContentProvider: " + connection 11068 + " not a ContentProviderConnection"; 11069 Slog.w(TAG, msg); 11070 throw new IllegalArgumentException(msg); 11071 } 11072 if (conn == null) { 11073 throw new NullPointerException("connection is null"); 11074 } 11075 11076 // Safely retrieve the content provider associated with the connection. 11077 IContentProvider provider; 11078 synchronized (this) { 11079 provider = conn.provider.provider; 11080 } 11081 11082 if (provider == null) { 11083 // Um, yeah, we're way ahead of you. 11084 return; 11085 } 11086 11087 // Make sure the caller is being honest with us. 11088 if (provider.asBinder().pingBinder()) { 11089 // Er, no, still looks good to us. 11090 synchronized (this) { 11091 Slog.w(TAG, "unstableProviderDied: caller " + Binder.getCallingUid() 11092 + " says " + conn + " died, but we don't agree"); 11093 return; 11094 } 11095 } 11096 11097 // Well look at that! It's dead! 11098 synchronized (this) { 11099 if (conn.provider.provider != provider) { 11100 // But something changed... good enough. 11101 return; 11102 } 11103 11104 ProcessRecord proc = conn.provider.proc; 11105 if (proc == null || proc.thread == null) { 11106 // Seems like the process is already cleaned up. 11107 return; 11108 } 11109 11110 // As far as we're concerned, this is just like receiving a 11111 // death notification... just a bit prematurely. 11112 Slog.i(TAG, "Process " + proc.processName + " (pid " + proc.pid 11113 + ") early provider death"); 11114 final long ident = Binder.clearCallingIdentity(); 11115 try { 11116 appDiedLocked(proc); 11117 } finally { 11118 Binder.restoreCallingIdentity(ident); 11119 } 11120 } 11121 } 11122 11123 @Override 11124 public void appNotRespondingViaProvider(IBinder connection) { 11125 enforceCallingPermission( 11126 android.Manifest.permission.REMOVE_TASKS, "appNotRespondingViaProvider()"); 11127 11128 final ContentProviderConnection conn = (ContentProviderConnection) connection; 11129 if (conn == null) { 11130 Slog.w(TAG, "ContentProviderConnection is null"); 11131 return; 11132 } 11133 11134 final ProcessRecord host = conn.provider.proc; 11135 if (host == null) { 11136 Slog.w(TAG, "Failed to find hosting ProcessRecord"); 11137 return; 11138 } 11139 11140 mHandler.post(new Runnable() { 11141 @Override 11142 public void run() { 11143 mAppErrors.appNotResponding(host, null, null, false, 11144 "ContentProvider not responding"); 11145 } 11146 }); 11147 } 11148 11149 public final void installSystemProviders() { 11150 List<ProviderInfo> providers; 11151 synchronized (this) { 11152 ProcessRecord app = mProcessNames.get("system", Process.SYSTEM_UID); 11153 providers = generateApplicationProvidersLocked(app); 11154 if (providers != null) { 11155 for (int i=providers.size()-1; i>=0; i--) { 11156 ProviderInfo pi = (ProviderInfo)providers.get(i); 11157 if ((pi.applicationInfo.flags&ApplicationInfo.FLAG_SYSTEM) == 0) { 11158 Slog.w(TAG, "Not installing system proc provider " + pi.name 11159 + ": not system .apk"); 11160 providers.remove(i); 11161 } 11162 } 11163 } 11164 } 11165 if (providers != null) { 11166 mSystemThread.installSystemProviders(providers); 11167 } 11168 11169 mCoreSettingsObserver = new CoreSettingsObserver(this); 11170 mFontScaleSettingObserver = new FontScaleSettingObserver(); 11171 11172 //mUsageStatsService.monitorPackages(); 11173 } 11174 11175 private void startPersistentApps(int matchFlags) { 11176 if (mFactoryTest == FactoryTest.FACTORY_TEST_LOW_LEVEL) return; 11177 11178 synchronized (this) { 11179 try { 11180 final List<ApplicationInfo> apps = AppGlobals.getPackageManager() 11181 .getPersistentApplications(STOCK_PM_FLAGS | matchFlags).getList(); 11182 for (ApplicationInfo app : apps) { 11183 if (!"android".equals(app.packageName)) { 11184 addAppLocked(app, false, null /* ABI override */); 11185 } 11186 } 11187 } catch (RemoteException ex) { 11188 } 11189 } 11190 } 11191 11192 /** 11193 * When a user is unlocked, we need to install encryption-unaware providers 11194 * belonging to any running apps. 11195 */ 11196 private void installEncryptionUnawareProviders(int userId) { 11197 // We're only interested in providers that are encryption unaware, and 11198 // we don't care about uninstalled apps, since there's no way they're 11199 // running at this point. 11200 final int matchFlags = GET_PROVIDERS | MATCH_DIRECT_BOOT_UNAWARE; 11201 11202 synchronized (this) { 11203 final int NP = mProcessNames.getMap().size(); 11204 for (int ip = 0; ip < NP; ip++) { 11205 final SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 11206 final int NA = apps.size(); 11207 for (int ia = 0; ia < NA; ia++) { 11208 final ProcessRecord app = apps.valueAt(ia); 11209 if (app.userId != userId || app.thread == null || app.unlocked) continue; 11210 11211 final int NG = app.pkgList.size(); 11212 for (int ig = 0; ig < NG; ig++) { 11213 try { 11214 final String pkgName = app.pkgList.keyAt(ig); 11215 final PackageInfo pkgInfo = AppGlobals.getPackageManager() 11216 .getPackageInfo(pkgName, matchFlags, userId); 11217 if (pkgInfo != null && !ArrayUtils.isEmpty(pkgInfo.providers)) { 11218 for (ProviderInfo pi : pkgInfo.providers) { 11219 // TODO: keep in sync with generateApplicationProvidersLocked 11220 final boolean processMatch = Objects.equals(pi.processName, 11221 app.processName) || pi.multiprocess; 11222 final boolean userMatch = isSingleton(pi.processName, 11223 pi.applicationInfo, pi.name, pi.flags) 11224 ? (app.userId == UserHandle.USER_SYSTEM) : true; 11225 if (processMatch && userMatch) { 11226 Log.v(TAG, "Installing " + pi); 11227 app.thread.scheduleInstallProvider(pi); 11228 } else { 11229 Log.v(TAG, "Skipping " + pi); 11230 } 11231 } 11232 } 11233 } catch (RemoteException ignored) { 11234 } 11235 } 11236 } 11237 } 11238 } 11239 } 11240 11241 /** 11242 * Allows apps to retrieve the MIME type of a URI. 11243 * If an app is in the same user as the ContentProvider, or if it is allowed to interact across 11244 * users, then it does not need permission to access the ContentProvider. 11245 * Either, it needs cross-user uri grants. 11246 * 11247 * CTS tests for this functionality can be run with "runtest cts-appsecurity". 11248 * 11249 * Test cases are at cts/tests/appsecurity-tests/test-apps/UsePermissionDiffCert/ 11250 * src/com/android/cts/usespermissiondiffcertapp/AccessPermissionWithDiffSigTest.java 11251 */ 11252 public String getProviderMimeType(Uri uri, int userId) { 11253 enforceNotIsolatedCaller("getProviderMimeType"); 11254 final String name = uri.getAuthority(); 11255 int callingUid = Binder.getCallingUid(); 11256 int callingPid = Binder.getCallingPid(); 11257 long ident = 0; 11258 boolean clearedIdentity = false; 11259 synchronized (this) { 11260 userId = mUserController.unsafeConvertIncomingUserLocked(userId); 11261 } 11262 if (canClearIdentity(callingPid, callingUid, userId)) { 11263 clearedIdentity = true; 11264 ident = Binder.clearCallingIdentity(); 11265 } 11266 ContentProviderHolder holder = null; 11267 try { 11268 holder = getContentProviderExternalUnchecked(name, null, userId); 11269 if (holder != null) { 11270 return holder.provider.getType(uri); 11271 } 11272 } catch (RemoteException e) { 11273 Log.w(TAG, "Content provider dead retrieving " + uri, e); 11274 return null; 11275 } catch (Exception e) { 11276 Log.w(TAG, "Exception while determining type of " + uri, e); 11277 return null; 11278 } finally { 11279 // We need to clear the identity to call removeContentProviderExternalUnchecked 11280 if (!clearedIdentity) { 11281 ident = Binder.clearCallingIdentity(); 11282 } 11283 try { 11284 if (holder != null) { 11285 removeContentProviderExternalUnchecked(name, null, userId); 11286 } 11287 } finally { 11288 Binder.restoreCallingIdentity(ident); 11289 } 11290 } 11291 11292 return null; 11293 } 11294 11295 private boolean canClearIdentity(int callingPid, int callingUid, int userId) { 11296 if (UserHandle.getUserId(callingUid) == userId) { 11297 return true; 11298 } 11299 if (checkComponentPermission(INTERACT_ACROSS_USERS, callingPid, 11300 callingUid, -1, true) == PackageManager.PERMISSION_GRANTED 11301 || checkComponentPermission(INTERACT_ACROSS_USERS_FULL, callingPid, 11302 callingUid, -1, true) == PackageManager.PERMISSION_GRANTED) { 11303 return true; 11304 } 11305 return false; 11306 } 11307 11308 // ========================================================= 11309 // GLOBAL MANAGEMENT 11310 // ========================================================= 11311 11312 final ProcessRecord newProcessRecordLocked(ApplicationInfo info, String customProcess, 11313 boolean isolated, int isolatedUid) { 11314 String proc = customProcess != null ? customProcess : info.processName; 11315 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 11316 final int userId = UserHandle.getUserId(info.uid); 11317 int uid = info.uid; 11318 if (isolated) { 11319 if (isolatedUid == 0) { 11320 int stepsLeft = Process.LAST_ISOLATED_UID - Process.FIRST_ISOLATED_UID + 1; 11321 while (true) { 11322 if (mNextIsolatedProcessUid < Process.FIRST_ISOLATED_UID 11323 || mNextIsolatedProcessUid > Process.LAST_ISOLATED_UID) { 11324 mNextIsolatedProcessUid = Process.FIRST_ISOLATED_UID; 11325 } 11326 uid = UserHandle.getUid(userId, mNextIsolatedProcessUid); 11327 mNextIsolatedProcessUid++; 11328 if (mIsolatedProcesses.indexOfKey(uid) < 0) { 11329 // No process for this uid, use it. 11330 break; 11331 } 11332 stepsLeft--; 11333 if (stepsLeft <= 0) { 11334 return null; 11335 } 11336 } 11337 } else { 11338 // Special case for startIsolatedProcess (internal only), where 11339 // the uid of the isolated process is specified by the caller. 11340 uid = isolatedUid; 11341 } 11342 11343 // Register the isolated UID with this application so BatteryStats knows to 11344 // attribute resource usage to the application. 11345 // 11346 // NOTE: This is done here before addProcessNameLocked, which will tell BatteryStats 11347 // about the process state of the isolated UID *before* it is registered with the 11348 // owning application. 11349 mBatteryStatsService.addIsolatedUid(uid, info.uid); 11350 } 11351 final ProcessRecord r = new ProcessRecord(stats, info, proc, uid); 11352 if (!mBooted && !mBooting 11353 && userId == UserHandle.USER_SYSTEM 11354 && (info.flags & PERSISTENT_MASK) == PERSISTENT_MASK) { 11355 r.persistent = true; 11356 r.maxAdj = ProcessList.PERSISTENT_PROC_ADJ; 11357 } 11358 addProcessNameLocked(r); 11359 return r; 11360 } 11361 11362 final ProcessRecord addAppLocked(ApplicationInfo info, boolean isolated, 11363 String abiOverride) { 11364 ProcessRecord app; 11365 if (!isolated) { 11366 app = getProcessRecordLocked(info.processName, info.uid, true); 11367 } else { 11368 app = null; 11369 } 11370 11371 if (app == null) { 11372 app = newProcessRecordLocked(info, null, isolated, 0); 11373 updateLruProcessLocked(app, false, null); 11374 updateOomAdjLocked(); 11375 } 11376 11377 // This package really, really can not be stopped. 11378 try { 11379 AppGlobals.getPackageManager().setPackageStoppedState( 11380 info.packageName, false, UserHandle.getUserId(app.uid)); 11381 } catch (RemoteException e) { 11382 } catch (IllegalArgumentException e) { 11383 Slog.w(TAG, "Failed trying to unstop package " 11384 + info.packageName + ": " + e); 11385 } 11386 11387 if ((info.flags & PERSISTENT_MASK) == PERSISTENT_MASK) { 11388 app.persistent = true; 11389 app.maxAdj = ProcessList.PERSISTENT_PROC_ADJ; 11390 } 11391 if (app.thread == null && mPersistentStartingProcesses.indexOf(app) < 0) { 11392 mPersistentStartingProcesses.add(app); 11393 startProcessLocked(app, "added application", app.processName, abiOverride, 11394 null /* entryPoint */, null /* entryPointArgs */); 11395 } 11396 11397 return app; 11398 } 11399 11400 public void unhandledBack() { 11401 enforceCallingPermission(android.Manifest.permission.FORCE_BACK, 11402 "unhandledBack()"); 11403 11404 synchronized(this) { 11405 final long origId = Binder.clearCallingIdentity(); 11406 try { 11407 getFocusedStack().unhandledBackLocked(); 11408 } finally { 11409 Binder.restoreCallingIdentity(origId); 11410 } 11411 } 11412 } 11413 11414 public ParcelFileDescriptor openContentUri(String uriString) throws RemoteException { 11415 enforceNotIsolatedCaller("openContentUri"); 11416 final int userId = UserHandle.getCallingUserId(); 11417 final Uri uri = Uri.parse(uriString); 11418 String name = uri.getAuthority(); 11419 ContentProviderHolder cph = getContentProviderExternalUnchecked(name, null, userId); 11420 ParcelFileDescriptor pfd = null; 11421 if (cph != null) { 11422 // We record the binder invoker's uid in thread-local storage before 11423 // going to the content provider to open the file. Later, in the code 11424 // that handles all permissions checks, we look for this uid and use 11425 // that rather than the Activity Manager's own uid. The effect is that 11426 // we do the check against the caller's permissions even though it looks 11427 // to the content provider like the Activity Manager itself is making 11428 // the request. 11429 Binder token = new Binder(); 11430 sCallerIdentity.set(new Identity( 11431 token, Binder.getCallingPid(), Binder.getCallingUid())); 11432 try { 11433 pfd = cph.provider.openFile(null, uri, "r", null, token); 11434 } catch (FileNotFoundException e) { 11435 // do nothing; pfd will be returned null 11436 } finally { 11437 // Ensure that whatever happens, we clean up the identity state 11438 sCallerIdentity.remove(); 11439 // Ensure we're done with the provider. 11440 removeContentProviderExternalUnchecked(name, null, userId); 11441 } 11442 } else { 11443 Slog.d(TAG, "Failed to get provider for authority '" + name + "'"); 11444 } 11445 return pfd; 11446 } 11447 11448 // Actually is sleeping or shutting down or whatever else in the future 11449 // is an inactive state. 11450 boolean isSleepingOrShuttingDownLocked() { 11451 return isSleepingLocked() || mShuttingDown; 11452 } 11453 11454 boolean isShuttingDownLocked() { 11455 return mShuttingDown; 11456 } 11457 11458 boolean isSleepingLocked() { 11459 return mSleeping; 11460 } 11461 11462 void onWakefulnessChanged(int wakefulness) { 11463 synchronized(this) { 11464 mWakefulness = wakefulness; 11465 updateSleepIfNeededLocked(); 11466 } 11467 } 11468 11469 void finishRunningVoiceLocked() { 11470 if (mRunningVoice != null) { 11471 mRunningVoice = null; 11472 mVoiceWakeLock.release(); 11473 updateSleepIfNeededLocked(); 11474 } 11475 } 11476 11477 void startTimeTrackingFocusedActivityLocked() { 11478 final ActivityRecord resumedActivity = mStackSupervisor.getResumedActivityLocked(); 11479 if (!mSleeping && mCurAppTimeTracker != null && resumedActivity != null) { 11480 mCurAppTimeTracker.start(resumedActivity.packageName); 11481 } 11482 } 11483 11484 void updateSleepIfNeededLocked() { 11485 if (mSleeping && !shouldSleepLocked()) { 11486 mSleeping = false; 11487 startTimeTrackingFocusedActivityLocked(); 11488 mTopProcessState = ActivityManager.PROCESS_STATE_TOP; 11489 mStackSupervisor.comeOutOfSleepIfNeededLocked(); 11490 updateOomAdjLocked(); 11491 } else if (!mSleeping && shouldSleepLocked()) { 11492 mSleeping = true; 11493 if (mCurAppTimeTracker != null) { 11494 mCurAppTimeTracker.stop(); 11495 } 11496 mTopProcessState = ActivityManager.PROCESS_STATE_TOP_SLEEPING; 11497 mStackSupervisor.goingToSleepLocked(); 11498 updateOomAdjLocked(); 11499 11500 // Initialize the wake times of all processes. 11501 checkExcessivePowerUsageLocked(false); 11502 mHandler.removeMessages(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 11503 Message nmsg = mHandler.obtainMessage(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 11504 mHandler.sendMessageDelayed(nmsg, POWER_CHECK_DELAY); 11505 } 11506 } 11507 11508 private boolean shouldSleepLocked() { 11509 // Resume applications while running a voice interactor. 11510 if (mRunningVoice != null) { 11511 return false; 11512 } 11513 11514 // TODO: Transform the lock screen state into a sleep token instead. 11515 switch (mWakefulness) { 11516 case PowerManagerInternal.WAKEFULNESS_AWAKE: 11517 case PowerManagerInternal.WAKEFULNESS_DREAMING: 11518 case PowerManagerInternal.WAKEFULNESS_DOZING: 11519 // Pause applications whenever the lock screen is shown or any sleep 11520 // tokens have been acquired. 11521 return mKeyguardController.isKeyguardShowing() || !mSleepTokens.isEmpty(); 11522 case PowerManagerInternal.WAKEFULNESS_ASLEEP: 11523 default: 11524 // If we're asleep then pause applications unconditionally. 11525 return true; 11526 } 11527 } 11528 11529 /** Pokes the task persister. */ 11530 void notifyTaskPersisterLocked(TaskRecord task, boolean flush) { 11531 mRecentTasks.notifyTaskPersisterLocked(task, flush); 11532 } 11533 11534 /** Notifies all listeners when the pinned stack animation ends. */ 11535 @Override 11536 public void notifyPinnedStackAnimationEnded() { 11537 mTaskChangeNotificationController.notifyPinnedStackAnimationEnded(); 11538 } 11539 11540 @Override 11541 public void notifyCleartextNetwork(int uid, byte[] firstPacket) { 11542 mHandler.obtainMessage(NOTIFY_CLEARTEXT_NETWORK_MSG, uid, 0, firstPacket).sendToTarget(); 11543 } 11544 11545 @Override 11546 public boolean shutdown(int timeout) { 11547 if (checkCallingPermission(android.Manifest.permission.SHUTDOWN) 11548 != PackageManager.PERMISSION_GRANTED) { 11549 throw new SecurityException("Requires permission " 11550 + android.Manifest.permission.SHUTDOWN); 11551 } 11552 11553 boolean timedout = false; 11554 11555 synchronized(this) { 11556 mShuttingDown = true; 11557 updateEventDispatchingLocked(); 11558 timedout = mStackSupervisor.shutdownLocked(timeout); 11559 } 11560 11561 mAppOpsService.shutdown(); 11562 if (mUsageStatsService != null) { 11563 mUsageStatsService.prepareShutdown(); 11564 } 11565 mBatteryStatsService.shutdown(); 11566 synchronized (this) { 11567 mProcessStats.shutdownLocked(); 11568 notifyTaskPersisterLocked(null, true); 11569 } 11570 11571 return timedout; 11572 } 11573 11574 public final void activitySlept(IBinder token) { 11575 if (DEBUG_ALL) Slog.v(TAG, "Activity slept: token=" + token); 11576 11577 final long origId = Binder.clearCallingIdentity(); 11578 11579 synchronized (this) { 11580 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 11581 if (r != null) { 11582 mStackSupervisor.activitySleptLocked(r); 11583 } 11584 } 11585 11586 Binder.restoreCallingIdentity(origId); 11587 } 11588 11589 void startRunningVoiceLocked(IVoiceInteractionSession session, int targetUid) { 11590 Slog.d(TAG, "<<< startRunningVoiceLocked()"); 11591 mVoiceWakeLock.setWorkSource(new WorkSource(targetUid)); 11592 if (mRunningVoice == null || mRunningVoice.asBinder() != session.asBinder()) { 11593 boolean wasRunningVoice = mRunningVoice != null; 11594 mRunningVoice = session; 11595 if (!wasRunningVoice) { 11596 mVoiceWakeLock.acquire(); 11597 updateSleepIfNeededLocked(); 11598 } 11599 } 11600 } 11601 11602 private void updateEventDispatchingLocked() { 11603 mWindowManager.setEventDispatching(mBooted && !mShuttingDown); 11604 } 11605 11606 @Override 11607 public void setLockScreenShown(boolean showing) { 11608 if (checkCallingPermission(android.Manifest.permission.DEVICE_POWER) 11609 != PackageManager.PERMISSION_GRANTED) { 11610 throw new SecurityException("Requires permission " 11611 + android.Manifest.permission.DEVICE_POWER); 11612 } 11613 11614 synchronized(this) { 11615 long ident = Binder.clearCallingIdentity(); 11616 try { 11617 mKeyguardController.setKeyguardShown(showing); 11618 } finally { 11619 Binder.restoreCallingIdentity(ident); 11620 } 11621 } 11622 } 11623 11624 @Override 11625 public void notifyLockedProfile(@UserIdInt int userId) { 11626 try { 11627 if (!AppGlobals.getPackageManager().isUidPrivileged(Binder.getCallingUid())) { 11628 throw new SecurityException("Only privileged app can call notifyLockedProfile"); 11629 } 11630 } catch (RemoteException ex) { 11631 throw new SecurityException("Fail to check is caller a privileged app", ex); 11632 } 11633 11634 synchronized (this) { 11635 if (mStackSupervisor.isUserLockedProfile(userId)) { 11636 final long ident = Binder.clearCallingIdentity(); 11637 try { 11638 final int currentUserId = mUserController.getCurrentUserIdLocked(); 11639 if (mUserController.isLockScreenDisabled(currentUserId)) { 11640 // If there is no device lock, we will show the profile's credential page. 11641 mActivityStarter.showConfirmDeviceCredential(userId); 11642 } else { 11643 // Showing launcher to avoid user entering credential twice. 11644 startHomeActivityLocked(currentUserId, "notifyLockedProfile"); 11645 } 11646 } finally { 11647 Binder.restoreCallingIdentity(ident); 11648 } 11649 } 11650 } 11651 } 11652 11653 @Override 11654 public void startConfirmDeviceCredentialIntent(Intent intent) { 11655 enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "startConfirmDeviceCredentialIntent"); 11656 synchronized (this) { 11657 final long ident = Binder.clearCallingIdentity(); 11658 try { 11659 mActivityStarter.startConfirmCredentialIntent(intent); 11660 } finally { 11661 Binder.restoreCallingIdentity(ident); 11662 } 11663 } 11664 } 11665 11666 @Override 11667 public void stopAppSwitches() { 11668 if (checkCallingPermission(android.Manifest.permission.STOP_APP_SWITCHES) 11669 != PackageManager.PERMISSION_GRANTED) { 11670 throw new SecurityException("viewquires permission " 11671 + android.Manifest.permission.STOP_APP_SWITCHES); 11672 } 11673 11674 synchronized(this) { 11675 mAppSwitchesAllowedTime = SystemClock.uptimeMillis() 11676 + APP_SWITCH_DELAY_TIME; 11677 mDidAppSwitch = false; 11678 mHandler.removeMessages(DO_PENDING_ACTIVITY_LAUNCHES_MSG); 11679 Message msg = mHandler.obtainMessage(DO_PENDING_ACTIVITY_LAUNCHES_MSG); 11680 mHandler.sendMessageDelayed(msg, APP_SWITCH_DELAY_TIME); 11681 } 11682 } 11683 11684 public void resumeAppSwitches() { 11685 if (checkCallingPermission(android.Manifest.permission.STOP_APP_SWITCHES) 11686 != PackageManager.PERMISSION_GRANTED) { 11687 throw new SecurityException("Requires permission " 11688 + android.Manifest.permission.STOP_APP_SWITCHES); 11689 } 11690 11691 synchronized(this) { 11692 // Note that we don't execute any pending app switches... we will 11693 // let those wait until either the timeout, or the next start 11694 // activity request. 11695 mAppSwitchesAllowedTime = 0; 11696 } 11697 } 11698 11699 boolean checkAppSwitchAllowedLocked(int sourcePid, int sourceUid, 11700 int callingPid, int callingUid, String name) { 11701 if (mAppSwitchesAllowedTime < SystemClock.uptimeMillis()) { 11702 return true; 11703 } 11704 11705 int perm = checkComponentPermission( 11706 android.Manifest.permission.STOP_APP_SWITCHES, sourcePid, 11707 sourceUid, -1, true); 11708 if (perm == PackageManager.PERMISSION_GRANTED) { 11709 return true; 11710 } 11711 11712 // If the actual IPC caller is different from the logical source, then 11713 // also see if they are allowed to control app switches. 11714 if (callingUid != -1 && callingUid != sourceUid) { 11715 perm = checkComponentPermission( 11716 android.Manifest.permission.STOP_APP_SWITCHES, callingPid, 11717 callingUid, -1, true); 11718 if (perm == PackageManager.PERMISSION_GRANTED) { 11719 return true; 11720 } 11721 } 11722 11723 Slog.w(TAG, name + " request from " + sourceUid + " stopped"); 11724 return false; 11725 } 11726 11727 public void setDebugApp(String packageName, boolean waitForDebugger, 11728 boolean persistent) { 11729 enforceCallingPermission(android.Manifest.permission.SET_DEBUG_APP, 11730 "setDebugApp()"); 11731 11732 long ident = Binder.clearCallingIdentity(); 11733 try { 11734 // Note that this is not really thread safe if there are multiple 11735 // callers into it at the same time, but that's not a situation we 11736 // care about. 11737 if (persistent) { 11738 final ContentResolver resolver = mContext.getContentResolver(); 11739 Settings.Global.putString( 11740 resolver, Settings.Global.DEBUG_APP, 11741 packageName); 11742 Settings.Global.putInt( 11743 resolver, Settings.Global.WAIT_FOR_DEBUGGER, 11744 waitForDebugger ? 1 : 0); 11745 } 11746 11747 synchronized (this) { 11748 if (!persistent) { 11749 mOrigDebugApp = mDebugApp; 11750 mOrigWaitForDebugger = mWaitForDebugger; 11751 } 11752 mDebugApp = packageName; 11753 mWaitForDebugger = waitForDebugger; 11754 mDebugTransient = !persistent; 11755 if (packageName != null) { 11756 forceStopPackageLocked(packageName, -1, false, false, true, true, 11757 false, UserHandle.USER_ALL, "set debug app"); 11758 } 11759 } 11760 } finally { 11761 Binder.restoreCallingIdentity(ident); 11762 } 11763 } 11764 11765 void setTrackAllocationApp(ApplicationInfo app, String processName) { 11766 synchronized (this) { 11767 boolean isDebuggable = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 11768 if (!isDebuggable) { 11769 if ((app.flags & ApplicationInfo.FLAG_DEBUGGABLE) == 0) { 11770 throw new SecurityException("Process not debuggable: " + app.packageName); 11771 } 11772 } 11773 11774 mTrackAllocationApp = processName; 11775 } 11776 } 11777 11778 void setProfileApp(ApplicationInfo app, String processName, ProfilerInfo profilerInfo) { 11779 synchronized (this) { 11780 boolean isDebuggable = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 11781 if (!isDebuggable) { 11782 if ((app.flags & ApplicationInfo.FLAG_DEBUGGABLE) == 0) { 11783 throw new SecurityException("Process not debuggable: " + app.packageName); 11784 } 11785 } 11786 mProfileApp = processName; 11787 mProfileFile = profilerInfo.profileFile; 11788 if (mProfileFd != null) { 11789 try { 11790 mProfileFd.close(); 11791 } catch (IOException e) { 11792 } 11793 mProfileFd = null; 11794 } 11795 mProfileFd = profilerInfo.profileFd; 11796 mSamplingInterval = profilerInfo.samplingInterval; 11797 mAutoStopProfiler = profilerInfo.autoStopProfiler; 11798 mProfileType = 0; 11799 } 11800 } 11801 11802 void setNativeDebuggingAppLocked(ApplicationInfo app, String processName) { 11803 boolean isDebuggable = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 11804 if (!isDebuggable) { 11805 if ((app.flags & ApplicationInfo.FLAG_DEBUGGABLE) == 0) { 11806 throw new SecurityException("Process not debuggable: " + app.packageName); 11807 } 11808 } 11809 mNativeDebuggingApp = processName; 11810 } 11811 11812 @Override 11813 public void setAlwaysFinish(boolean enabled) { 11814 enforceCallingPermission(android.Manifest.permission.SET_ALWAYS_FINISH, 11815 "setAlwaysFinish()"); 11816 11817 long ident = Binder.clearCallingIdentity(); 11818 try { 11819 Settings.Global.putInt( 11820 mContext.getContentResolver(), 11821 Settings.Global.ALWAYS_FINISH_ACTIVITIES, enabled ? 1 : 0); 11822 11823 synchronized (this) { 11824 mAlwaysFinishActivities = enabled; 11825 } 11826 } finally { 11827 Binder.restoreCallingIdentity(ident); 11828 } 11829 } 11830 11831 @Override 11832 public void setLenientBackgroundCheck(boolean enabled) { 11833 enforceCallingPermission(android.Manifest.permission.SET_PROCESS_LIMIT, 11834 "setLenientBackgroundCheck()"); 11835 11836 long ident = Binder.clearCallingIdentity(); 11837 try { 11838 Settings.Global.putInt( 11839 mContext.getContentResolver(), 11840 Settings.Global.LENIENT_BACKGROUND_CHECK, enabled ? 1 : 0); 11841 11842 synchronized (this) { 11843 mLenientBackgroundCheck = enabled; 11844 } 11845 } finally { 11846 Binder.restoreCallingIdentity(ident); 11847 } 11848 } 11849 11850 @Override 11851 public void setActivityController(IActivityController controller, boolean imAMonkey) { 11852 enforceCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER, 11853 "setActivityController()"); 11854 synchronized (this) { 11855 mController = controller; 11856 mControllerIsAMonkey = imAMonkey; 11857 Watchdog.getInstance().setActivityController(controller); 11858 } 11859 } 11860 11861 @Override 11862 public void setUserIsMonkey(boolean userIsMonkey) { 11863 synchronized (this) { 11864 synchronized (mPidsSelfLocked) { 11865 final int callingPid = Binder.getCallingPid(); 11866 ProcessRecord precessRecord = mPidsSelfLocked.get(callingPid); 11867 if (precessRecord == null) { 11868 throw new SecurityException("Unknown process: " + callingPid); 11869 } 11870 if (precessRecord.instrumentationUiAutomationConnection == null) { 11871 throw new SecurityException("Only an instrumentation process " 11872 + "with a UiAutomation can call setUserIsMonkey"); 11873 } 11874 } 11875 mUserIsMonkey = userIsMonkey; 11876 } 11877 } 11878 11879 @Override 11880 public boolean isUserAMonkey() { 11881 synchronized (this) { 11882 // If there is a controller also implies the user is a monkey. 11883 return (mUserIsMonkey || (mController != null && mControllerIsAMonkey)); 11884 } 11885 } 11886 11887 public void requestBugReport(int bugreportType) { 11888 String extraOptions = null; 11889 switch (bugreportType) { 11890 case ActivityManager.BUGREPORT_OPTION_FULL: 11891 // Default options. 11892 break; 11893 case ActivityManager.BUGREPORT_OPTION_INTERACTIVE: 11894 extraOptions = "bugreportplus"; 11895 break; 11896 case ActivityManager.BUGREPORT_OPTION_REMOTE: 11897 extraOptions = "bugreportremote"; 11898 break; 11899 case ActivityManager.BUGREPORT_OPTION_WEAR: 11900 extraOptions = "bugreportwear"; 11901 break; 11902 default: 11903 throw new IllegalArgumentException("Provided bugreport type is not correct, value: " 11904 + bugreportType); 11905 } 11906 enforceCallingPermission(android.Manifest.permission.DUMP, "requestBugReport"); 11907 if (extraOptions != null) { 11908 SystemProperties.set("dumpstate.options", extraOptions); 11909 } 11910 SystemProperties.set("ctl.start", "bugreport"); 11911 } 11912 11913 public static long getInputDispatchingTimeoutLocked(ActivityRecord r) { 11914 return r != null ? getInputDispatchingTimeoutLocked(r.app) : KEY_DISPATCHING_TIMEOUT; 11915 } 11916 11917 public static long getInputDispatchingTimeoutLocked(ProcessRecord r) { 11918 if (r != null && (r.instrumentationClass != null || r.usingWrapper)) { 11919 return INSTRUMENTATION_KEY_DISPATCHING_TIMEOUT; 11920 } 11921 return KEY_DISPATCHING_TIMEOUT; 11922 } 11923 11924 @Override 11925 public long inputDispatchingTimedOut(int pid, final boolean aboveSystem, String reason) { 11926 if (checkCallingPermission(android.Manifest.permission.FILTER_EVENTS) 11927 != PackageManager.PERMISSION_GRANTED) { 11928 throw new SecurityException("Requires permission " 11929 + android.Manifest.permission.FILTER_EVENTS); 11930 } 11931 ProcessRecord proc; 11932 long timeout; 11933 synchronized (this) { 11934 synchronized (mPidsSelfLocked) { 11935 proc = mPidsSelfLocked.get(pid); 11936 } 11937 timeout = getInputDispatchingTimeoutLocked(proc); 11938 } 11939 11940 if (!inputDispatchingTimedOut(proc, null, null, aboveSystem, reason)) { 11941 return -1; 11942 } 11943 11944 return timeout; 11945 } 11946 11947 /** 11948 * Handle input dispatching timeouts. 11949 * Returns whether input dispatching should be aborted or not. 11950 */ 11951 public boolean inputDispatchingTimedOut(final ProcessRecord proc, 11952 final ActivityRecord activity, final ActivityRecord parent, 11953 final boolean aboveSystem, String reason) { 11954 if (checkCallingPermission(android.Manifest.permission.FILTER_EVENTS) 11955 != PackageManager.PERMISSION_GRANTED) { 11956 throw new SecurityException("Requires permission " 11957 + android.Manifest.permission.FILTER_EVENTS); 11958 } 11959 11960 final String annotation; 11961 if (reason == null) { 11962 annotation = "Input dispatching timed out"; 11963 } else { 11964 annotation = "Input dispatching timed out (" + reason + ")"; 11965 } 11966 11967 if (proc != null) { 11968 synchronized (this) { 11969 if (proc.debugging) { 11970 return false; 11971 } 11972 11973 if (mDidDexOpt) { 11974 // Give more time since we were dexopting. 11975 mDidDexOpt = false; 11976 return false; 11977 } 11978 11979 if (proc.instrumentationClass != null) { 11980 Bundle info = new Bundle(); 11981 info.putString("shortMsg", "keyDispatchingTimedOut"); 11982 info.putString("longMsg", annotation); 11983 finishInstrumentationLocked(proc, Activity.RESULT_CANCELED, info); 11984 return true; 11985 } 11986 } 11987 mHandler.post(new Runnable() { 11988 @Override 11989 public void run() { 11990 mAppErrors.appNotResponding(proc, activity, parent, aboveSystem, annotation); 11991 } 11992 }); 11993 } 11994 11995 return true; 11996 } 11997 11998 @Override 11999 public Bundle getAssistContextExtras(int requestType) { 12000 PendingAssistExtras pae = enqueueAssistContext(requestType, null, null, null, 12001 null, null, true /* focused */, true /* newSessionId */, 12002 UserHandle.getCallingUserId(), null, PENDING_ASSIST_EXTRAS_TIMEOUT); 12003 if (pae == null) { 12004 return null; 12005 } 12006 synchronized (pae) { 12007 while (!pae.haveResult) { 12008 try { 12009 pae.wait(); 12010 } catch (InterruptedException e) { 12011 } 12012 } 12013 } 12014 synchronized (this) { 12015 buildAssistBundleLocked(pae, pae.result); 12016 mPendingAssistExtras.remove(pae); 12017 mUiHandler.removeCallbacks(pae); 12018 } 12019 return pae.extras; 12020 } 12021 12022 @Override 12023 public boolean isAssistDataAllowedOnCurrentActivity() { 12024 int userId; 12025 synchronized (this) { 12026 userId = mUserController.getCurrentUserIdLocked(); 12027 ActivityRecord activity = getFocusedStack().topActivity(); 12028 if (activity == null) { 12029 return false; 12030 } 12031 userId = activity.userId; 12032 } 12033 DevicePolicyManager dpm = (DevicePolicyManager) mContext.getSystemService( 12034 Context.DEVICE_POLICY_SERVICE); 12035 return (dpm == null) || (!dpm.getScreenCaptureDisabled(null, userId)); 12036 } 12037 12038 @Override 12039 public boolean showAssistFromActivity(IBinder token, Bundle args) { 12040 long ident = Binder.clearCallingIdentity(); 12041 try { 12042 synchronized (this) { 12043 ActivityRecord caller = ActivityRecord.forTokenLocked(token); 12044 ActivityRecord top = getFocusedStack().topActivity(); 12045 if (top != caller) { 12046 Slog.w(TAG, "showAssistFromActivity failed: caller " + caller 12047 + " is not current top " + top); 12048 return false; 12049 } 12050 if (!top.nowVisible) { 12051 Slog.w(TAG, "showAssistFromActivity failed: caller " + caller 12052 + " is not visible"); 12053 return false; 12054 } 12055 } 12056 AssistUtils utils = new AssistUtils(mContext); 12057 return utils.showSessionForActiveService(args, 12058 VoiceInteractionSession.SHOW_SOURCE_APPLICATION, null, token); 12059 } finally { 12060 Binder.restoreCallingIdentity(ident); 12061 } 12062 } 12063 12064 @Override 12065 public boolean requestAssistContextExtras(int requestType, IResultReceiver receiver, 12066 Bundle receiverExtras, 12067 IBinder activityToken, boolean focused, boolean newSessionId) { 12068 return enqueueAssistContext(requestType, null, null, receiver, receiverExtras, 12069 activityToken, focused, newSessionId, 12070 UserHandle.getCallingUserId(), null, PENDING_ASSIST_EXTRAS_LONG_TIMEOUT) 12071 != null; 12072 } 12073 12074 private PendingAssistExtras enqueueAssistContext(int requestType, Intent intent, String hint, 12075 IResultReceiver receiver, Bundle receiverExtras, IBinder activityToken, 12076 boolean focused, boolean newSessionId, int userHandle, Bundle args, long timeout) { 12077 enforceCallingPermission(android.Manifest.permission.GET_TOP_ACTIVITY_INFO, 12078 "enqueueAssistContext()"); 12079 synchronized (this) { 12080 ActivityRecord activity = getFocusedStack().topActivity(); 12081 if (activity == null) { 12082 Slog.w(TAG, "getAssistContextExtras failed: no top activity"); 12083 return null; 12084 } 12085 if (activity.app == null || activity.app.thread == null) { 12086 Slog.w(TAG, "getAssistContextExtras failed: no process for " + activity); 12087 return null; 12088 } 12089 if (focused) { 12090 if (activityToken != null) { 12091 ActivityRecord caller = ActivityRecord.forTokenLocked(activityToken); 12092 if (activity != caller) { 12093 Slog.w(TAG, "enqueueAssistContext failed: caller " + caller 12094 + " is not current top " + activity); 12095 return null; 12096 } 12097 } 12098 } else { 12099 activity = ActivityRecord.forTokenLocked(activityToken); 12100 if (activity == null) { 12101 Slog.w(TAG, "enqueueAssistContext failed: activity for token=" + activityToken 12102 + " couldn't be found"); 12103 return null; 12104 } 12105 } 12106 12107 PendingAssistExtras pae; 12108 Bundle extras = new Bundle(); 12109 if (args != null) { 12110 extras.putAll(args); 12111 } 12112 extras.putString(Intent.EXTRA_ASSIST_PACKAGE, activity.packageName); 12113 extras.putInt(Intent.EXTRA_ASSIST_UID, activity.app.uid); 12114 pae = new PendingAssistExtras(activity, extras, intent, hint, receiver, receiverExtras, 12115 userHandle); 12116 // Increment the sessionId if necessary 12117 if (newSessionId) { 12118 mViSessionId++; 12119 } 12120 try { 12121 activity.app.thread.requestAssistContextExtras(activity.appToken, pae, 12122 requestType, mViSessionId); 12123 mPendingAssistExtras.add(pae); 12124 mUiHandler.postDelayed(pae, timeout); 12125 } catch (RemoteException e) { 12126 Slog.w(TAG, "getAssistContextExtras failed: crash calling " + activity); 12127 return null; 12128 } 12129 return pae; 12130 } 12131 } 12132 12133 void pendingAssistExtrasTimedOut(PendingAssistExtras pae) { 12134 IResultReceiver receiver; 12135 synchronized (this) { 12136 mPendingAssistExtras.remove(pae); 12137 receiver = pae.receiver; 12138 } 12139 if (receiver != null) { 12140 // Caller wants result sent back to them. 12141 Bundle sendBundle = new Bundle(); 12142 // At least return the receiver extras 12143 sendBundle.putBundle(VoiceInteractionSession.KEY_RECEIVER_EXTRAS, 12144 pae.receiverExtras); 12145 try { 12146 pae.receiver.send(0, sendBundle); 12147 } catch (RemoteException e) { 12148 } 12149 } 12150 } 12151 12152 private void buildAssistBundleLocked(PendingAssistExtras pae, Bundle result) { 12153 if (result != null) { 12154 pae.extras.putBundle(Intent.EXTRA_ASSIST_CONTEXT, result); 12155 } 12156 if (pae.hint != null) { 12157 pae.extras.putBoolean(pae.hint, true); 12158 } 12159 } 12160 12161 public void reportAssistContextExtras(IBinder token, Bundle extras, AssistStructure structure, 12162 AssistContent content, Uri referrer) { 12163 PendingAssistExtras pae = (PendingAssistExtras)token; 12164 synchronized (pae) { 12165 pae.result = extras; 12166 pae.structure = structure; 12167 pae.content = content; 12168 if (referrer != null) { 12169 pae.extras.putParcelable(Intent.EXTRA_REFERRER, referrer); 12170 } 12171 pae.haveResult = true; 12172 pae.notifyAll(); 12173 if (pae.intent == null && pae.receiver == null) { 12174 // Caller is just waiting for the result. 12175 return; 12176 } 12177 } 12178 12179 // We are now ready to launch the assist activity. 12180 IResultReceiver sendReceiver = null; 12181 Bundle sendBundle = null; 12182 synchronized (this) { 12183 buildAssistBundleLocked(pae, extras); 12184 boolean exists = mPendingAssistExtras.remove(pae); 12185 mUiHandler.removeCallbacks(pae); 12186 if (!exists) { 12187 // Timed out. 12188 return; 12189 } 12190 if ((sendReceiver=pae.receiver) != null) { 12191 // Caller wants result sent back to them. 12192 sendBundle = new Bundle(); 12193 sendBundle.putBundle(VoiceInteractionSession.KEY_DATA, pae.extras); 12194 sendBundle.putParcelable(VoiceInteractionSession.KEY_STRUCTURE, pae.structure); 12195 sendBundle.putParcelable(VoiceInteractionSession.KEY_CONTENT, pae.content); 12196 sendBundle.putBundle(VoiceInteractionSession.KEY_RECEIVER_EXTRAS, 12197 pae.receiverExtras); 12198 } 12199 } 12200 if (sendReceiver != null) { 12201 try { 12202 sendReceiver.send(0, sendBundle); 12203 } catch (RemoteException e) { 12204 } 12205 return; 12206 } 12207 12208 long ident = Binder.clearCallingIdentity(); 12209 try { 12210 pae.intent.replaceExtras(pae.extras); 12211 pae.intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK 12212 | Intent.FLAG_ACTIVITY_SINGLE_TOP 12213 | Intent.FLAG_ACTIVITY_CLEAR_TOP); 12214 closeSystemDialogs("assist"); 12215 try { 12216 mContext.startActivityAsUser(pae.intent, new UserHandle(pae.userHandle)); 12217 } catch (ActivityNotFoundException e) { 12218 Slog.w(TAG, "No activity to handle assist action.", e); 12219 } 12220 } finally { 12221 Binder.restoreCallingIdentity(ident); 12222 } 12223 } 12224 12225 public boolean launchAssistIntent(Intent intent, int requestType, String hint, int userHandle, 12226 Bundle args) { 12227 return enqueueAssistContext(requestType, intent, hint, null, null, null, 12228 true /* focused */, true /* newSessionId */, 12229 userHandle, args, PENDING_ASSIST_EXTRAS_TIMEOUT) != null; 12230 } 12231 12232 public void registerProcessObserver(IProcessObserver observer) { 12233 enforceCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER, 12234 "registerProcessObserver()"); 12235 synchronized (this) { 12236 mProcessObservers.register(observer); 12237 } 12238 } 12239 12240 @Override 12241 public void unregisterProcessObserver(IProcessObserver observer) { 12242 synchronized (this) { 12243 mProcessObservers.unregister(observer); 12244 } 12245 } 12246 12247 @Override 12248 public void registerUidObserver(IUidObserver observer, int which, String callingPackage) { 12249 if (!hasUsageStatsPermission(callingPackage)) { 12250 enforceCallingPermission(android.Manifest.permission.PACKAGE_USAGE_STATS, 12251 "registerUidObserver"); 12252 } 12253 synchronized (this) { 12254 mUidObservers.register(observer, which); 12255 } 12256 } 12257 12258 @Override 12259 public void unregisterUidObserver(IUidObserver observer) { 12260 synchronized (this) { 12261 mUidObservers.unregister(observer); 12262 } 12263 } 12264 12265 @Override 12266 public boolean convertFromTranslucent(IBinder token) { 12267 final long origId = Binder.clearCallingIdentity(); 12268 try { 12269 synchronized (this) { 12270 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 12271 if (r == null) { 12272 return false; 12273 } 12274 final boolean translucentChanged = r.changeWindowTranslucency(true); 12275 if (translucentChanged) { 12276 r.getStack().releaseBackgroundResources(r); 12277 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0, !PRESERVE_WINDOWS); 12278 } 12279 mWindowManager.setAppFullscreen(token, true); 12280 return translucentChanged; 12281 } 12282 } finally { 12283 Binder.restoreCallingIdentity(origId); 12284 } 12285 } 12286 12287 @Override 12288 public boolean convertToTranslucent(IBinder token, Bundle options) { 12289 final long origId = Binder.clearCallingIdentity(); 12290 try { 12291 synchronized (this) { 12292 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 12293 if (r == null) { 12294 return false; 12295 } 12296 int index = r.task.mActivities.lastIndexOf(r); 12297 if (index > 0) { 12298 ActivityRecord under = r.task.mActivities.get(index - 1); 12299 under.returningOptions = ActivityOptions.fromBundle(options); 12300 } 12301 final boolean translucentChanged = r.changeWindowTranslucency(false); 12302 if (translucentChanged) { 12303 r.getStack().convertActivityToTranslucent(r); 12304 } 12305 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0, !PRESERVE_WINDOWS); 12306 mWindowManager.setAppFullscreen(token, false); 12307 return translucentChanged; 12308 } 12309 } finally { 12310 Binder.restoreCallingIdentity(origId); 12311 } 12312 } 12313 12314 @Override 12315 public boolean requestVisibleBehind(IBinder token, boolean visible) { 12316 final long origId = Binder.clearCallingIdentity(); 12317 try { 12318 synchronized (this) { 12319 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 12320 if (r != null) { 12321 return mStackSupervisor.requestVisibleBehindLocked(r, visible); 12322 } 12323 } 12324 return false; 12325 } finally { 12326 Binder.restoreCallingIdentity(origId); 12327 } 12328 } 12329 12330 @Override 12331 public boolean isBackgroundVisibleBehind(IBinder token) { 12332 final long origId = Binder.clearCallingIdentity(); 12333 try { 12334 synchronized (this) { 12335 final ActivityStack stack = ActivityRecord.getStackLocked(token); 12336 final boolean visible = stack == null ? false : stack.hasVisibleBehindActivity(); 12337 if (DEBUG_VISIBLE_BEHIND) Slog.d(TAG_VISIBLE_BEHIND, 12338 "isBackgroundVisibleBehind: stack=" + stack + " visible=" + visible); 12339 return visible; 12340 } 12341 } finally { 12342 Binder.restoreCallingIdentity(origId); 12343 } 12344 } 12345 12346 @Override 12347 public Bundle getActivityOptions(IBinder token) { 12348 final long origId = Binder.clearCallingIdentity(); 12349 try { 12350 synchronized (this) { 12351 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 12352 if (r != null) { 12353 final ActivityOptions activityOptions = r.pendingOptions; 12354 r.pendingOptions = null; 12355 return activityOptions == null ? null : activityOptions.toBundle(); 12356 } 12357 return null; 12358 } 12359 } finally { 12360 Binder.restoreCallingIdentity(origId); 12361 } 12362 } 12363 12364 @Override 12365 public void setImmersive(IBinder token, boolean immersive) { 12366 synchronized(this) { 12367 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 12368 if (r == null) { 12369 throw new IllegalArgumentException(); 12370 } 12371 r.immersive = immersive; 12372 12373 // update associated state if we're frontmost 12374 if (r == mStackSupervisor.getResumedActivityLocked()) { 12375 if (DEBUG_IMMERSIVE) Slog.d(TAG_IMMERSIVE, "Frontmost changed immersion: "+ r); 12376 applyUpdateLockStateLocked(r); 12377 } 12378 } 12379 } 12380 12381 @Override 12382 public boolean isImmersive(IBinder token) { 12383 synchronized (this) { 12384 ActivityRecord r = ActivityRecord.isInStackLocked(token); 12385 if (r == null) { 12386 throw new IllegalArgumentException(); 12387 } 12388 return r.immersive; 12389 } 12390 } 12391 12392 public void setVrThread(int tid) { 12393 if (!mContext.getPackageManager().hasSystemFeature(PackageManager.FEATURE_VR_MODE)) { 12394 throw new UnsupportedOperationException("VR mode not supported on this device!"); 12395 } 12396 12397 synchronized (this) { 12398 ProcessRecord proc; 12399 synchronized (mPidsSelfLocked) { 12400 final int pid = Binder.getCallingPid(); 12401 proc = mPidsSelfLocked.get(pid); 12402 12403 if (proc != null && mInVrMode && tid >= 0) { 12404 // ensure the tid belongs to the process 12405 if (!Process.isThreadInProcess(pid, tid)) { 12406 throw new IllegalArgumentException("VR thread does not belong to process"); 12407 } 12408 12409 // reset existing VR thread to CFS if this thread still exists and belongs to 12410 // the calling process 12411 if (proc.vrThreadTid != 0 12412 && Process.isThreadInProcess(pid, proc.vrThreadTid)) { 12413 try { 12414 Process.setThreadScheduler(proc.vrThreadTid, Process.SCHED_OTHER, 0); 12415 } catch (IllegalArgumentException e) { 12416 // Ignore this. Only occurs in race condition where previous VR thread 12417 // was destroyed during this method call. 12418 } 12419 } 12420 12421 proc.vrThreadTid = tid; 12422 12423 // promote to FIFO now if the tid is non-zero 12424 try { 12425 if (proc.curSchedGroup == ProcessList.SCHED_GROUP_TOP_APP && 12426 proc.vrThreadTid > 0) { 12427 Process.setThreadScheduler(proc.vrThreadTid, 12428 Process.SCHED_FIFO | Process.SCHED_RESET_ON_FORK, 1); 12429 } 12430 } catch (IllegalArgumentException e) { 12431 Slog.e(TAG, "Failed to set scheduling policy, thread does" 12432 + " not exist:\n" + e); 12433 } 12434 } 12435 } 12436 } 12437 } 12438 12439 @Override 12440 public void setRenderThread(int tid) { 12441 synchronized (this) { 12442 ProcessRecord proc; 12443 synchronized (mPidsSelfLocked) { 12444 int pid = Binder.getCallingPid(); 12445 proc = mPidsSelfLocked.get(pid); 12446 if (proc != null && proc.renderThreadTid == 0 && tid > 0) { 12447 // ensure the tid belongs to the process 12448 if (!Process.isThreadInProcess(pid, tid)) { 12449 throw new IllegalArgumentException( 12450 "Render thread does not belong to process"); 12451 } 12452 proc.renderThreadTid = tid; 12453 if (DEBUG_OOM_ADJ) { 12454 Slog.d("UI_FIFO", "Set RenderThread tid " + tid + " for pid " + pid); 12455 } 12456 // promote to FIFO now 12457 if (proc.curSchedGroup == ProcessList.SCHED_GROUP_TOP_APP) { 12458 if (DEBUG_OOM_ADJ) Slog.d("UI_FIFO", "Promoting " + tid + "out of band"); 12459 if (mUseFifoUiScheduling) { 12460 Process.setThreadScheduler(proc.renderThreadTid, 12461 Process.SCHED_FIFO | Process.SCHED_RESET_ON_FORK, 1); 12462 } else { 12463 Process.setThreadPriority(proc.renderThreadTid, -10); 12464 } 12465 } 12466 } else { 12467 if (DEBUG_OOM_ADJ) { 12468 Slog.d("UI_FIFO", "Didn't set thread from setRenderThread? " + 12469 "PID: " + pid + ", TID: " + tid + " FIFO: " + 12470 mUseFifoUiScheduling); 12471 } 12472 } 12473 } 12474 } 12475 } 12476 12477 @Override 12478 public int setVrMode(IBinder token, boolean enabled, ComponentName packageName) { 12479 if (!mContext.getPackageManager().hasSystemFeature(PackageManager.FEATURE_VR_MODE)) { 12480 throw new UnsupportedOperationException("VR mode not supported on this device!"); 12481 } 12482 12483 final VrManagerInternal vrService = LocalServices.getService(VrManagerInternal.class); 12484 12485 ActivityRecord r; 12486 synchronized (this) { 12487 r = ActivityRecord.isInStackLocked(token); 12488 } 12489 12490 if (r == null) { 12491 throw new IllegalArgumentException(); 12492 } 12493 12494 int err; 12495 if ((err = vrService.hasVrPackage(packageName, r.userId)) != 12496 VrManagerInternal.NO_ERROR) { 12497 return err; 12498 } 12499 12500 synchronized(this) { 12501 r.requestedVrComponent = (enabled) ? packageName : null; 12502 12503 // Update associated state if this activity is currently focused 12504 if (r == mStackSupervisor.getResumedActivityLocked()) { 12505 applyUpdateVrModeLocked(r); 12506 } 12507 return 0; 12508 } 12509 } 12510 12511 @Override 12512 public boolean isVrModePackageEnabled(ComponentName packageName) { 12513 if (!mContext.getPackageManager().hasSystemFeature(PackageManager.FEATURE_VR_MODE)) { 12514 throw new UnsupportedOperationException("VR mode not supported on this device!"); 12515 } 12516 12517 final VrManagerInternal vrService = LocalServices.getService(VrManagerInternal.class); 12518 12519 return vrService.hasVrPackage(packageName, UserHandle.getCallingUserId()) == 12520 VrManagerInternal.NO_ERROR; 12521 } 12522 12523 public boolean isTopActivityImmersive() { 12524 enforceNotIsolatedCaller("startActivity"); 12525 synchronized (this) { 12526 ActivityRecord r = getFocusedStack().topRunningActivityLocked(); 12527 return (r != null) ? r.immersive : false; 12528 } 12529 } 12530 12531 @Override 12532 public boolean isTopOfTask(IBinder token) { 12533 synchronized (this) { 12534 ActivityRecord r = ActivityRecord.isInStackLocked(token); 12535 if (r == null) { 12536 throw new IllegalArgumentException(); 12537 } 12538 return r.task.getTopActivity() == r; 12539 } 12540 } 12541 12542 @Override 12543 public void setHasTopUi(boolean hasTopUi) throws RemoteException { 12544 if (checkCallingPermission(permission.INTERNAL_SYSTEM_WINDOW) != PERMISSION_GRANTED) { 12545 String msg = "Permission Denial: setHasTopUi() from pid=" 12546 + Binder.getCallingPid() 12547 + ", uid=" + Binder.getCallingUid() 12548 + " requires " + permission.INTERNAL_SYSTEM_WINDOW; 12549 Slog.w(TAG, msg); 12550 throw new SecurityException(msg); 12551 } 12552 final int pid = Binder.getCallingPid(); 12553 final long origId = Binder.clearCallingIdentity(); 12554 try { 12555 synchronized (this) { 12556 boolean changed = false; 12557 ProcessRecord pr; 12558 synchronized (mPidsSelfLocked) { 12559 pr = mPidsSelfLocked.get(pid); 12560 if (pr == null) { 12561 Slog.w(TAG, "setHasTopUi called on unknown pid: " + pid); 12562 return; 12563 } 12564 if (pr.hasTopUi != hasTopUi) { 12565 Slog.i(TAG, "Setting hasTopUi=" + hasTopUi + " for pid=" + pid); 12566 pr.hasTopUi = hasTopUi; 12567 changed = true; 12568 } 12569 } 12570 if (changed) { 12571 updateOomAdjLocked(pr); 12572 } 12573 } 12574 } finally { 12575 Binder.restoreCallingIdentity(origId); 12576 } 12577 } 12578 12579 public final void enterSafeMode() { 12580 synchronized(this) { 12581 // It only makes sense to do this before the system is ready 12582 // and started launching other packages. 12583 if (!mSystemReady) { 12584 try { 12585 AppGlobals.getPackageManager().enterSafeMode(); 12586 } catch (RemoteException e) { 12587 } 12588 } 12589 12590 mSafeMode = true; 12591 } 12592 } 12593 12594 public final void showSafeModeOverlay() { 12595 View v = LayoutInflater.from(mContext).inflate( 12596 com.android.internal.R.layout.safe_mode, null); 12597 WindowManager.LayoutParams lp = new WindowManager.LayoutParams(); 12598 lp.type = WindowManager.LayoutParams.TYPE_SECURE_SYSTEM_OVERLAY; 12599 lp.width = WindowManager.LayoutParams.WRAP_CONTENT; 12600 lp.height = WindowManager.LayoutParams.WRAP_CONTENT; 12601 lp.gravity = Gravity.BOTTOM | Gravity.START; 12602 lp.format = v.getBackground().getOpacity(); 12603 lp.flags = WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE 12604 | WindowManager.LayoutParams.FLAG_NOT_TOUCHABLE; 12605 lp.privateFlags |= WindowManager.LayoutParams.PRIVATE_FLAG_SHOW_FOR_ALL_USERS; 12606 ((WindowManager)mContext.getSystemService( 12607 Context.WINDOW_SERVICE)).addView(v, lp); 12608 } 12609 12610 public void noteWakeupAlarm(IIntentSender sender, int sourceUid, String sourcePkg, String tag) { 12611 if (sender != null && !(sender instanceof PendingIntentRecord)) { 12612 return; 12613 } 12614 final PendingIntentRecord rec = (PendingIntentRecord)sender; 12615 final BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 12616 synchronized (stats) { 12617 if (mBatteryStatsService.isOnBattery()) { 12618 mBatteryStatsService.enforceCallingPermission(); 12619 int MY_UID = Binder.getCallingUid(); 12620 final int uid; 12621 if (sender == null) { 12622 uid = sourceUid; 12623 } else { 12624 uid = rec.uid == MY_UID ? Process.SYSTEM_UID : rec.uid; 12625 } 12626 BatteryStatsImpl.Uid.Pkg pkg = 12627 stats.getPackageStatsLocked(sourceUid >= 0 ? sourceUid : uid, 12628 sourcePkg != null ? sourcePkg : rec.key.packageName); 12629 pkg.noteWakeupAlarmLocked(tag); 12630 } 12631 } 12632 } 12633 12634 public void noteAlarmStart(IIntentSender sender, int sourceUid, String tag) { 12635 if (sender != null && !(sender instanceof PendingIntentRecord)) { 12636 return; 12637 } 12638 final PendingIntentRecord rec = (PendingIntentRecord)sender; 12639 final BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 12640 synchronized (stats) { 12641 mBatteryStatsService.enforceCallingPermission(); 12642 int MY_UID = Binder.getCallingUid(); 12643 final int uid; 12644 if (sender == null) { 12645 uid = sourceUid; 12646 } else { 12647 uid = rec.uid == MY_UID ? Process.SYSTEM_UID : rec.uid; 12648 } 12649 mBatteryStatsService.noteAlarmStart(tag, sourceUid >= 0 ? sourceUid : uid); 12650 } 12651 } 12652 12653 public void noteAlarmFinish(IIntentSender sender, int sourceUid, String tag) { 12654 if (sender != null && !(sender instanceof PendingIntentRecord)) { 12655 return; 12656 } 12657 final PendingIntentRecord rec = (PendingIntentRecord)sender; 12658 final BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 12659 synchronized (stats) { 12660 mBatteryStatsService.enforceCallingPermission(); 12661 int MY_UID = Binder.getCallingUid(); 12662 final int uid; 12663 if (sender == null) { 12664 uid = sourceUid; 12665 } else { 12666 uid = rec.uid == MY_UID ? Process.SYSTEM_UID : rec.uid; 12667 } 12668 mBatteryStatsService.noteAlarmFinish(tag, sourceUid >= 0 ? sourceUid : uid); 12669 } 12670 } 12671 12672 public boolean killPids(int[] pids, String pReason, boolean secure) { 12673 if (Binder.getCallingUid() != Process.SYSTEM_UID) { 12674 throw new SecurityException("killPids only available to the system"); 12675 } 12676 String reason = (pReason == null) ? "Unknown" : pReason; 12677 // XXX Note: don't acquire main activity lock here, because the window 12678 // manager calls in with its locks held. 12679 12680 boolean killed = false; 12681 synchronized (mPidsSelfLocked) { 12682 int worstType = 0; 12683 for (int i=0; i<pids.length; i++) { 12684 ProcessRecord proc = mPidsSelfLocked.get(pids[i]); 12685 if (proc != null) { 12686 int type = proc.setAdj; 12687 if (type > worstType) { 12688 worstType = type; 12689 } 12690 } 12691 } 12692 12693 // If the worst oom_adj is somewhere in the cached proc LRU range, 12694 // then constrain it so we will kill all cached procs. 12695 if (worstType < ProcessList.CACHED_APP_MAX_ADJ 12696 && worstType > ProcessList.CACHED_APP_MIN_ADJ) { 12697 worstType = ProcessList.CACHED_APP_MIN_ADJ; 12698 } 12699 12700 // If this is not a secure call, don't let it kill processes that 12701 // are important. 12702 if (!secure && worstType < ProcessList.SERVICE_ADJ) { 12703 worstType = ProcessList.SERVICE_ADJ; 12704 } 12705 12706 Slog.w(TAG, "Killing processes " + reason + " at adjustment " + worstType); 12707 for (int i=0; i<pids.length; i++) { 12708 ProcessRecord proc = mPidsSelfLocked.get(pids[i]); 12709 if (proc == null) { 12710 continue; 12711 } 12712 int adj = proc.setAdj; 12713 if (adj >= worstType && !proc.killedByAm) { 12714 proc.kill(reason, true); 12715 killed = true; 12716 } 12717 } 12718 } 12719 return killed; 12720 } 12721 12722 @Override 12723 public void killUid(int appId, int userId, String reason) { 12724 enforceCallingPermission(Manifest.permission.KILL_UID, "killUid"); 12725 synchronized (this) { 12726 final long identity = Binder.clearCallingIdentity(); 12727 try { 12728 killPackageProcessesLocked(null, appId, userId, 12729 ProcessList.PERSISTENT_PROC_ADJ, false, true, true, true, 12730 reason != null ? reason : "kill uid"); 12731 } finally { 12732 Binder.restoreCallingIdentity(identity); 12733 } 12734 } 12735 } 12736 12737 @Override 12738 public boolean killProcessesBelowForeground(String reason) { 12739 if (Binder.getCallingUid() != Process.SYSTEM_UID) { 12740 throw new SecurityException("killProcessesBelowForeground() only available to system"); 12741 } 12742 12743 return killProcessesBelowAdj(ProcessList.FOREGROUND_APP_ADJ, reason); 12744 } 12745 12746 private boolean killProcessesBelowAdj(int belowAdj, String reason) { 12747 if (Binder.getCallingUid() != Process.SYSTEM_UID) { 12748 throw new SecurityException("killProcessesBelowAdj() only available to system"); 12749 } 12750 12751 boolean killed = false; 12752 synchronized (mPidsSelfLocked) { 12753 final int size = mPidsSelfLocked.size(); 12754 for (int i = 0; i < size; i++) { 12755 final int pid = mPidsSelfLocked.keyAt(i); 12756 final ProcessRecord proc = mPidsSelfLocked.valueAt(i); 12757 if (proc == null) continue; 12758 12759 final int adj = proc.setAdj; 12760 if (adj > belowAdj && !proc.killedByAm) { 12761 proc.kill(reason, true); 12762 killed = true; 12763 } 12764 } 12765 } 12766 return killed; 12767 } 12768 12769 @Override 12770 public void hang(final IBinder who, boolean allowRestart) { 12771 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 12772 != PackageManager.PERMISSION_GRANTED) { 12773 throw new SecurityException("Requires permission " 12774 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 12775 } 12776 12777 final IBinder.DeathRecipient death = new DeathRecipient() { 12778 @Override 12779 public void binderDied() { 12780 synchronized (this) { 12781 notifyAll(); 12782 } 12783 } 12784 }; 12785 12786 try { 12787 who.linkToDeath(death, 0); 12788 } catch (RemoteException e) { 12789 Slog.w(TAG, "hang: given caller IBinder is already dead."); 12790 return; 12791 } 12792 12793 synchronized (this) { 12794 Watchdog.getInstance().setAllowRestart(allowRestart); 12795 Slog.i(TAG, "Hanging system process at request of pid " + Binder.getCallingPid()); 12796 synchronized (death) { 12797 while (who.isBinderAlive()) { 12798 try { 12799 death.wait(); 12800 } catch (InterruptedException e) { 12801 } 12802 } 12803 } 12804 Watchdog.getInstance().setAllowRestart(true); 12805 } 12806 } 12807 12808 @Override 12809 public void restart() { 12810 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 12811 != PackageManager.PERMISSION_GRANTED) { 12812 throw new SecurityException("Requires permission " 12813 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 12814 } 12815 12816 Log.i(TAG, "Sending shutdown broadcast..."); 12817 12818 BroadcastReceiver br = new BroadcastReceiver() { 12819 @Override public void onReceive(Context context, Intent intent) { 12820 // Now the broadcast is done, finish up the low-level shutdown. 12821 Log.i(TAG, "Shutting down activity manager..."); 12822 shutdown(10000); 12823 Log.i(TAG, "Shutdown complete, restarting!"); 12824 Process.killProcess(Process.myPid()); 12825 System.exit(10); 12826 } 12827 }; 12828 12829 // First send the high-level shut down broadcast. 12830 Intent intent = new Intent(Intent.ACTION_SHUTDOWN); 12831 intent.addFlags(Intent.FLAG_RECEIVER_FOREGROUND); 12832 intent.putExtra(Intent.EXTRA_SHUTDOWN_USERSPACE_ONLY, true); 12833 /* For now we are not doing a clean shutdown, because things seem to get unhappy. 12834 mContext.sendOrderedBroadcastAsUser(intent, 12835 UserHandle.ALL, null, br, mHandler, 0, null, null); 12836 */ 12837 br.onReceive(mContext, intent); 12838 } 12839 12840 private long getLowRamTimeSinceIdle(long now) { 12841 return mLowRamTimeSinceLastIdle + (mLowRamStartTime > 0 ? (now-mLowRamStartTime) : 0); 12842 } 12843 12844 @Override 12845 public void performIdleMaintenance() { 12846 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 12847 != PackageManager.PERMISSION_GRANTED) { 12848 throw new SecurityException("Requires permission " 12849 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 12850 } 12851 12852 synchronized (this) { 12853 final long now = SystemClock.uptimeMillis(); 12854 final long timeSinceLastIdle = now - mLastIdleTime; 12855 final long lowRamSinceLastIdle = getLowRamTimeSinceIdle(now); 12856 mLastIdleTime = now; 12857 mLowRamTimeSinceLastIdle = 0; 12858 if (mLowRamStartTime != 0) { 12859 mLowRamStartTime = now; 12860 } 12861 12862 StringBuilder sb = new StringBuilder(128); 12863 sb.append("Idle maintenance over "); 12864 TimeUtils.formatDuration(timeSinceLastIdle, sb); 12865 sb.append(" low RAM for "); 12866 TimeUtils.formatDuration(lowRamSinceLastIdle, sb); 12867 Slog.i(TAG, sb.toString()); 12868 12869 // If at least 1/3 of our time since the last idle period has been spent 12870 // with RAM low, then we want to kill processes. 12871 boolean doKilling = lowRamSinceLastIdle > (timeSinceLastIdle/3); 12872 12873 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 12874 ProcessRecord proc = mLruProcesses.get(i); 12875 if (proc.notCachedSinceIdle) { 12876 if (proc.setProcState != ActivityManager.PROCESS_STATE_TOP_SLEEPING 12877 && proc.setProcState >= ActivityManager.PROCESS_STATE_FOREGROUND_SERVICE 12878 && proc.setProcState <= ActivityManager.PROCESS_STATE_SERVICE) { 12879 if (doKilling && proc.initialIdlePss != 0 12880 && proc.lastPss > ((proc.initialIdlePss*3)/2)) { 12881 sb = new StringBuilder(128); 12882 sb.append("Kill"); 12883 sb.append(proc.processName); 12884 sb.append(" in idle maint: pss="); 12885 sb.append(proc.lastPss); 12886 sb.append(", swapPss="); 12887 sb.append(proc.lastSwapPss); 12888 sb.append(", initialPss="); 12889 sb.append(proc.initialIdlePss); 12890 sb.append(", period="); 12891 TimeUtils.formatDuration(timeSinceLastIdle, sb); 12892 sb.append(", lowRamPeriod="); 12893 TimeUtils.formatDuration(lowRamSinceLastIdle, sb); 12894 Slog.wtfQuiet(TAG, sb.toString()); 12895 proc.kill("idle maint (pss " + proc.lastPss 12896 + " from " + proc.initialIdlePss + ")", true); 12897 } 12898 } 12899 } else if (proc.setProcState < ActivityManager.PROCESS_STATE_HOME 12900 && proc.setProcState > ActivityManager.PROCESS_STATE_NONEXISTENT) { 12901 proc.notCachedSinceIdle = true; 12902 proc.initialIdlePss = 0; 12903 proc.nextPssTime = ProcessList.computeNextPssTime(proc.setProcState, true, 12904 mTestPssMode, isSleepingLocked(), now); 12905 } 12906 } 12907 12908 mHandler.removeMessages(REQUEST_ALL_PSS_MSG); 12909 mHandler.sendEmptyMessageDelayed(REQUEST_ALL_PSS_MSG, 2*60*1000); 12910 } 12911 } 12912 12913 @Override 12914 public void sendIdleJobTrigger() { 12915 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 12916 != PackageManager.PERMISSION_GRANTED) { 12917 throw new SecurityException("Requires permission " 12918 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 12919 } 12920 12921 final long ident = Binder.clearCallingIdentity(); 12922 try { 12923 Intent intent = new Intent(ACTION_TRIGGER_IDLE) 12924 .setPackage("android") 12925 .addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 12926 broadcastIntent(null, intent, null, null, 0, null, null, null, 12927 android.app.AppOpsManager.OP_NONE, null, true, false, UserHandle.USER_ALL); 12928 } finally { 12929 Binder.restoreCallingIdentity(ident); 12930 } 12931 } 12932 12933 private void retrieveSettings() { 12934 final ContentResolver resolver = mContext.getContentResolver(); 12935 final boolean freeformWindowManagement = 12936 mContext.getPackageManager().hasSystemFeature(FEATURE_FREEFORM_WINDOW_MANAGEMENT) 12937 || Settings.Global.getInt( 12938 resolver, DEVELOPMENT_ENABLE_FREEFORM_WINDOWS_SUPPORT, 0) != 0; 12939 final boolean supportsPictureInPicture = 12940 mContext.getPackageManager().hasSystemFeature(FEATURE_PICTURE_IN_PICTURE); 12941 12942 final boolean supportsMultiWindow = ActivityManager.supportsMultiWindow(); 12943 final String debugApp = Settings.Global.getString(resolver, DEBUG_APP); 12944 final boolean waitForDebugger = Settings.Global.getInt(resolver, WAIT_FOR_DEBUGGER, 0) != 0; 12945 final boolean alwaysFinishActivities = 12946 Settings.Global.getInt(resolver, ALWAYS_FINISH_ACTIVITIES, 0) != 0; 12947 final boolean lenientBackgroundCheck = 12948 Settings.Global.getInt(resolver, LENIENT_BACKGROUND_CHECK, 0) != 0; 12949 final boolean forceRtl = Settings.Global.getInt(resolver, DEVELOPMENT_FORCE_RTL, 0) != 0; 12950 final boolean forceResizable = Settings.Global.getInt( 12951 resolver, DEVELOPMENT_FORCE_RESIZABLE_ACTIVITIES, 0) != 0; 12952 final boolean supportsLeanbackOnly = 12953 mContext.getPackageManager().hasSystemFeature(FEATURE_LEANBACK_ONLY); 12954 12955 // Transfer any global setting for forcing RTL layout, into a System Property 12956 SystemProperties.set(DEVELOPMENT_FORCE_RTL, forceRtl ? "1":"0"); 12957 12958 final Configuration configuration = new Configuration(); 12959 Settings.System.getConfiguration(resolver, configuration); 12960 if (forceRtl) { 12961 // This will take care of setting the correct layout direction flags 12962 configuration.setLayoutDirection(configuration.locale); 12963 } 12964 12965 synchronized (this) { 12966 mDebugApp = mOrigDebugApp = debugApp; 12967 mWaitForDebugger = mOrigWaitForDebugger = waitForDebugger; 12968 mAlwaysFinishActivities = alwaysFinishActivities; 12969 mLenientBackgroundCheck = lenientBackgroundCheck; 12970 mSupportsLeanbackOnly = supportsLeanbackOnly; 12971 mForceResizableActivities = forceResizable; 12972 if (supportsMultiWindow || forceResizable) { 12973 mSupportsMultiWindow = true; 12974 mSupportsFreeformWindowManagement = freeformWindowManagement || forceResizable; 12975 mSupportsPictureInPicture = supportsPictureInPicture || forceResizable; 12976 } else { 12977 mSupportsMultiWindow = false; 12978 mSupportsFreeformWindowManagement = false; 12979 mSupportsPictureInPicture = false; 12980 } 12981 mWindowManager.setForceResizableTasks(mForceResizableActivities); 12982 mWindowManager.setSupportsPictureInPicture(mSupportsPictureInPicture); 12983 // This happens before any activities are started, so we can change global configuration 12984 // in-place. 12985 updateConfigurationLocked(configuration, null, true); 12986 final Configuration globalConfig = getGlobalConfiguration(); 12987 if (DEBUG_CONFIGURATION) Slog.v(TAG_CONFIGURATION, "Initial config: " + globalConfig); 12988 12989 // Load resources only after the current configuration has been set. 12990 final Resources res = mContext.getResources(); 12991 mHasRecents = res.getBoolean(com.android.internal.R.bool.config_hasRecents); 12992 mThumbnailWidth = res.getDimensionPixelSize( 12993 com.android.internal.R.dimen.thumbnail_width); 12994 mThumbnailHeight = res.getDimensionPixelSize( 12995 com.android.internal.R.dimen.thumbnail_height); 12996 mAppErrors.loadAppsNotReportingCrashesFromConfigLocked(res.getString( 12997 com.android.internal.R.string.config_appsNotReportingCrashes)); 12998 mUserController.mUserSwitchUiEnabled = !res.getBoolean( 12999 com.android.internal.R.bool.config_customUserSwitchUi); 13000 if ((globalConfig.uiMode & UI_MODE_TYPE_TELEVISION) == UI_MODE_TYPE_TELEVISION) { 13001 mFullscreenThumbnailScale = (float) res 13002 .getInteger(com.android.internal.R.integer.thumbnail_width_tv) / 13003 (float) globalConfig.screenWidthDp; 13004 } else { 13005 mFullscreenThumbnailScale = res.getFraction( 13006 com.android.internal.R.fraction.thumbnail_fullscreen_scale, 1, 1); 13007 } 13008 } 13009 } 13010 13011 public void systemReady(final Runnable goingCallback) { 13012 synchronized(this) { 13013 if (mSystemReady) { 13014 // If we're done calling all the receivers, run the next "boot phase" passed in 13015 // by the SystemServer 13016 if (goingCallback != null) { 13017 goingCallback.run(); 13018 } 13019 return; 13020 } 13021 13022 mLocalDeviceIdleController 13023 = LocalServices.getService(DeviceIdleController.LocalService.class); 13024 13025 // Make sure we have the current profile info, since it is needed for security checks. 13026 mUserController.onSystemReady(); 13027 mRecentTasks.onSystemReadyLocked(); 13028 mAppOpsService.systemReady(); 13029 mSystemReady = true; 13030 } 13031 13032 ArrayList<ProcessRecord> procsToKill = null; 13033 synchronized(mPidsSelfLocked) { 13034 for (int i=mPidsSelfLocked.size()-1; i>=0; i--) { 13035 ProcessRecord proc = mPidsSelfLocked.valueAt(i); 13036 if (!isAllowedWhileBooting(proc.info)){ 13037 if (procsToKill == null) { 13038 procsToKill = new ArrayList<ProcessRecord>(); 13039 } 13040 procsToKill.add(proc); 13041 } 13042 } 13043 } 13044 13045 synchronized(this) { 13046 if (procsToKill != null) { 13047 for (int i=procsToKill.size()-1; i>=0; i--) { 13048 ProcessRecord proc = procsToKill.get(i); 13049 Slog.i(TAG, "Removing system update proc: " + proc); 13050 removeProcessLocked(proc, true, false, "system update done"); 13051 } 13052 } 13053 13054 // Now that we have cleaned up any update processes, we 13055 // are ready to start launching real processes and know that 13056 // we won't trample on them any more. 13057 mProcessesReady = true; 13058 } 13059 13060 Slog.i(TAG, "System now ready"); 13061 EventLog.writeEvent(EventLogTags.BOOT_PROGRESS_AMS_READY, 13062 SystemClock.uptimeMillis()); 13063 13064 synchronized(this) { 13065 // Make sure we have no pre-ready processes sitting around. 13066 13067 if (mFactoryTest == FactoryTest.FACTORY_TEST_LOW_LEVEL) { 13068 ResolveInfo ri = mContext.getPackageManager() 13069 .resolveActivity(new Intent(Intent.ACTION_FACTORY_TEST), 13070 STOCK_PM_FLAGS); 13071 CharSequence errorMsg = null; 13072 if (ri != null) { 13073 ActivityInfo ai = ri.activityInfo; 13074 ApplicationInfo app = ai.applicationInfo; 13075 if ((app.flags&ApplicationInfo.FLAG_SYSTEM) != 0) { 13076 mTopAction = Intent.ACTION_FACTORY_TEST; 13077 mTopData = null; 13078 mTopComponent = new ComponentName(app.packageName, 13079 ai.name); 13080 } else { 13081 errorMsg = mContext.getResources().getText( 13082 com.android.internal.R.string.factorytest_not_system); 13083 } 13084 } else { 13085 errorMsg = mContext.getResources().getText( 13086 com.android.internal.R.string.factorytest_no_action); 13087 } 13088 if (errorMsg != null) { 13089 mTopAction = null; 13090 mTopData = null; 13091 mTopComponent = null; 13092 Message msg = Message.obtain(); 13093 msg.what = SHOW_FACTORY_ERROR_UI_MSG; 13094 msg.getData().putCharSequence("msg", errorMsg); 13095 mUiHandler.sendMessage(msg); 13096 } 13097 } 13098 } 13099 13100 retrieveSettings(); 13101 final int currentUserId; 13102 synchronized (this) { 13103 currentUserId = mUserController.getCurrentUserIdLocked(); 13104 readGrantedUriPermissionsLocked(); 13105 } 13106 13107 if (goingCallback != null) goingCallback.run(); 13108 13109 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_USER_RUNNING_START, 13110 Integer.toString(currentUserId), currentUserId); 13111 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_USER_FOREGROUND_START, 13112 Integer.toString(currentUserId), currentUserId); 13113 mSystemServiceManager.startUser(currentUserId); 13114 13115 synchronized (this) { 13116 // Only start up encryption-aware persistent apps; once user is 13117 // unlocked we'll come back around and start unaware apps 13118 startPersistentApps(PackageManager.MATCH_DIRECT_BOOT_AWARE); 13119 13120 // Start up initial activity. 13121 mBooting = true; 13122 // Enable home activity for system user, so that the system can always boot. We don't 13123 // do this when the system user is not setup since the setup wizard should be the one 13124 // to handle home activity in this case. 13125 if (UserManager.isSplitSystemUser() && 13126 Settings.Secure.getInt(mContext.getContentResolver(), 13127 Settings.Secure.USER_SETUP_COMPLETE, 0) != 0) { 13128 ComponentName cName = new ComponentName(mContext, SystemUserHomeActivity.class); 13129 try { 13130 AppGlobals.getPackageManager().setComponentEnabledSetting(cName, 13131 PackageManager.COMPONENT_ENABLED_STATE_ENABLED, 0, 13132 UserHandle.USER_SYSTEM); 13133 } catch (RemoteException e) { 13134 throw e.rethrowAsRuntimeException(); 13135 } 13136 } 13137 startHomeActivityLocked(currentUserId, "systemReady"); 13138 13139 try { 13140 if (AppGlobals.getPackageManager().hasSystemUidErrors()) { 13141 Slog.e(TAG, "UIDs on the system are inconsistent, you need to wipe your" 13142 + " data partition or your device will be unstable."); 13143 mUiHandler.obtainMessage(SHOW_UID_ERROR_UI_MSG).sendToTarget(); 13144 } 13145 } catch (RemoteException e) { 13146 } 13147 13148 if (!Build.isBuildConsistent()) { 13149 Slog.e(TAG, "Build fingerprint is not consistent, warning user"); 13150 mUiHandler.obtainMessage(SHOW_FINGERPRINT_ERROR_UI_MSG).sendToTarget(); 13151 } 13152 13153 long ident = Binder.clearCallingIdentity(); 13154 try { 13155 Intent intent = new Intent(Intent.ACTION_USER_STARTED); 13156 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 13157 | Intent.FLAG_RECEIVER_FOREGROUND); 13158 intent.putExtra(Intent.EXTRA_USER_HANDLE, currentUserId); 13159 broadcastIntentLocked(null, null, intent, 13160 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 13161 null, false, false, MY_PID, Process.SYSTEM_UID, 13162 currentUserId); 13163 intent = new Intent(Intent.ACTION_USER_STARTING); 13164 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 13165 intent.putExtra(Intent.EXTRA_USER_HANDLE, currentUserId); 13166 broadcastIntentLocked(null, null, intent, 13167 null, new IIntentReceiver.Stub() { 13168 @Override 13169 public void performReceive(Intent intent, int resultCode, String data, 13170 Bundle extras, boolean ordered, boolean sticky, int sendingUser) 13171 throws RemoteException { 13172 } 13173 }, 0, null, null, 13174 new String[] {INTERACT_ACROSS_USERS}, AppOpsManager.OP_NONE, 13175 null, true, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 13176 } catch (Throwable t) { 13177 Slog.wtf(TAG, "Failed sending first user broadcasts", t); 13178 } finally { 13179 Binder.restoreCallingIdentity(ident); 13180 } 13181 mStackSupervisor.resumeFocusedStackTopActivityLocked(); 13182 mUserController.sendUserSwitchBroadcastsLocked(-1, currentUserId); 13183 } 13184 } 13185 13186 void killAppAtUsersRequest(ProcessRecord app, Dialog fromDialog) { 13187 synchronized (this) { 13188 mAppErrors.killAppAtUserRequestLocked(app, fromDialog); 13189 } 13190 } 13191 13192 void skipCurrentReceiverLocked(ProcessRecord app) { 13193 for (BroadcastQueue queue : mBroadcastQueues) { 13194 queue.skipCurrentReceiverLocked(app); 13195 } 13196 } 13197 13198 /** 13199 * Used by {@link com.android.internal.os.RuntimeInit} to report when an application crashes. 13200 * The application process will exit immediately after this call returns. 13201 * @param app object of the crashing app, null for the system server 13202 * @param crashInfo describing the exception 13203 */ 13204 public void handleApplicationCrash(IBinder app, 13205 ApplicationErrorReport.ParcelableCrashInfo crashInfo) { 13206 ProcessRecord r = findAppProcess(app, "Crash"); 13207 final String processName = app == null ? "system_server" 13208 : (r == null ? "unknown" : r.processName); 13209 13210 handleApplicationCrashInner("crash", r, processName, crashInfo); 13211 } 13212 13213 /* Native crash reporting uses this inner version because it needs to be somewhat 13214 * decoupled from the AM-managed cleanup lifecycle 13215 */ 13216 void handleApplicationCrashInner(String eventType, ProcessRecord r, String processName, 13217 ApplicationErrorReport.CrashInfo crashInfo) { 13218 EventLog.writeEvent(EventLogTags.AM_CRASH, Binder.getCallingPid(), 13219 UserHandle.getUserId(Binder.getCallingUid()), processName, 13220 r == null ? -1 : r.info.flags, 13221 crashInfo.exceptionClassName, 13222 crashInfo.exceptionMessage, 13223 crashInfo.throwFileName, 13224 crashInfo.throwLineNumber); 13225 13226 addErrorToDropBox(eventType, r, processName, null, null, null, null, null, crashInfo); 13227 13228 mAppErrors.crashApplication(r, crashInfo); 13229 } 13230 13231 public void handleApplicationStrictModeViolation( 13232 IBinder app, 13233 int violationMask, 13234 StrictMode.ViolationInfo info) { 13235 ProcessRecord r = findAppProcess(app, "StrictMode"); 13236 if (r == null) { 13237 return; 13238 } 13239 13240 if ((violationMask & StrictMode.PENALTY_DROPBOX) != 0) { 13241 Integer stackFingerprint = info.hashCode(); 13242 boolean logIt = true; 13243 synchronized (mAlreadyLoggedViolatedStacks) { 13244 if (mAlreadyLoggedViolatedStacks.contains(stackFingerprint)) { 13245 logIt = false; 13246 // TODO: sub-sample into EventLog for these, with 13247 // the info.durationMillis? Then we'd get 13248 // the relative pain numbers, without logging all 13249 // the stack traces repeatedly. We'd want to do 13250 // likewise in the client code, which also does 13251 // dup suppression, before the Binder call. 13252 } else { 13253 if (mAlreadyLoggedViolatedStacks.size() >= MAX_DUP_SUPPRESSED_STACKS) { 13254 mAlreadyLoggedViolatedStacks.clear(); 13255 } 13256 mAlreadyLoggedViolatedStacks.add(stackFingerprint); 13257 } 13258 } 13259 if (logIt) { 13260 logStrictModeViolationToDropBox(r, info); 13261 } 13262 } 13263 13264 if ((violationMask & StrictMode.PENALTY_DIALOG) != 0) { 13265 AppErrorResult result = new AppErrorResult(); 13266 synchronized (this) { 13267 final long origId = Binder.clearCallingIdentity(); 13268 13269 Message msg = Message.obtain(); 13270 msg.what = SHOW_STRICT_MODE_VIOLATION_UI_MSG; 13271 HashMap<String, Object> data = new HashMap<String, Object>(); 13272 data.put("result", result); 13273 data.put("app", r); 13274 data.put("violationMask", violationMask); 13275 data.put("info", info); 13276 msg.obj = data; 13277 mUiHandler.sendMessage(msg); 13278 13279 Binder.restoreCallingIdentity(origId); 13280 } 13281 int res = result.get(); 13282 Slog.w(TAG, "handleApplicationStrictModeViolation; res=" + res); 13283 } 13284 } 13285 13286 // Depending on the policy in effect, there could be a bunch of 13287 // these in quick succession so we try to batch these together to 13288 // minimize disk writes, number of dropbox entries, and maximize 13289 // compression, by having more fewer, larger records. 13290 private void logStrictModeViolationToDropBox( 13291 ProcessRecord process, 13292 StrictMode.ViolationInfo info) { 13293 if (info == null) { 13294 return; 13295 } 13296 final boolean isSystemApp = process == null || 13297 (process.info.flags & (ApplicationInfo.FLAG_SYSTEM | 13298 ApplicationInfo.FLAG_UPDATED_SYSTEM_APP)) != 0; 13299 final String processName = process == null ? "unknown" : process.processName; 13300 final String dropboxTag = isSystemApp ? "system_app_strictmode" : "data_app_strictmode"; 13301 final DropBoxManager dbox = (DropBoxManager) 13302 mContext.getSystemService(Context.DROPBOX_SERVICE); 13303 13304 // Exit early if the dropbox isn't configured to accept this report type. 13305 if (dbox == null || !dbox.isTagEnabled(dropboxTag)) return; 13306 13307 boolean bufferWasEmpty; 13308 boolean needsFlush; 13309 final StringBuilder sb = isSystemApp ? mStrictModeBuffer : new StringBuilder(1024); 13310 synchronized (sb) { 13311 bufferWasEmpty = sb.length() == 0; 13312 appendDropBoxProcessHeaders(process, processName, sb); 13313 sb.append("Build: ").append(Build.FINGERPRINT).append("\n"); 13314 sb.append("System-App: ").append(isSystemApp).append("\n"); 13315 sb.append("Uptime-Millis: ").append(info.violationUptimeMillis).append("\n"); 13316 if (info.violationNumThisLoop != 0) { 13317 sb.append("Loop-Violation-Number: ").append(info.violationNumThisLoop).append("\n"); 13318 } 13319 if (info.numAnimationsRunning != 0) { 13320 sb.append("Animations-Running: ").append(info.numAnimationsRunning).append("\n"); 13321 } 13322 if (info.broadcastIntentAction != null) { 13323 sb.append("Broadcast-Intent-Action: ").append(info.broadcastIntentAction).append("\n"); 13324 } 13325 if (info.durationMillis != -1) { 13326 sb.append("Duration-Millis: ").append(info.durationMillis).append("\n"); 13327 } 13328 if (info.numInstances != -1) { 13329 sb.append("Instance-Count: ").append(info.numInstances).append("\n"); 13330 } 13331 if (info.tags != null) { 13332 for (String tag : info.tags) { 13333 sb.append("Span-Tag: ").append(tag).append("\n"); 13334 } 13335 } 13336 sb.append("\n"); 13337 if (info.crashInfo != null && info.crashInfo.stackTrace != null) { 13338 sb.append(info.crashInfo.stackTrace); 13339 sb.append("\n"); 13340 } 13341 if (info.message != null) { 13342 sb.append(info.message); 13343 sb.append("\n"); 13344 } 13345 13346 // Only buffer up to ~64k. Various logging bits truncate 13347 // things at 128k. 13348 needsFlush = (sb.length() > 64 * 1024); 13349 } 13350 13351 // Flush immediately if the buffer's grown too large, or this 13352 // is a non-system app. Non-system apps are isolated with a 13353 // different tag & policy and not batched. 13354 // 13355 // Batching is useful during internal testing with 13356 // StrictMode settings turned up high. Without batching, 13357 // thousands of separate files could be created on boot. 13358 if (!isSystemApp || needsFlush) { 13359 new Thread("Error dump: " + dropboxTag) { 13360 @Override 13361 public void run() { 13362 String report; 13363 synchronized (sb) { 13364 report = sb.toString(); 13365 sb.delete(0, sb.length()); 13366 sb.trimToSize(); 13367 } 13368 if (report.length() != 0) { 13369 dbox.addText(dropboxTag, report); 13370 } 13371 } 13372 }.start(); 13373 return; 13374 } 13375 13376 // System app batching: 13377 if (!bufferWasEmpty) { 13378 // An existing dropbox-writing thread is outstanding, so 13379 // we don't need to start it up. The existing thread will 13380 // catch the buffer appends we just did. 13381 return; 13382 } 13383 13384 // Worker thread to both batch writes and to avoid blocking the caller on I/O. 13385 // (After this point, we shouldn't access AMS internal data structures.) 13386 new Thread("Error dump: " + dropboxTag) { 13387 @Override 13388 public void run() { 13389 // 5 second sleep to let stacks arrive and be batched together 13390 try { 13391 Thread.sleep(5000); // 5 seconds 13392 } catch (InterruptedException e) {} 13393 13394 String errorReport; 13395 synchronized (mStrictModeBuffer) { 13396 errorReport = mStrictModeBuffer.toString(); 13397 if (errorReport.length() == 0) { 13398 return; 13399 } 13400 mStrictModeBuffer.delete(0, mStrictModeBuffer.length()); 13401 mStrictModeBuffer.trimToSize(); 13402 } 13403 dbox.addText(dropboxTag, errorReport); 13404 } 13405 }.start(); 13406 } 13407 13408 /** 13409 * Used by {@link Log} via {@link com.android.internal.os.RuntimeInit} to report serious errors. 13410 * @param app object of the crashing app, null for the system server 13411 * @param tag reported by the caller 13412 * @param system whether this wtf is coming from the system 13413 * @param crashInfo describing the context of the error 13414 * @return true if the process should exit immediately (WTF is fatal) 13415 */ 13416 public boolean handleApplicationWtf(final IBinder app, final String tag, boolean system, 13417 final ApplicationErrorReport.ParcelableCrashInfo crashInfo) { 13418 final int callingUid = Binder.getCallingUid(); 13419 final int callingPid = Binder.getCallingPid(); 13420 13421 if (system) { 13422 // If this is coming from the system, we could very well have low-level 13423 // system locks held, so we want to do this all asynchronously. And we 13424 // never want this to become fatal, so there is that too. 13425 mHandler.post(new Runnable() { 13426 @Override public void run() { 13427 handleApplicationWtfInner(callingUid, callingPid, app, tag, crashInfo); 13428 } 13429 }); 13430 return false; 13431 } 13432 13433 final ProcessRecord r = handleApplicationWtfInner(callingUid, callingPid, app, tag, 13434 crashInfo); 13435 13436 if (r != null && r.pid != Process.myPid() && 13437 Settings.Global.getInt(mContext.getContentResolver(), 13438 Settings.Global.WTF_IS_FATAL, 0) != 0) { 13439 mAppErrors.crashApplication(r, crashInfo); 13440 return true; 13441 } else { 13442 return false; 13443 } 13444 } 13445 13446 ProcessRecord handleApplicationWtfInner(int callingUid, int callingPid, IBinder app, String tag, 13447 final ApplicationErrorReport.CrashInfo crashInfo) { 13448 final ProcessRecord r = findAppProcess(app, "WTF"); 13449 final String processName = app == null ? "system_server" 13450 : (r == null ? "unknown" : r.processName); 13451 13452 EventLog.writeEvent(EventLogTags.AM_WTF, UserHandle.getUserId(callingUid), callingPid, 13453 processName, r == null ? -1 : r.info.flags, tag, crashInfo.exceptionMessage); 13454 13455 addErrorToDropBox("wtf", r, processName, null, null, tag, null, null, crashInfo); 13456 13457 return r; 13458 } 13459 13460 /** 13461 * @param app object of some object (as stored in {@link com.android.internal.os.RuntimeInit}) 13462 * @return the corresponding {@link ProcessRecord} object, or null if none could be found 13463 */ 13464 private ProcessRecord findAppProcess(IBinder app, String reason) { 13465 if (app == null) { 13466 return null; 13467 } 13468 13469 synchronized (this) { 13470 final int NP = mProcessNames.getMap().size(); 13471 for (int ip=0; ip<NP; ip++) { 13472 SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 13473 final int NA = apps.size(); 13474 for (int ia=0; ia<NA; ia++) { 13475 ProcessRecord p = apps.valueAt(ia); 13476 if (p.thread != null && p.thread.asBinder() == app) { 13477 return p; 13478 } 13479 } 13480 } 13481 13482 Slog.w(TAG, "Can't find mystery application for " + reason 13483 + " from pid=" + Binder.getCallingPid() 13484 + " uid=" + Binder.getCallingUid() + ": " + app); 13485 return null; 13486 } 13487 } 13488 13489 /** 13490 * Utility function for addErrorToDropBox and handleStrictModeViolation's logging 13491 * to append various headers to the dropbox log text. 13492 */ 13493 private void appendDropBoxProcessHeaders(ProcessRecord process, String processName, 13494 StringBuilder sb) { 13495 // Watchdog thread ends up invoking this function (with 13496 // a null ProcessRecord) to add the stack file to dropbox. 13497 // Do not acquire a lock on this (am) in such cases, as it 13498 // could cause a potential deadlock, if and when watchdog 13499 // is invoked due to unavailability of lock on am and it 13500 // would prevent watchdog from killing system_server. 13501 if (process == null) { 13502 sb.append("Process: ").append(processName).append("\n"); 13503 return; 13504 } 13505 // Note: ProcessRecord 'process' is guarded by the service 13506 // instance. (notably process.pkgList, which could otherwise change 13507 // concurrently during execution of this method) 13508 synchronized (this) { 13509 sb.append("Process: ").append(processName).append("\n"); 13510 int flags = process.info.flags; 13511 IPackageManager pm = AppGlobals.getPackageManager(); 13512 sb.append("Flags: 0x").append(Integer.toHexString(flags)).append("\n"); 13513 for (int ip=0; ip<process.pkgList.size(); ip++) { 13514 String pkg = process.pkgList.keyAt(ip); 13515 sb.append("Package: ").append(pkg); 13516 try { 13517 PackageInfo pi = pm.getPackageInfo(pkg, 0, UserHandle.getCallingUserId()); 13518 if (pi != null) { 13519 sb.append(" v").append(pi.versionCode); 13520 if (pi.versionName != null) { 13521 sb.append(" (").append(pi.versionName).append(")"); 13522 } 13523 } 13524 } catch (RemoteException e) { 13525 Slog.e(TAG, "Error getting package info: " + pkg, e); 13526 } 13527 sb.append("\n"); 13528 } 13529 } 13530 } 13531 13532 private static String processClass(ProcessRecord process) { 13533 if (process == null || process.pid == MY_PID) { 13534 return "system_server"; 13535 } else if ((process.info.flags & ApplicationInfo.FLAG_SYSTEM) != 0) { 13536 return "system_app"; 13537 } else { 13538 return "data_app"; 13539 } 13540 } 13541 13542 private volatile long mWtfClusterStart; 13543 private volatile int mWtfClusterCount; 13544 13545 /** 13546 * Write a description of an error (crash, WTF, ANR) to the drop box. 13547 * @param eventType to include in the drop box tag ("crash", "wtf", etc.) 13548 * @param process which caused the error, null means the system server 13549 * @param activity which triggered the error, null if unknown 13550 * @param parent activity related to the error, null if unknown 13551 * @param subject line related to the error, null if absent 13552 * @param report in long form describing the error, null if absent 13553 * @param dataFile text file to include in the report, null if none 13554 * @param crashInfo giving an application stack trace, null if absent 13555 */ 13556 public void addErrorToDropBox(String eventType, 13557 ProcessRecord process, String processName, ActivityRecord activity, 13558 ActivityRecord parent, String subject, 13559 final String report, final File dataFile, 13560 final ApplicationErrorReport.CrashInfo crashInfo) { 13561 // NOTE -- this must never acquire the ActivityManagerService lock, 13562 // otherwise the watchdog may be prevented from resetting the system. 13563 13564 // Bail early if not published yet 13565 if (ServiceManager.getService(Context.DROPBOX_SERVICE) == null) return; 13566 final DropBoxManager dbox = mContext.getSystemService(DropBoxManager.class); 13567 13568 // Exit early if the dropbox isn't configured to accept this report type. 13569 final String dropboxTag = processClass(process) + "_" + eventType; 13570 if (dbox == null || !dbox.isTagEnabled(dropboxTag)) return; 13571 13572 // Rate-limit how often we're willing to do the heavy lifting below to 13573 // collect and record logs; currently 5 logs per 10 second period. 13574 final long now = SystemClock.elapsedRealtime(); 13575 if (now - mWtfClusterStart > 10 * DateUtils.SECOND_IN_MILLIS) { 13576 mWtfClusterStart = now; 13577 mWtfClusterCount = 1; 13578 } else { 13579 if (mWtfClusterCount++ >= 5) return; 13580 } 13581 13582 final StringBuilder sb = new StringBuilder(1024); 13583 appendDropBoxProcessHeaders(process, processName, sb); 13584 if (process != null) { 13585 sb.append("Foreground: ") 13586 .append(process.isInterestingToUserLocked() ? "Yes" : "No") 13587 .append("\n"); 13588 } 13589 if (activity != null) { 13590 sb.append("Activity: ").append(activity.shortComponentName).append("\n"); 13591 } 13592 if (parent != null && parent.app != null && parent.app.pid != process.pid) { 13593 sb.append("Parent-Process: ").append(parent.app.processName).append("\n"); 13594 } 13595 if (parent != null && parent != activity) { 13596 sb.append("Parent-Activity: ").append(parent.shortComponentName).append("\n"); 13597 } 13598 if (subject != null) { 13599 sb.append("Subject: ").append(subject).append("\n"); 13600 } 13601 sb.append("Build: ").append(Build.FINGERPRINT).append("\n"); 13602 if (Debug.isDebuggerConnected()) { 13603 sb.append("Debugger: Connected\n"); 13604 } 13605 sb.append("\n"); 13606 13607 // Do the rest in a worker thread to avoid blocking the caller on I/O 13608 // (After this point, we shouldn't access AMS internal data structures.) 13609 Thread worker = new Thread("Error dump: " + dropboxTag) { 13610 @Override 13611 public void run() { 13612 if (report != null) { 13613 sb.append(report); 13614 } 13615 13616 String setting = Settings.Global.ERROR_LOGCAT_PREFIX + dropboxTag; 13617 int lines = Settings.Global.getInt(mContext.getContentResolver(), setting, 0); 13618 int maxDataFileSize = DROPBOX_MAX_SIZE - sb.length() 13619 - lines * RESERVED_BYTES_PER_LOGCAT_LINE; 13620 13621 if (dataFile != null && maxDataFileSize > 0) { 13622 try { 13623 sb.append(FileUtils.readTextFile(dataFile, maxDataFileSize, 13624 "\n\n[[TRUNCATED]]")); 13625 } catch (IOException e) { 13626 Slog.e(TAG, "Error reading " + dataFile, e); 13627 } 13628 } 13629 if (crashInfo != null && crashInfo.stackTrace != null) { 13630 sb.append(crashInfo.stackTrace); 13631 } 13632 13633 if (lines > 0) { 13634 sb.append("\n"); 13635 13636 // Merge several logcat streams, and take the last N lines 13637 InputStreamReader input = null; 13638 try { 13639 java.lang.Process logcat = new ProcessBuilder( 13640 "/system/bin/timeout", "-k", "15s", "10s", 13641 "/system/bin/logcat", "-v", "threadtime", "-b", "events", "-b", "system", 13642 "-b", "main", "-b", "crash", "-t", String.valueOf(lines)) 13643 .redirectErrorStream(true).start(); 13644 13645 try { logcat.getOutputStream().close(); } catch (IOException e) {} 13646 try { logcat.getErrorStream().close(); } catch (IOException e) {} 13647 input = new InputStreamReader(logcat.getInputStream()); 13648 13649 int num; 13650 char[] buf = new char[8192]; 13651 while ((num = input.read(buf)) > 0) sb.append(buf, 0, num); 13652 } catch (IOException e) { 13653 Slog.e(TAG, "Error running logcat", e); 13654 } finally { 13655 if (input != null) try { input.close(); } catch (IOException e) {} 13656 } 13657 } 13658 13659 dbox.addText(dropboxTag, sb.toString()); 13660 } 13661 }; 13662 13663 if (process == null) { 13664 // If process is null, we are being called from some internal code 13665 // and may be about to die -- run this synchronously. 13666 worker.run(); 13667 } else { 13668 worker.start(); 13669 } 13670 } 13671 13672 @Override 13673 public List<ActivityManager.ProcessErrorStateInfo> getProcessesInErrorState() { 13674 enforceNotIsolatedCaller("getProcessesInErrorState"); 13675 // assume our apps are happy - lazy create the list 13676 List<ActivityManager.ProcessErrorStateInfo> errList = null; 13677 13678 final boolean allUsers = ActivityManager.checkUidPermission(INTERACT_ACROSS_USERS_FULL, 13679 Binder.getCallingUid()) == PackageManager.PERMISSION_GRANTED; 13680 int userId = UserHandle.getUserId(Binder.getCallingUid()); 13681 13682 synchronized (this) { 13683 13684 // iterate across all processes 13685 for (int i=mLruProcesses.size()-1; i>=0; i--) { 13686 ProcessRecord app = mLruProcesses.get(i); 13687 if (!allUsers && app.userId != userId) { 13688 continue; 13689 } 13690 if ((app.thread != null) && (app.crashing || app.notResponding)) { 13691 // This one's in trouble, so we'll generate a report for it 13692 // crashes are higher priority (in case there's a crash *and* an anr) 13693 ActivityManager.ProcessErrorStateInfo report = null; 13694 if (app.crashing) { 13695 report = app.crashingReport; 13696 } else if (app.notResponding) { 13697 report = app.notRespondingReport; 13698 } 13699 13700 if (report != null) { 13701 if (errList == null) { 13702 errList = new ArrayList<ActivityManager.ProcessErrorStateInfo>(1); 13703 } 13704 errList.add(report); 13705 } else { 13706 Slog.w(TAG, "Missing app error report, app = " + app.processName + 13707 " crashing = " + app.crashing + 13708 " notResponding = " + app.notResponding); 13709 } 13710 } 13711 } 13712 } 13713 13714 return errList; 13715 } 13716 13717 static int procStateToImportance(int procState, int memAdj, 13718 ActivityManager.RunningAppProcessInfo currApp) { 13719 int imp = ActivityManager.RunningAppProcessInfo.procStateToImportance(procState); 13720 if (imp == ActivityManager.RunningAppProcessInfo.IMPORTANCE_BACKGROUND) { 13721 currApp.lru = memAdj; 13722 } else { 13723 currApp.lru = 0; 13724 } 13725 return imp; 13726 } 13727 13728 private void fillInProcMemInfo(ProcessRecord app, 13729 ActivityManager.RunningAppProcessInfo outInfo) { 13730 outInfo.pid = app.pid; 13731 outInfo.uid = app.info.uid; 13732 if (mHeavyWeightProcess == app) { 13733 outInfo.flags |= ActivityManager.RunningAppProcessInfo.FLAG_CANT_SAVE_STATE; 13734 } 13735 if (app.persistent) { 13736 outInfo.flags |= ActivityManager.RunningAppProcessInfo.FLAG_PERSISTENT; 13737 } 13738 if (app.activities.size() > 0) { 13739 outInfo.flags |= ActivityManager.RunningAppProcessInfo.FLAG_HAS_ACTIVITIES; 13740 } 13741 outInfo.lastTrimLevel = app.trimMemoryLevel; 13742 int adj = app.curAdj; 13743 int procState = app.curProcState; 13744 outInfo.importance = procStateToImportance(procState, adj, outInfo); 13745 outInfo.importanceReasonCode = app.adjTypeCode; 13746 outInfo.processState = app.curProcState; 13747 } 13748 13749 @Override 13750 public List<ActivityManager.RunningAppProcessInfo> getRunningAppProcesses() { 13751 enforceNotIsolatedCaller("getRunningAppProcesses"); 13752 13753 final int callingUid = Binder.getCallingUid(); 13754 13755 // Lazy instantiation of list 13756 List<ActivityManager.RunningAppProcessInfo> runList = null; 13757 final boolean allUsers = ActivityManager.checkUidPermission(INTERACT_ACROSS_USERS_FULL, 13758 callingUid) == PackageManager.PERMISSION_GRANTED; 13759 final int userId = UserHandle.getUserId(callingUid); 13760 final boolean allUids = isGetTasksAllowed( 13761 "getRunningAppProcesses", Binder.getCallingPid(), callingUid); 13762 13763 synchronized (this) { 13764 // Iterate across all processes 13765 for (int i = mLruProcesses.size() - 1; i >= 0; i--) { 13766 ProcessRecord app = mLruProcesses.get(i); 13767 if ((!allUsers && app.userId != userId) 13768 || (!allUids && app.uid != callingUid)) { 13769 continue; 13770 } 13771 if ((app.thread != null) && (!app.crashing && !app.notResponding)) { 13772 // Generate process state info for running application 13773 ActivityManager.RunningAppProcessInfo currApp = 13774 new ActivityManager.RunningAppProcessInfo(app.processName, 13775 app.pid, app.getPackageList()); 13776 fillInProcMemInfo(app, currApp); 13777 if (app.adjSource instanceof ProcessRecord) { 13778 currApp.importanceReasonPid = ((ProcessRecord)app.adjSource).pid; 13779 currApp.importanceReasonImportance = 13780 ActivityManager.RunningAppProcessInfo.procStateToImportance( 13781 app.adjSourceProcState); 13782 } else if (app.adjSource instanceof ActivityRecord) { 13783 ActivityRecord r = (ActivityRecord)app.adjSource; 13784 if (r.app != null) currApp.importanceReasonPid = r.app.pid; 13785 } 13786 if (app.adjTarget instanceof ComponentName) { 13787 currApp.importanceReasonComponent = (ComponentName)app.adjTarget; 13788 } 13789 //Slog.v(TAG, "Proc " + app.processName + ": imp=" + currApp.importance 13790 // + " lru=" + currApp.lru); 13791 if (runList == null) { 13792 runList = new ArrayList<>(); 13793 } 13794 runList.add(currApp); 13795 } 13796 } 13797 } 13798 return runList; 13799 } 13800 13801 @Override 13802 public List<ApplicationInfo> getRunningExternalApplications() { 13803 enforceNotIsolatedCaller("getRunningExternalApplications"); 13804 List<ActivityManager.RunningAppProcessInfo> runningApps = getRunningAppProcesses(); 13805 List<ApplicationInfo> retList = new ArrayList<ApplicationInfo>(); 13806 if (runningApps != null && runningApps.size() > 0) { 13807 Set<String> extList = new HashSet<String>(); 13808 for (ActivityManager.RunningAppProcessInfo app : runningApps) { 13809 if (app.pkgList != null) { 13810 for (String pkg : app.pkgList) { 13811 extList.add(pkg); 13812 } 13813 } 13814 } 13815 IPackageManager pm = AppGlobals.getPackageManager(); 13816 for (String pkg : extList) { 13817 try { 13818 ApplicationInfo info = pm.getApplicationInfo(pkg, 0, UserHandle.getCallingUserId()); 13819 if ((info.flags & ApplicationInfo.FLAG_EXTERNAL_STORAGE) != 0) { 13820 retList.add(info); 13821 } 13822 } catch (RemoteException e) { 13823 } 13824 } 13825 } 13826 return retList; 13827 } 13828 13829 @Override 13830 public void getMyMemoryState(ActivityManager.RunningAppProcessInfo outInfo) { 13831 enforceNotIsolatedCaller("getMyMemoryState"); 13832 synchronized (this) { 13833 ProcessRecord proc; 13834 synchronized (mPidsSelfLocked) { 13835 proc = mPidsSelfLocked.get(Binder.getCallingPid()); 13836 } 13837 fillInProcMemInfo(proc, outInfo); 13838 } 13839 } 13840 13841 @Override 13842 public int getMemoryTrimLevel() { 13843 enforceNotIsolatedCaller("getMyMemoryState"); 13844 synchronized (this) { 13845 return mLastMemoryLevel; 13846 } 13847 } 13848 13849 @Override 13850 public void onShellCommand(FileDescriptor in, FileDescriptor out, 13851 FileDescriptor err, String[] args, ShellCallback callback, 13852 ResultReceiver resultReceiver) { 13853 (new ActivityManagerShellCommand(this, false)).exec( 13854 this, in, out, err, args, callback, resultReceiver); 13855 } 13856 13857 @Override 13858 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 13859 if (checkCallingPermission(android.Manifest.permission.DUMP) 13860 != PackageManager.PERMISSION_GRANTED) { 13861 pw.println("Permission Denial: can't dump ActivityManager from from pid=" 13862 + Binder.getCallingPid() 13863 + ", uid=" + Binder.getCallingUid() 13864 + " without permission " 13865 + android.Manifest.permission.DUMP); 13866 return; 13867 } 13868 13869 boolean dumpAll = false; 13870 boolean dumpClient = false; 13871 boolean dumpCheckin = false; 13872 boolean dumpCheckinFormat = false; 13873 boolean dumpVisibleStacks = false; 13874 String dumpPackage = null; 13875 13876 int opti = 0; 13877 while (opti < args.length) { 13878 String opt = args[opti]; 13879 if (opt == null || opt.length() <= 0 || opt.charAt(0) != '-') { 13880 break; 13881 } 13882 opti++; 13883 if ("-a".equals(opt)) { 13884 dumpAll = true; 13885 } else if ("-c".equals(opt)) { 13886 dumpClient = true; 13887 } else if ("-v".equals(opt)) { 13888 dumpVisibleStacks = true; 13889 } else if ("-p".equals(opt)) { 13890 if (opti < args.length) { 13891 dumpPackage = args[opti]; 13892 opti++; 13893 } else { 13894 pw.println("Error: -p option requires package argument"); 13895 return; 13896 } 13897 dumpClient = true; 13898 } else if ("--checkin".equals(opt)) { 13899 dumpCheckin = dumpCheckinFormat = true; 13900 } else if ("-C".equals(opt)) { 13901 dumpCheckinFormat = true; 13902 } else if ("-h".equals(opt)) { 13903 ActivityManagerShellCommand.dumpHelp(pw, true); 13904 return; 13905 } else { 13906 pw.println("Unknown argument: " + opt + "; use -h for help"); 13907 } 13908 } 13909 13910 long origId = Binder.clearCallingIdentity(); 13911 boolean more = false; 13912 // Is the caller requesting to dump a particular piece of data? 13913 if (opti < args.length) { 13914 String cmd = args[opti]; 13915 opti++; 13916 if ("activities".equals(cmd) || "a".equals(cmd)) { 13917 synchronized (this) { 13918 dumpActivitiesLocked(fd, pw, args, opti, true, dumpClient, dumpPackage); 13919 } 13920 } else if ("recents".equals(cmd) || "r".equals(cmd)) { 13921 synchronized (this) { 13922 dumpRecentsLocked(fd, pw, args, opti, true, dumpPackage); 13923 } 13924 } else if ("broadcasts".equals(cmd) || "b".equals(cmd)) { 13925 String[] newArgs; 13926 String name; 13927 if (opti >= args.length) { 13928 name = null; 13929 newArgs = EMPTY_STRING_ARRAY; 13930 } else { 13931 dumpPackage = args[opti]; 13932 opti++; 13933 newArgs = new String[args.length - opti]; 13934 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 13935 args.length - opti); 13936 } 13937 synchronized (this) { 13938 dumpBroadcastsLocked(fd, pw, args, opti, true, dumpPackage); 13939 } 13940 } else if ("broadcast-stats".equals(cmd)) { 13941 String[] newArgs; 13942 String name; 13943 if (opti >= args.length) { 13944 name = null; 13945 newArgs = EMPTY_STRING_ARRAY; 13946 } else { 13947 dumpPackage = args[opti]; 13948 opti++; 13949 newArgs = new String[args.length - opti]; 13950 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 13951 args.length - opti); 13952 } 13953 synchronized (this) { 13954 if (dumpCheckinFormat) { 13955 dumpBroadcastStatsCheckinLocked(fd, pw, args, opti, dumpCheckin, 13956 dumpPackage); 13957 } else { 13958 dumpBroadcastStatsLocked(fd, pw, args, opti, true, dumpPackage); 13959 } 13960 } 13961 } else if ("intents".equals(cmd) || "i".equals(cmd)) { 13962 String[] newArgs; 13963 String name; 13964 if (opti >= args.length) { 13965 name = null; 13966 newArgs = EMPTY_STRING_ARRAY; 13967 } else { 13968 dumpPackage = args[opti]; 13969 opti++; 13970 newArgs = new String[args.length - opti]; 13971 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 13972 args.length - opti); 13973 } 13974 synchronized (this) { 13975 dumpPendingIntentsLocked(fd, pw, args, opti, true, dumpPackage); 13976 } 13977 } else if ("processes".equals(cmd) || "p".equals(cmd)) { 13978 String[] newArgs; 13979 String name; 13980 if (opti >= args.length) { 13981 name = null; 13982 newArgs = EMPTY_STRING_ARRAY; 13983 } else { 13984 dumpPackage = args[opti]; 13985 opti++; 13986 newArgs = new String[args.length - opti]; 13987 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 13988 args.length - opti); 13989 } 13990 synchronized (this) { 13991 dumpProcessesLocked(fd, pw, args, opti, true, dumpPackage); 13992 } 13993 } else if ("oom".equals(cmd) || "o".equals(cmd)) { 13994 synchronized (this) { 13995 dumpOomLocked(fd, pw, args, opti, true); 13996 } 13997 } else if ("permissions".equals(cmd) || "perm".equals(cmd)) { 13998 synchronized (this) { 13999 dumpPermissionsLocked(fd, pw, args, opti, true, null); 14000 } 14001 } else if ("provider".equals(cmd)) { 14002 String[] newArgs; 14003 String name; 14004 if (opti >= args.length) { 14005 name = null; 14006 newArgs = EMPTY_STRING_ARRAY; 14007 } else { 14008 name = args[opti]; 14009 opti++; 14010 newArgs = new String[args.length - opti]; 14011 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, args.length - opti); 14012 } 14013 if (!dumpProvider(fd, pw, name, newArgs, 0, dumpAll)) { 14014 pw.println("No providers match: " + name); 14015 pw.println("Use -h for help."); 14016 } 14017 } else if ("providers".equals(cmd) || "prov".equals(cmd)) { 14018 synchronized (this) { 14019 dumpProvidersLocked(fd, pw, args, opti, true, null); 14020 } 14021 } else if ("service".equals(cmd)) { 14022 String[] newArgs; 14023 String name; 14024 if (opti >= args.length) { 14025 name = null; 14026 newArgs = EMPTY_STRING_ARRAY; 14027 } else { 14028 name = args[opti]; 14029 opti++; 14030 newArgs = new String[args.length - opti]; 14031 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 14032 args.length - opti); 14033 } 14034 if (!mServices.dumpService(fd, pw, name, newArgs, 0, dumpAll)) { 14035 pw.println("No services match: " + name); 14036 pw.println("Use -h for help."); 14037 } 14038 } else if ("package".equals(cmd)) { 14039 String[] newArgs; 14040 if (opti >= args.length) { 14041 pw.println("package: no package name specified"); 14042 pw.println("Use -h for help."); 14043 } else { 14044 dumpPackage = args[opti]; 14045 opti++; 14046 newArgs = new String[args.length - opti]; 14047 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 14048 args.length - opti); 14049 args = newArgs; 14050 opti = 0; 14051 more = true; 14052 } 14053 } else if ("associations".equals(cmd) || "as".equals(cmd)) { 14054 synchronized (this) { 14055 dumpAssociationsLocked(fd, pw, args, opti, true, dumpClient, dumpPackage); 14056 } 14057 } else if ("services".equals(cmd) || "s".equals(cmd)) { 14058 if (dumpClient) { 14059 ActiveServices.ServiceDumper dumper; 14060 synchronized (this) { 14061 dumper = mServices.newServiceDumperLocked(fd, pw, args, opti, true, 14062 dumpPackage); 14063 } 14064 dumper.dumpWithClient(); 14065 } else { 14066 synchronized (this) { 14067 mServices.newServiceDumperLocked(fd, pw, args, opti, true, 14068 dumpPackage).dumpLocked(); 14069 } 14070 } 14071 } else if ("locks".equals(cmd)) { 14072 LockGuard.dump(fd, pw, args); 14073 } else { 14074 // Dumping a single activity? 14075 if (!dumpActivity(fd, pw, cmd, args, opti, dumpAll, dumpVisibleStacks)) { 14076 ActivityManagerShellCommand shell = new ActivityManagerShellCommand(this, true); 14077 int res = shell.exec(this, null, fd, null, args, null, 14078 new ResultReceiver(null)); 14079 if (res < 0) { 14080 pw.println("Bad activity command, or no activities match: " + cmd); 14081 pw.println("Use -h for help."); 14082 } 14083 } 14084 } 14085 if (!more) { 14086 Binder.restoreCallingIdentity(origId); 14087 return; 14088 } 14089 } 14090 14091 // No piece of data specified, dump everything. 14092 if (dumpCheckinFormat) { 14093 dumpBroadcastStatsCheckinLocked(fd, pw, args, opti, dumpCheckin, dumpPackage); 14094 } else if (dumpClient) { 14095 ActiveServices.ServiceDumper sdumper; 14096 synchronized (this) { 14097 dumpPendingIntentsLocked(fd, pw, args, opti, dumpAll, dumpPackage); 14098 pw.println(); 14099 if (dumpAll) { 14100 pw.println("-------------------------------------------------------------------------------"); 14101 } 14102 dumpBroadcastsLocked(fd, pw, args, opti, dumpAll, dumpPackage); 14103 pw.println(); 14104 if (dumpAll) { 14105 pw.println("-------------------------------------------------------------------------------"); 14106 } 14107 if (dumpAll || dumpPackage != null) { 14108 dumpBroadcastStatsLocked(fd, pw, args, opti, dumpAll, dumpPackage); 14109 pw.println(); 14110 if (dumpAll) { 14111 pw.println("-------------------------------------------------------------------------------"); 14112 } 14113 } 14114 dumpProvidersLocked(fd, pw, args, opti, dumpAll, dumpPackage); 14115 pw.println(); 14116 if (dumpAll) { 14117 pw.println("-------------------------------------------------------------------------------"); 14118 } 14119 dumpPermissionsLocked(fd, pw, args, opti, dumpAll, dumpPackage); 14120 pw.println(); 14121 if (dumpAll) { 14122 pw.println("-------------------------------------------------------------------------------"); 14123 } 14124 sdumper = mServices.newServiceDumperLocked(fd, pw, args, opti, dumpAll, 14125 dumpPackage); 14126 } 14127 sdumper.dumpWithClient(); 14128 pw.println(); 14129 synchronized (this) { 14130 if (dumpAll) { 14131 pw.println("-------------------------------------------------------------------------------"); 14132 } 14133 dumpRecentsLocked(fd, pw, args, opti, dumpAll, dumpPackage); 14134 pw.println(); 14135 if (dumpAll) { 14136 pw.println("-------------------------------------------------------------------------------"); 14137 } 14138 dumpActivitiesLocked(fd, pw, args, opti, dumpAll, dumpClient, dumpPackage); 14139 if (mAssociations.size() > 0) { 14140 pw.println(); 14141 if (dumpAll) { 14142 pw.println("-------------------------------------------------------------------------------"); 14143 } 14144 dumpAssociationsLocked(fd, pw, args, opti, dumpAll, dumpClient, dumpPackage); 14145 } 14146 pw.println(); 14147 if (dumpAll) { 14148 pw.println("-------------------------------------------------------------------------------"); 14149 } 14150 dumpProcessesLocked(fd, pw, args, opti, dumpAll, dumpPackage); 14151 } 14152 14153 } else { 14154 synchronized (this) { 14155 dumpPendingIntentsLocked(fd, pw, args, opti, dumpAll, dumpPackage); 14156 pw.println(); 14157 if (dumpAll) { 14158 pw.println("-------------------------------------------------------------------------------"); 14159 } 14160 dumpBroadcastsLocked(fd, pw, args, opti, dumpAll, dumpPackage); 14161 pw.println(); 14162 if (dumpAll) { 14163 pw.println("-------------------------------------------------------------------------------"); 14164 } 14165 if (dumpAll || dumpPackage != null) { 14166 dumpBroadcastStatsLocked(fd, pw, args, opti, dumpAll, dumpPackage); 14167 pw.println(); 14168 if (dumpAll) { 14169 pw.println("-------------------------------------------------------------------------------"); 14170 } 14171 } 14172 dumpProvidersLocked(fd, pw, args, opti, dumpAll, dumpPackage); 14173 pw.println(); 14174 if (dumpAll) { 14175 pw.println("-------------------------------------------------------------------------------"); 14176 } 14177 dumpPermissionsLocked(fd, pw, args, opti, dumpAll, dumpPackage); 14178 pw.println(); 14179 if (dumpAll) { 14180 pw.println("-------------------------------------------------------------------------------"); 14181 } 14182 mServices.newServiceDumperLocked(fd, pw, args, opti, dumpAll, dumpPackage) 14183 .dumpLocked(); 14184 pw.println(); 14185 if (dumpAll) { 14186 pw.println("-------------------------------------------------------------------------------"); 14187 } 14188 dumpRecentsLocked(fd, pw, args, opti, dumpAll, dumpPackage); 14189 pw.println(); 14190 if (dumpAll) { 14191 pw.println("-------------------------------------------------------------------------------"); 14192 } 14193 dumpActivitiesLocked(fd, pw, args, opti, dumpAll, dumpClient, dumpPackage); 14194 if (mAssociations.size() > 0) { 14195 pw.println(); 14196 if (dumpAll) { 14197 pw.println("-------------------------------------------------------------------------------"); 14198 } 14199 dumpAssociationsLocked(fd, pw, args, opti, dumpAll, dumpClient, dumpPackage); 14200 } 14201 pw.println(); 14202 if (dumpAll) { 14203 pw.println("-------------------------------------------------------------------------------"); 14204 } 14205 dumpProcessesLocked(fd, pw, args, opti, dumpAll, dumpPackage); 14206 } 14207 } 14208 Binder.restoreCallingIdentity(origId); 14209 } 14210 14211 void dumpActivitiesLocked(FileDescriptor fd, PrintWriter pw, String[] args, 14212 int opti, boolean dumpAll, boolean dumpClient, String dumpPackage) { 14213 pw.println("ACTIVITY MANAGER ACTIVITIES (dumpsys activity activities)"); 14214 14215 boolean printedAnything = mStackSupervisor.dumpActivitiesLocked(fd, pw, dumpAll, dumpClient, 14216 dumpPackage); 14217 boolean needSep = printedAnything; 14218 14219 boolean printed = ActivityStackSupervisor.printThisActivity(pw, 14220 mStackSupervisor.getResumedActivityLocked(), 14221 dumpPackage, needSep, " ResumedActivity: "); 14222 if (printed) { 14223 printedAnything = true; 14224 needSep = false; 14225 } 14226 14227 if (dumpPackage == null) { 14228 if (needSep) { 14229 pw.println(); 14230 } 14231 needSep = true; 14232 printedAnything = true; 14233 mStackSupervisor.dump(pw, " "); 14234 } 14235 14236 if (!printedAnything) { 14237 pw.println(" (nothing)"); 14238 } 14239 } 14240 14241 void dumpRecentsLocked(FileDescriptor fd, PrintWriter pw, String[] args, 14242 int opti, boolean dumpAll, String dumpPackage) { 14243 pw.println("ACTIVITY MANAGER RECENT TASKS (dumpsys activity recents)"); 14244 14245 boolean printedAnything = false; 14246 14247 if (mRecentTasks != null && mRecentTasks.size() > 0) { 14248 boolean printedHeader = false; 14249 14250 final int N = mRecentTasks.size(); 14251 for (int i=0; i<N; i++) { 14252 TaskRecord tr = mRecentTasks.get(i); 14253 if (dumpPackage != null) { 14254 if (tr.realActivity == null || 14255 !dumpPackage.equals(tr.realActivity.getPackageName())) { 14256 continue; 14257 } 14258 } 14259 if (!printedHeader) { 14260 pw.println(" Recent tasks:"); 14261 printedHeader = true; 14262 printedAnything = true; 14263 } 14264 pw.print(" * Recent #"); pw.print(i); pw.print(": "); 14265 pw.println(tr); 14266 if (dumpAll) { 14267 mRecentTasks.get(i).dump(pw, " "); 14268 } 14269 } 14270 } 14271 14272 if (!printedAnything) { 14273 pw.println(" (nothing)"); 14274 } 14275 } 14276 14277 void dumpAssociationsLocked(FileDescriptor fd, PrintWriter pw, String[] args, 14278 int opti, boolean dumpAll, boolean dumpClient, String dumpPackage) { 14279 pw.println("ACTIVITY MANAGER ASSOCIATIONS (dumpsys activity associations)"); 14280 14281 int dumpUid = 0; 14282 if (dumpPackage != null) { 14283 IPackageManager pm = AppGlobals.getPackageManager(); 14284 try { 14285 dumpUid = pm.getPackageUid(dumpPackage, MATCH_UNINSTALLED_PACKAGES, 0); 14286 } catch (RemoteException e) { 14287 } 14288 } 14289 14290 boolean printedAnything = false; 14291 14292 final long now = SystemClock.uptimeMillis(); 14293 14294 for (int i1=0, N1=mAssociations.size(); i1<N1; i1++) { 14295 ArrayMap<ComponentName, SparseArray<ArrayMap<String, Association>>> targetComponents 14296 = mAssociations.valueAt(i1); 14297 for (int i2=0, N2=targetComponents.size(); i2<N2; i2++) { 14298 SparseArray<ArrayMap<String, Association>> sourceUids 14299 = targetComponents.valueAt(i2); 14300 for (int i3=0, N3=sourceUids.size(); i3<N3; i3++) { 14301 ArrayMap<String, Association> sourceProcesses = sourceUids.valueAt(i3); 14302 for (int i4=0, N4=sourceProcesses.size(); i4<N4; i4++) { 14303 Association ass = sourceProcesses.valueAt(i4); 14304 if (dumpPackage != null) { 14305 if (!ass.mTargetComponent.getPackageName().equals(dumpPackage) 14306 && UserHandle.getAppId(ass.mSourceUid) != dumpUid) { 14307 continue; 14308 } 14309 } 14310 printedAnything = true; 14311 pw.print(" "); 14312 pw.print(ass.mTargetProcess); 14313 pw.print("/"); 14314 UserHandle.formatUid(pw, ass.mTargetUid); 14315 pw.print(" <- "); 14316 pw.print(ass.mSourceProcess); 14317 pw.print("/"); 14318 UserHandle.formatUid(pw, ass.mSourceUid); 14319 pw.println(); 14320 pw.print(" via "); 14321 pw.print(ass.mTargetComponent.flattenToShortString()); 14322 pw.println(); 14323 pw.print(" "); 14324 long dur = ass.mTime; 14325 if (ass.mNesting > 0) { 14326 dur += now - ass.mStartTime; 14327 } 14328 TimeUtils.formatDuration(dur, pw); 14329 pw.print(" ("); 14330 pw.print(ass.mCount); 14331 pw.print(" times)"); 14332 pw.print(" "); 14333 for (int i=0; i<ass.mStateTimes.length; i++) { 14334 long amt = ass.mStateTimes[i]; 14335 if (ass.mLastState-ActivityManager.MIN_PROCESS_STATE == i) { 14336 amt += now - ass.mLastStateUptime; 14337 } 14338 if (amt != 0) { 14339 pw.print(" "); 14340 pw.print(ProcessList.makeProcStateString( 14341 i + ActivityManager.MIN_PROCESS_STATE)); 14342 pw.print("="); 14343 TimeUtils.formatDuration(amt, pw); 14344 if (ass.mLastState-ActivityManager.MIN_PROCESS_STATE == i) { 14345 pw.print("*"); 14346 } 14347 } 14348 } 14349 pw.println(); 14350 if (ass.mNesting > 0) { 14351 pw.print(" Currently active: "); 14352 TimeUtils.formatDuration(now - ass.mStartTime, pw); 14353 pw.println(); 14354 } 14355 } 14356 } 14357 } 14358 14359 } 14360 14361 if (!printedAnything) { 14362 pw.println(" (nothing)"); 14363 } 14364 } 14365 14366 boolean dumpUids(PrintWriter pw, String dumpPackage, SparseArray<UidRecord> uids, 14367 String header, boolean needSep) { 14368 boolean printed = false; 14369 int whichAppId = -1; 14370 if (dumpPackage != null) { 14371 try { 14372 ApplicationInfo info = mContext.getPackageManager().getApplicationInfo( 14373 dumpPackage, 0); 14374 whichAppId = UserHandle.getAppId(info.uid); 14375 } catch (NameNotFoundException e) { 14376 e.printStackTrace(); 14377 } 14378 } 14379 for (int i=0; i<uids.size(); i++) { 14380 UidRecord uidRec = uids.valueAt(i); 14381 if (dumpPackage != null && UserHandle.getAppId(uidRec.uid) != whichAppId) { 14382 continue; 14383 } 14384 if (!printed) { 14385 printed = true; 14386 if (needSep) { 14387 pw.println(); 14388 } 14389 pw.print(" "); 14390 pw.println(header); 14391 needSep = true; 14392 } 14393 pw.print(" UID "); UserHandle.formatUid(pw, uidRec.uid); 14394 pw.print(": "); pw.println(uidRec); 14395 } 14396 return printed; 14397 } 14398 14399 void dumpProcessesLocked(FileDescriptor fd, PrintWriter pw, String[] args, 14400 int opti, boolean dumpAll, String dumpPackage) { 14401 boolean needSep = false; 14402 boolean printedAnything = false; 14403 int numPers = 0; 14404 14405 pw.println("ACTIVITY MANAGER RUNNING PROCESSES (dumpsys activity processes)"); 14406 14407 if (dumpAll) { 14408 final int NP = mProcessNames.getMap().size(); 14409 for (int ip=0; ip<NP; ip++) { 14410 SparseArray<ProcessRecord> procs = mProcessNames.getMap().valueAt(ip); 14411 final int NA = procs.size(); 14412 for (int ia=0; ia<NA; ia++) { 14413 ProcessRecord r = procs.valueAt(ia); 14414 if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) { 14415 continue; 14416 } 14417 if (!needSep) { 14418 pw.println(" All known processes:"); 14419 needSep = true; 14420 printedAnything = true; 14421 } 14422 pw.print(r.persistent ? " *PERS*" : " *APP*"); 14423 pw.print(" UID "); pw.print(procs.keyAt(ia)); 14424 pw.print(" "); pw.println(r); 14425 r.dump(pw, " "); 14426 if (r.persistent) { 14427 numPers++; 14428 } 14429 } 14430 } 14431 } 14432 14433 if (mIsolatedProcesses.size() > 0) { 14434 boolean printed = false; 14435 for (int i=0; i<mIsolatedProcesses.size(); i++) { 14436 ProcessRecord r = mIsolatedProcesses.valueAt(i); 14437 if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) { 14438 continue; 14439 } 14440 if (!printed) { 14441 if (needSep) { 14442 pw.println(); 14443 } 14444 pw.println(" Isolated process list (sorted by uid):"); 14445 printedAnything = true; 14446 printed = true; 14447 needSep = true; 14448 } 14449 pw.println(String.format("%sIsolated #%2d: %s", 14450 " ", i, r.toString())); 14451 } 14452 } 14453 14454 if (mActiveUids.size() > 0) { 14455 if (dumpUids(pw, dumpPackage, mActiveUids, "UID states:", needSep)) { 14456 printedAnything = needSep = true; 14457 } 14458 } 14459 if (mValidateUids.size() > 0) { 14460 if (dumpUids(pw, dumpPackage, mValidateUids, "UID validation:", needSep)) { 14461 printedAnything = needSep = true; 14462 } 14463 } 14464 14465 if (mLruProcesses.size() > 0) { 14466 if (needSep) { 14467 pw.println(); 14468 } 14469 pw.print(" Process LRU list (sorted by oom_adj, "); pw.print(mLruProcesses.size()); 14470 pw.print(" total, non-act at "); 14471 pw.print(mLruProcesses.size()-mLruProcessActivityStart); 14472 pw.print(", non-svc at "); 14473 pw.print(mLruProcesses.size()-mLruProcessServiceStart); 14474 pw.println("):"); 14475 dumpProcessOomList(pw, this, mLruProcesses, " ", "Proc", "PERS", false, dumpPackage); 14476 needSep = true; 14477 printedAnything = true; 14478 } 14479 14480 if (dumpAll || dumpPackage != null) { 14481 synchronized (mPidsSelfLocked) { 14482 boolean printed = false; 14483 for (int i=0; i<mPidsSelfLocked.size(); i++) { 14484 ProcessRecord r = mPidsSelfLocked.valueAt(i); 14485 if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) { 14486 continue; 14487 } 14488 if (!printed) { 14489 if (needSep) pw.println(); 14490 needSep = true; 14491 pw.println(" PID mappings:"); 14492 printed = true; 14493 printedAnything = true; 14494 } 14495 pw.print(" PID #"); pw.print(mPidsSelfLocked.keyAt(i)); 14496 pw.print(": "); pw.println(mPidsSelfLocked.valueAt(i)); 14497 } 14498 } 14499 } 14500 14501 if (mForegroundProcesses.size() > 0) { 14502 synchronized (mPidsSelfLocked) { 14503 boolean printed = false; 14504 for (int i=0; i<mForegroundProcesses.size(); i++) { 14505 ProcessRecord r = mPidsSelfLocked.get( 14506 mForegroundProcesses.valueAt(i).pid); 14507 if (dumpPackage != null && (r == null 14508 || !r.pkgList.containsKey(dumpPackage))) { 14509 continue; 14510 } 14511 if (!printed) { 14512 if (needSep) pw.println(); 14513 needSep = true; 14514 pw.println(" Foreground Processes:"); 14515 printed = true; 14516 printedAnything = true; 14517 } 14518 pw.print(" PID #"); pw.print(mForegroundProcesses.keyAt(i)); 14519 pw.print(": "); pw.println(mForegroundProcesses.valueAt(i)); 14520 } 14521 } 14522 } 14523 14524 if (mPersistentStartingProcesses.size() > 0) { 14525 if (needSep) pw.println(); 14526 needSep = true; 14527 printedAnything = true; 14528 pw.println(" Persisent processes that are starting:"); 14529 dumpProcessList(pw, this, mPersistentStartingProcesses, " ", 14530 "Starting Norm", "Restarting PERS", dumpPackage); 14531 } 14532 14533 if (mRemovedProcesses.size() > 0) { 14534 if (needSep) pw.println(); 14535 needSep = true; 14536 printedAnything = true; 14537 pw.println(" Processes that are being removed:"); 14538 dumpProcessList(pw, this, mRemovedProcesses, " ", 14539 "Removed Norm", "Removed PERS", dumpPackage); 14540 } 14541 14542 if (mProcessesOnHold.size() > 0) { 14543 if (needSep) pw.println(); 14544 needSep = true; 14545 printedAnything = true; 14546 pw.println(" Processes that are on old until the system is ready:"); 14547 dumpProcessList(pw, this, mProcessesOnHold, " ", 14548 "OnHold Norm", "OnHold PERS", dumpPackage); 14549 } 14550 14551 needSep = dumpProcessesToGc(fd, pw, args, opti, needSep, dumpAll, dumpPackage); 14552 14553 needSep = mAppErrors.dumpLocked(fd, pw, needSep, dumpPackage); 14554 if (needSep) { 14555 printedAnything = true; 14556 } 14557 14558 if (dumpPackage == null) { 14559 pw.println(); 14560 needSep = false; 14561 mUserController.dump(pw, dumpAll); 14562 } 14563 if (mHomeProcess != null && (dumpPackage == null 14564 || mHomeProcess.pkgList.containsKey(dumpPackage))) { 14565 if (needSep) { 14566 pw.println(); 14567 needSep = false; 14568 } 14569 pw.println(" mHomeProcess: " + mHomeProcess); 14570 } 14571 if (mPreviousProcess != null && (dumpPackage == null 14572 || mPreviousProcess.pkgList.containsKey(dumpPackage))) { 14573 if (needSep) { 14574 pw.println(); 14575 needSep = false; 14576 } 14577 pw.println(" mPreviousProcess: " + mPreviousProcess); 14578 } 14579 if (dumpAll) { 14580 StringBuilder sb = new StringBuilder(128); 14581 sb.append(" mPreviousProcessVisibleTime: "); 14582 TimeUtils.formatDuration(mPreviousProcessVisibleTime, sb); 14583 pw.println(sb); 14584 } 14585 if (mHeavyWeightProcess != null && (dumpPackage == null 14586 || mHeavyWeightProcess.pkgList.containsKey(dumpPackage))) { 14587 if (needSep) { 14588 pw.println(); 14589 needSep = false; 14590 } 14591 pw.println(" mHeavyWeightProcess: " + mHeavyWeightProcess); 14592 } 14593 if (dumpPackage == null) { 14594 pw.println(" mGlobalConfiguration: " + getGlobalConfiguration()); 14595 mStackSupervisor.dumpDisplayConfigs(pw, " "); 14596 } 14597 if (dumpAll) { 14598 pw.println(" mConfigWillChange: " + getFocusedStack().mConfigWillChange); 14599 if (mCompatModePackages.getPackages().size() > 0) { 14600 boolean printed = false; 14601 for (Map.Entry<String, Integer> entry 14602 : mCompatModePackages.getPackages().entrySet()) { 14603 String pkg = entry.getKey(); 14604 int mode = entry.getValue(); 14605 if (dumpPackage != null && !dumpPackage.equals(pkg)) { 14606 continue; 14607 } 14608 if (!printed) { 14609 pw.println(" mScreenCompatPackages:"); 14610 printed = true; 14611 } 14612 pw.print(" "); pw.print(pkg); pw.print(": "); 14613 pw.print(mode); pw.println(); 14614 } 14615 } 14616 } 14617 if (dumpPackage == null) { 14618 pw.println(" mWakefulness=" 14619 + PowerManagerInternal.wakefulnessToString(mWakefulness)); 14620 pw.println(" mSleepTokens=" + mSleepTokens); 14621 pw.println(" mSleeping=" + mSleeping); 14622 pw.println(" mShuttingDown=" + mShuttingDown + " mTestPssMode=" + mTestPssMode); 14623 if (mRunningVoice != null) { 14624 pw.println(" mRunningVoice=" + mRunningVoice); 14625 pw.println(" mVoiceWakeLock" + mVoiceWakeLock); 14626 } 14627 } 14628 if (mDebugApp != null || mOrigDebugApp != null || mDebugTransient 14629 || mOrigWaitForDebugger) { 14630 if (dumpPackage == null || dumpPackage.equals(mDebugApp) 14631 || dumpPackage.equals(mOrigDebugApp)) { 14632 if (needSep) { 14633 pw.println(); 14634 needSep = false; 14635 } 14636 pw.println(" mDebugApp=" + mDebugApp + "/orig=" + mOrigDebugApp 14637 + " mDebugTransient=" + mDebugTransient 14638 + " mOrigWaitForDebugger=" + mOrigWaitForDebugger); 14639 } 14640 } 14641 if (mCurAppTimeTracker != null) { 14642 mCurAppTimeTracker.dumpWithHeader(pw, " ", true); 14643 } 14644 if (mMemWatchProcesses.getMap().size() > 0) { 14645 pw.println(" Mem watch processes:"); 14646 final ArrayMap<String, SparseArray<Pair<Long, String>>> procs 14647 = mMemWatchProcesses.getMap(); 14648 for (int i=0; i<procs.size(); i++) { 14649 final String proc = procs.keyAt(i); 14650 final SparseArray<Pair<Long, String>> uids = procs.valueAt(i); 14651 for (int j=0; j<uids.size(); j++) { 14652 if (needSep) { 14653 pw.println(); 14654 needSep = false; 14655 } 14656 StringBuilder sb = new StringBuilder(); 14657 sb.append(" ").append(proc).append('/'); 14658 UserHandle.formatUid(sb, uids.keyAt(j)); 14659 Pair<Long, String> val = uids.valueAt(j); 14660 sb.append(": "); DebugUtils.sizeValueToString(val.first, sb); 14661 if (val.second != null) { 14662 sb.append(", report to ").append(val.second); 14663 } 14664 pw.println(sb.toString()); 14665 } 14666 } 14667 pw.print(" mMemWatchDumpProcName="); pw.println(mMemWatchDumpProcName); 14668 pw.print(" mMemWatchDumpFile="); pw.println(mMemWatchDumpFile); 14669 pw.print(" mMemWatchDumpPid="); pw.print(mMemWatchDumpPid); 14670 pw.print(" mMemWatchDumpUid="); pw.println(mMemWatchDumpUid); 14671 } 14672 if (mTrackAllocationApp != null) { 14673 if (dumpPackage == null || dumpPackage.equals(mTrackAllocationApp)) { 14674 if (needSep) { 14675 pw.println(); 14676 needSep = false; 14677 } 14678 pw.println(" mTrackAllocationApp=" + mTrackAllocationApp); 14679 } 14680 } 14681 if (mProfileApp != null || mProfileProc != null || mProfileFile != null 14682 || mProfileFd != null) { 14683 if (dumpPackage == null || dumpPackage.equals(mProfileApp)) { 14684 if (needSep) { 14685 pw.println(); 14686 needSep = false; 14687 } 14688 pw.println(" mProfileApp=" + mProfileApp + " mProfileProc=" + mProfileProc); 14689 pw.println(" mProfileFile=" + mProfileFile + " mProfileFd=" + mProfileFd); 14690 pw.println(" mSamplingInterval=" + mSamplingInterval + " mAutoStopProfiler=" 14691 + mAutoStopProfiler); 14692 pw.println(" mProfileType=" + mProfileType); 14693 } 14694 } 14695 if (mNativeDebuggingApp != null) { 14696 if (dumpPackage == null || dumpPackage.equals(mNativeDebuggingApp)) { 14697 if (needSep) { 14698 pw.println(); 14699 needSep = false; 14700 } 14701 pw.println(" mNativeDebuggingApp=" + mNativeDebuggingApp); 14702 } 14703 } 14704 if (dumpPackage == null) { 14705 if (mAlwaysFinishActivities || mLenientBackgroundCheck) { 14706 pw.println(" mAlwaysFinishActivities=" + mAlwaysFinishActivities 14707 + " mLenientBackgroundCheck=" + mLenientBackgroundCheck); 14708 } 14709 if (mController != null) { 14710 pw.println(" mController=" + mController 14711 + " mControllerIsAMonkey=" + mControllerIsAMonkey); 14712 } 14713 if (dumpAll) { 14714 pw.println(" Total persistent processes: " + numPers); 14715 pw.println(" mProcessesReady=" + mProcessesReady 14716 + " mSystemReady=" + mSystemReady 14717 + " mBooted=" + mBooted 14718 + " mFactoryTest=" + mFactoryTest); 14719 pw.println(" mBooting=" + mBooting 14720 + " mCallFinishBooting=" + mCallFinishBooting 14721 + " mBootAnimationComplete=" + mBootAnimationComplete); 14722 pw.print(" mLastPowerCheckRealtime="); 14723 TimeUtils.formatDuration(mLastPowerCheckRealtime, pw); 14724 pw.println(""); 14725 pw.print(" mLastPowerCheckUptime="); 14726 TimeUtils.formatDuration(mLastPowerCheckUptime, pw); 14727 pw.println(""); 14728 pw.println(" mGoingToSleep=" + mStackSupervisor.mGoingToSleep); 14729 pw.println(" mLaunchingActivity=" + mStackSupervisor.mLaunchingActivity); 14730 pw.println(" mAdjSeq=" + mAdjSeq + " mLruSeq=" + mLruSeq); 14731 pw.println(" mNumNonCachedProcs=" + mNumNonCachedProcs 14732 + " (" + mLruProcesses.size() + " total)" 14733 + " mNumCachedHiddenProcs=" + mNumCachedHiddenProcs 14734 + " mNumServiceProcs=" + mNumServiceProcs 14735 + " mNewNumServiceProcs=" + mNewNumServiceProcs); 14736 pw.println(" mAllowLowerMemLevel=" + mAllowLowerMemLevel 14737 + " mLastMemoryLevel=" + mLastMemoryLevel 14738 + " mLastNumProcesses=" + mLastNumProcesses); 14739 long now = SystemClock.uptimeMillis(); 14740 pw.print(" mLastIdleTime="); 14741 TimeUtils.formatDuration(now, mLastIdleTime, pw); 14742 pw.print(" mLowRamSinceLastIdle="); 14743 TimeUtils.formatDuration(getLowRamTimeSinceIdle(now), pw); 14744 pw.println(); 14745 } 14746 } 14747 14748 if (!printedAnything) { 14749 pw.println(" (nothing)"); 14750 } 14751 } 14752 14753 boolean dumpProcessesToGc(FileDescriptor fd, PrintWriter pw, String[] args, 14754 int opti, boolean needSep, boolean dumpAll, String dumpPackage) { 14755 if (mProcessesToGc.size() > 0) { 14756 boolean printed = false; 14757 long now = SystemClock.uptimeMillis(); 14758 for (int i=0; i<mProcessesToGc.size(); i++) { 14759 ProcessRecord proc = mProcessesToGc.get(i); 14760 if (dumpPackage != null && !dumpPackage.equals(proc.info.packageName)) { 14761 continue; 14762 } 14763 if (!printed) { 14764 if (needSep) pw.println(); 14765 needSep = true; 14766 pw.println(" Processes that are waiting to GC:"); 14767 printed = true; 14768 } 14769 pw.print(" Process "); pw.println(proc); 14770 pw.print(" lowMem="); pw.print(proc.reportLowMemory); 14771 pw.print(", last gced="); 14772 pw.print(now-proc.lastRequestedGc); 14773 pw.print(" ms ago, last lowMem="); 14774 pw.print(now-proc.lastLowMemory); 14775 pw.println(" ms ago"); 14776 14777 } 14778 } 14779 return needSep; 14780 } 14781 14782 void printOomLevel(PrintWriter pw, String name, int adj) { 14783 pw.print(" "); 14784 if (adj >= 0) { 14785 pw.print(' '); 14786 if (adj < 10) pw.print(' '); 14787 } else { 14788 if (adj > -10) pw.print(' '); 14789 } 14790 pw.print(adj); 14791 pw.print(": "); 14792 pw.print(name); 14793 pw.print(" ("); 14794 pw.print(stringifySize(mProcessList.getMemLevel(adj), 1024)); 14795 pw.println(")"); 14796 } 14797 14798 boolean dumpOomLocked(FileDescriptor fd, PrintWriter pw, String[] args, 14799 int opti, boolean dumpAll) { 14800 boolean needSep = false; 14801 14802 if (mLruProcesses.size() > 0) { 14803 if (needSep) pw.println(); 14804 needSep = true; 14805 pw.println(" OOM levels:"); 14806 printOomLevel(pw, "SYSTEM_ADJ", ProcessList.SYSTEM_ADJ); 14807 printOomLevel(pw, "PERSISTENT_PROC_ADJ", ProcessList.PERSISTENT_PROC_ADJ); 14808 printOomLevel(pw, "PERSISTENT_SERVICE_ADJ", ProcessList.PERSISTENT_SERVICE_ADJ); 14809 printOomLevel(pw, "FOREGROUND_APP_ADJ", ProcessList.FOREGROUND_APP_ADJ); 14810 printOomLevel(pw, "VISIBLE_APP_ADJ", ProcessList.VISIBLE_APP_ADJ); 14811 printOomLevel(pw, "PERCEPTIBLE_APP_ADJ", ProcessList.PERCEPTIBLE_APP_ADJ); 14812 printOomLevel(pw, "BACKUP_APP_ADJ", ProcessList.BACKUP_APP_ADJ); 14813 printOomLevel(pw, "HEAVY_WEIGHT_APP_ADJ", ProcessList.HEAVY_WEIGHT_APP_ADJ); 14814 printOomLevel(pw, "SERVICE_ADJ", ProcessList.SERVICE_ADJ); 14815 printOomLevel(pw, "HOME_APP_ADJ", ProcessList.HOME_APP_ADJ); 14816 printOomLevel(pw, "PREVIOUS_APP_ADJ", ProcessList.PREVIOUS_APP_ADJ); 14817 printOomLevel(pw, "SERVICE_B_ADJ", ProcessList.SERVICE_B_ADJ); 14818 printOomLevel(pw, "CACHED_APP_MIN_ADJ", ProcessList.CACHED_APP_MIN_ADJ); 14819 printOomLevel(pw, "CACHED_APP_MAX_ADJ", ProcessList.CACHED_APP_MAX_ADJ); 14820 14821 if (needSep) pw.println(); 14822 pw.print(" Process OOM control ("); pw.print(mLruProcesses.size()); 14823 pw.print(" total, non-act at "); 14824 pw.print(mLruProcesses.size()-mLruProcessActivityStart); 14825 pw.print(", non-svc at "); 14826 pw.print(mLruProcesses.size()-mLruProcessServiceStart); 14827 pw.println("):"); 14828 dumpProcessOomList(pw, this, mLruProcesses, " ", "Proc", "PERS", true, null); 14829 needSep = true; 14830 } 14831 14832 dumpProcessesToGc(fd, pw, args, opti, needSep, dumpAll, null); 14833 14834 pw.println(); 14835 pw.println(" mHomeProcess: " + mHomeProcess); 14836 pw.println(" mPreviousProcess: " + mPreviousProcess); 14837 if (mHeavyWeightProcess != null) { 14838 pw.println(" mHeavyWeightProcess: " + mHeavyWeightProcess); 14839 } 14840 14841 return true; 14842 } 14843 14844 /** 14845 * There are three ways to call this: 14846 * - no provider specified: dump all the providers 14847 * - a flattened component name that matched an existing provider was specified as the 14848 * first arg: dump that one provider 14849 * - the first arg isn't the flattened component name of an existing provider: 14850 * dump all providers whose component contains the first arg as a substring 14851 */ 14852 protected boolean dumpProvider(FileDescriptor fd, PrintWriter pw, String name, String[] args, 14853 int opti, boolean dumpAll) { 14854 return mProviderMap.dumpProvider(fd, pw, name, args, opti, dumpAll); 14855 } 14856 14857 static class ItemMatcher { 14858 ArrayList<ComponentName> components; 14859 ArrayList<String> strings; 14860 ArrayList<Integer> objects; 14861 boolean all; 14862 14863 ItemMatcher() { 14864 all = true; 14865 } 14866 14867 void build(String name) { 14868 ComponentName componentName = ComponentName.unflattenFromString(name); 14869 if (componentName != null) { 14870 if (components == null) { 14871 components = new ArrayList<ComponentName>(); 14872 } 14873 components.add(componentName); 14874 all = false; 14875 } else { 14876 int objectId = 0; 14877 // Not a '/' separated full component name; maybe an object ID? 14878 try { 14879 objectId = Integer.parseInt(name, 16); 14880 if (objects == null) { 14881 objects = new ArrayList<Integer>(); 14882 } 14883 objects.add(objectId); 14884 all = false; 14885 } catch (RuntimeException e) { 14886 // Not an integer; just do string match. 14887 if (strings == null) { 14888 strings = new ArrayList<String>(); 14889 } 14890 strings.add(name); 14891 all = false; 14892 } 14893 } 14894 } 14895 14896 int build(String[] args, int opti) { 14897 for (; opti<args.length; opti++) { 14898 String name = args[opti]; 14899 if ("--".equals(name)) { 14900 return opti+1; 14901 } 14902 build(name); 14903 } 14904 return opti; 14905 } 14906 14907 boolean match(Object object, ComponentName comp) { 14908 if (all) { 14909 return true; 14910 } 14911 if (components != null) { 14912 for (int i=0; i<components.size(); i++) { 14913 if (components.get(i).equals(comp)) { 14914 return true; 14915 } 14916 } 14917 } 14918 if (objects != null) { 14919 for (int i=0; i<objects.size(); i++) { 14920 if (System.identityHashCode(object) == objects.get(i)) { 14921 return true; 14922 } 14923 } 14924 } 14925 if (strings != null) { 14926 String flat = comp.flattenToString(); 14927 for (int i=0; i<strings.size(); i++) { 14928 if (flat.contains(strings.get(i))) { 14929 return true; 14930 } 14931 } 14932 } 14933 return false; 14934 } 14935 } 14936 14937 /** 14938 * There are three things that cmd can be: 14939 * - a flattened component name that matches an existing activity 14940 * - the cmd arg isn't the flattened component name of an existing activity: 14941 * dump all activity whose component contains the cmd as a substring 14942 * - A hex number of the ActivityRecord object instance. 14943 */ 14944 protected boolean dumpActivity(FileDescriptor fd, PrintWriter pw, String name, String[] args, 14945 int opti, boolean dumpAll, boolean dumpVisibleStacks) { 14946 ArrayList<ActivityRecord> activities; 14947 14948 synchronized (this) { 14949 activities = mStackSupervisor.getDumpActivitiesLocked(name, dumpVisibleStacks); 14950 } 14951 14952 if (activities.size() <= 0) { 14953 return false; 14954 } 14955 14956 String[] newArgs = new String[args.length - opti]; 14957 System.arraycopy(args, opti, newArgs, 0, args.length - opti); 14958 14959 TaskRecord lastTask = null; 14960 boolean needSep = false; 14961 for (int i=activities.size()-1; i>=0; i--) { 14962 ActivityRecord r = activities.get(i); 14963 if (needSep) { 14964 pw.println(); 14965 } 14966 needSep = true; 14967 synchronized (this) { 14968 if (lastTask != r.task) { 14969 lastTask = r.task; 14970 pw.print("TASK "); pw.print(lastTask.affinity); 14971 pw.print(" id="); pw.print(lastTask.taskId); 14972 pw.print(" userId="); pw.println(lastTask.userId); 14973 if (dumpAll) { 14974 lastTask.dump(pw, " "); 14975 } 14976 } 14977 } 14978 dumpActivity(" ", fd, pw, activities.get(i), newArgs, dumpAll); 14979 } 14980 return true; 14981 } 14982 14983 /** 14984 * Invokes IApplicationThread.dumpActivity() on the thread of the specified activity if 14985 * there is a thread associated with the activity. 14986 */ 14987 private void dumpActivity(String prefix, FileDescriptor fd, PrintWriter pw, 14988 final ActivityRecord r, String[] args, boolean dumpAll) { 14989 String innerPrefix = prefix + " "; 14990 synchronized (this) { 14991 pw.print(prefix); pw.print("ACTIVITY "); pw.print(r.shortComponentName); 14992 pw.print(" "); pw.print(Integer.toHexString(System.identityHashCode(r))); 14993 pw.print(" pid="); 14994 if (r.app != null) pw.println(r.app.pid); 14995 else pw.println("(not running)"); 14996 if (dumpAll) { 14997 r.dump(pw, innerPrefix); 14998 } 14999 } 15000 if (r.app != null && r.app.thread != null) { 15001 // flush anything that is already in the PrintWriter since the thread is going 15002 // to write to the file descriptor directly 15003 pw.flush(); 15004 try { 15005 TransferPipe tp = new TransferPipe(); 15006 try { 15007 r.app.thread.dumpActivity(tp.getWriteFd(), 15008 r.appToken, innerPrefix, args); 15009 tp.go(fd); 15010 } finally { 15011 tp.kill(); 15012 } 15013 } catch (IOException e) { 15014 pw.println(innerPrefix + "Failure while dumping the activity: " + e); 15015 } catch (RemoteException e) { 15016 pw.println(innerPrefix + "Got a RemoteException while dumping the activity"); 15017 } 15018 } 15019 } 15020 15021 void dumpBroadcastsLocked(FileDescriptor fd, PrintWriter pw, String[] args, 15022 int opti, boolean dumpAll, String dumpPackage) { 15023 boolean needSep = false; 15024 boolean onlyHistory = false; 15025 boolean printedAnything = false; 15026 15027 if ("history".equals(dumpPackage)) { 15028 if (opti < args.length && "-s".equals(args[opti])) { 15029 dumpAll = false; 15030 } 15031 onlyHistory = true; 15032 dumpPackage = null; 15033 } 15034 15035 pw.println("ACTIVITY MANAGER BROADCAST STATE (dumpsys activity broadcasts)"); 15036 if (!onlyHistory && dumpAll) { 15037 if (mRegisteredReceivers.size() > 0) { 15038 boolean printed = false; 15039 Iterator it = mRegisteredReceivers.values().iterator(); 15040 while (it.hasNext()) { 15041 ReceiverList r = (ReceiverList)it.next(); 15042 if (dumpPackage != null && (r.app == null || 15043 !dumpPackage.equals(r.app.info.packageName))) { 15044 continue; 15045 } 15046 if (!printed) { 15047 pw.println(" Registered Receivers:"); 15048 needSep = true; 15049 printed = true; 15050 printedAnything = true; 15051 } 15052 pw.print(" * "); pw.println(r); 15053 r.dump(pw, " "); 15054 } 15055 } 15056 15057 if (mReceiverResolver.dump(pw, needSep ? 15058 "\n Receiver Resolver Table:" : " Receiver Resolver Table:", 15059 " ", dumpPackage, false, false)) { 15060 needSep = true; 15061 printedAnything = true; 15062 } 15063 } 15064 15065 for (BroadcastQueue q : mBroadcastQueues) { 15066 needSep = q.dumpLocked(fd, pw, args, opti, dumpAll, dumpPackage, needSep); 15067 printedAnything |= needSep; 15068 } 15069 15070 needSep = true; 15071 15072 if (!onlyHistory && mStickyBroadcasts != null && dumpPackage == null) { 15073 for (int user=0; user<mStickyBroadcasts.size(); user++) { 15074 if (needSep) { 15075 pw.println(); 15076 } 15077 needSep = true; 15078 printedAnything = true; 15079 pw.print(" Sticky broadcasts for user "); 15080 pw.print(mStickyBroadcasts.keyAt(user)); pw.println(":"); 15081 StringBuilder sb = new StringBuilder(128); 15082 for (Map.Entry<String, ArrayList<Intent>> ent 15083 : mStickyBroadcasts.valueAt(user).entrySet()) { 15084 pw.print(" * Sticky action "); pw.print(ent.getKey()); 15085 if (dumpAll) { 15086 pw.println(":"); 15087 ArrayList<Intent> intents = ent.getValue(); 15088 final int N = intents.size(); 15089 for (int i=0; i<N; i++) { 15090 sb.setLength(0); 15091 sb.append(" Intent: "); 15092 intents.get(i).toShortString(sb, false, true, false, false); 15093 pw.println(sb.toString()); 15094 Bundle bundle = intents.get(i).getExtras(); 15095 if (bundle != null) { 15096 pw.print(" "); 15097 pw.println(bundle.toString()); 15098 } 15099 } 15100 } else { 15101 pw.println(""); 15102 } 15103 } 15104 } 15105 } 15106 15107 if (!onlyHistory && dumpAll) { 15108 pw.println(); 15109 for (BroadcastQueue queue : mBroadcastQueues) { 15110 pw.println(" mBroadcastsScheduled [" + queue.mQueueName + "]=" 15111 + queue.mBroadcastsScheduled); 15112 } 15113 pw.println(" mHandler:"); 15114 mHandler.dump(new PrintWriterPrinter(pw), " "); 15115 needSep = true; 15116 printedAnything = true; 15117 } 15118 15119 if (!printedAnything) { 15120 pw.println(" (nothing)"); 15121 } 15122 } 15123 15124 void dumpBroadcastStatsLocked(FileDescriptor fd, PrintWriter pw, String[] args, 15125 int opti, boolean dumpAll, String dumpPackage) { 15126 if (mCurBroadcastStats == null) { 15127 return; 15128 } 15129 15130 pw.println("ACTIVITY MANAGER BROADCAST STATS STATE (dumpsys activity broadcast-stats)"); 15131 final long now = SystemClock.elapsedRealtime(); 15132 if (mLastBroadcastStats != null) { 15133 pw.print(" Last stats (from "); 15134 TimeUtils.formatDuration(mLastBroadcastStats.mStartRealtime, now, pw); 15135 pw.print(" to "); 15136 TimeUtils.formatDuration(mLastBroadcastStats.mEndRealtime, now, pw); 15137 pw.print(", "); 15138 TimeUtils.formatDuration(mLastBroadcastStats.mEndUptime 15139 - mLastBroadcastStats.mStartUptime, pw); 15140 pw.println(" uptime):"); 15141 if (!mLastBroadcastStats.dumpStats(pw, " ", dumpPackage)) { 15142 pw.println(" (nothing)"); 15143 } 15144 pw.println(); 15145 } 15146 pw.print(" Current stats (from "); 15147 TimeUtils.formatDuration(mCurBroadcastStats.mStartRealtime, now, pw); 15148 pw.print(" to now, "); 15149 TimeUtils.formatDuration(SystemClock.uptimeMillis() 15150 - mCurBroadcastStats.mStartUptime, pw); 15151 pw.println(" uptime):"); 15152 if (!mCurBroadcastStats.dumpStats(pw, " ", dumpPackage)) { 15153 pw.println(" (nothing)"); 15154 } 15155 } 15156 15157 void dumpBroadcastStatsCheckinLocked(FileDescriptor fd, PrintWriter pw, String[] args, 15158 int opti, boolean fullCheckin, String dumpPackage) { 15159 if (mCurBroadcastStats == null) { 15160 return; 15161 } 15162 15163 if (mLastBroadcastStats != null) { 15164 mLastBroadcastStats.dumpCheckinStats(pw, dumpPackage); 15165 if (fullCheckin) { 15166 mLastBroadcastStats = null; 15167 return; 15168 } 15169 } 15170 mCurBroadcastStats.dumpCheckinStats(pw, dumpPackage); 15171 if (fullCheckin) { 15172 mCurBroadcastStats = null; 15173 } 15174 } 15175 15176 void dumpProvidersLocked(FileDescriptor fd, PrintWriter pw, String[] args, 15177 int opti, boolean dumpAll, String dumpPackage) { 15178 boolean needSep; 15179 boolean printedAnything = false; 15180 15181 ItemMatcher matcher = new ItemMatcher(); 15182 matcher.build(args, opti); 15183 15184 pw.println("ACTIVITY MANAGER CONTENT PROVIDERS (dumpsys activity providers)"); 15185 15186 needSep = mProviderMap.dumpProvidersLocked(pw, dumpAll, dumpPackage); 15187 printedAnything |= needSep; 15188 15189 if (mLaunchingProviders.size() > 0) { 15190 boolean printed = false; 15191 for (int i=mLaunchingProviders.size()-1; i>=0; i--) { 15192 ContentProviderRecord r = mLaunchingProviders.get(i); 15193 if (dumpPackage != null && !dumpPackage.equals(r.name.getPackageName())) { 15194 continue; 15195 } 15196 if (!printed) { 15197 if (needSep) pw.println(); 15198 needSep = true; 15199 pw.println(" Launching content providers:"); 15200 printed = true; 15201 printedAnything = true; 15202 } 15203 pw.print(" Launching #"); pw.print(i); pw.print(": "); 15204 pw.println(r); 15205 } 15206 } 15207 15208 if (!printedAnything) { 15209 pw.println(" (nothing)"); 15210 } 15211 } 15212 15213 void dumpPermissionsLocked(FileDescriptor fd, PrintWriter pw, String[] args, 15214 int opti, boolean dumpAll, String dumpPackage) { 15215 boolean needSep = false; 15216 boolean printedAnything = false; 15217 15218 pw.println("ACTIVITY MANAGER URI PERMISSIONS (dumpsys activity permissions)"); 15219 15220 if (mGrantedUriPermissions.size() > 0) { 15221 boolean printed = false; 15222 int dumpUid = -2; 15223 if (dumpPackage != null) { 15224 try { 15225 dumpUid = mContext.getPackageManager().getPackageUidAsUser(dumpPackage, 15226 MATCH_UNINSTALLED_PACKAGES, 0); 15227 } catch (NameNotFoundException e) { 15228 dumpUid = -1; 15229 } 15230 } 15231 for (int i=0; i<mGrantedUriPermissions.size(); i++) { 15232 int uid = mGrantedUriPermissions.keyAt(i); 15233 if (dumpUid >= -1 && UserHandle.getAppId(uid) != dumpUid) { 15234 continue; 15235 } 15236 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i); 15237 if (!printed) { 15238 if (needSep) pw.println(); 15239 needSep = true; 15240 pw.println(" Granted Uri Permissions:"); 15241 printed = true; 15242 printedAnything = true; 15243 } 15244 pw.print(" * UID "); pw.print(uid); pw.println(" holds:"); 15245 for (UriPermission perm : perms.values()) { 15246 pw.print(" "); pw.println(perm); 15247 if (dumpAll) { 15248 perm.dump(pw, " "); 15249 } 15250 } 15251 } 15252 } 15253 15254 if (!printedAnything) { 15255 pw.println(" (nothing)"); 15256 } 15257 } 15258 15259 void dumpPendingIntentsLocked(FileDescriptor fd, PrintWriter pw, String[] args, 15260 int opti, boolean dumpAll, String dumpPackage) { 15261 boolean printed = false; 15262 15263 pw.println("ACTIVITY MANAGER PENDING INTENTS (dumpsys activity intents)"); 15264 15265 if (mIntentSenderRecords.size() > 0) { 15266 Iterator<WeakReference<PendingIntentRecord>> it 15267 = mIntentSenderRecords.values().iterator(); 15268 while (it.hasNext()) { 15269 WeakReference<PendingIntentRecord> ref = it.next(); 15270 PendingIntentRecord rec = ref != null ? ref.get(): null; 15271 if (dumpPackage != null && (rec == null 15272 || !dumpPackage.equals(rec.key.packageName))) { 15273 continue; 15274 } 15275 printed = true; 15276 if (rec != null) { 15277 pw.print(" * "); pw.println(rec); 15278 if (dumpAll) { 15279 rec.dump(pw, " "); 15280 } 15281 } else { 15282 pw.print(" * "); pw.println(ref); 15283 } 15284 } 15285 } 15286 15287 if (!printed) { 15288 pw.println(" (nothing)"); 15289 } 15290 } 15291 15292 private static final int dumpProcessList(PrintWriter pw, 15293 ActivityManagerService service, List list, 15294 String prefix, String normalLabel, String persistentLabel, 15295 String dumpPackage) { 15296 int numPers = 0; 15297 final int N = list.size()-1; 15298 for (int i=N; i>=0; i--) { 15299 ProcessRecord r = (ProcessRecord)list.get(i); 15300 if (dumpPackage != null && !dumpPackage.equals(r.info.packageName)) { 15301 continue; 15302 } 15303 pw.println(String.format("%s%s #%2d: %s", 15304 prefix, (r.persistent ? persistentLabel : normalLabel), 15305 i, r.toString())); 15306 if (r.persistent) { 15307 numPers++; 15308 } 15309 } 15310 return numPers; 15311 } 15312 15313 private static final boolean dumpProcessOomList(PrintWriter pw, 15314 ActivityManagerService service, List<ProcessRecord> origList, 15315 String prefix, String normalLabel, String persistentLabel, 15316 boolean inclDetails, String dumpPackage) { 15317 15318 ArrayList<Pair<ProcessRecord, Integer>> list 15319 = new ArrayList<Pair<ProcessRecord, Integer>>(origList.size()); 15320 for (int i=0; i<origList.size(); i++) { 15321 ProcessRecord r = origList.get(i); 15322 if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) { 15323 continue; 15324 } 15325 list.add(new Pair<ProcessRecord, Integer>(origList.get(i), i)); 15326 } 15327 15328 if (list.size() <= 0) { 15329 return false; 15330 } 15331 15332 Comparator<Pair<ProcessRecord, Integer>> comparator 15333 = new Comparator<Pair<ProcessRecord, Integer>>() { 15334 @Override 15335 public int compare(Pair<ProcessRecord, Integer> object1, 15336 Pair<ProcessRecord, Integer> object2) { 15337 if (object1.first.setAdj != object2.first.setAdj) { 15338 return object1.first.setAdj > object2.first.setAdj ? -1 : 1; 15339 } 15340 if (object1.first.setProcState != object2.first.setProcState) { 15341 return object1.first.setProcState > object2.first.setProcState ? -1 : 1; 15342 } 15343 if (object1.second.intValue() != object2.second.intValue()) { 15344 return object1.second.intValue() > object2.second.intValue() ? -1 : 1; 15345 } 15346 return 0; 15347 } 15348 }; 15349 15350 Collections.sort(list, comparator); 15351 15352 final long curRealtime = SystemClock.elapsedRealtime(); 15353 final long realtimeSince = curRealtime - service.mLastPowerCheckRealtime; 15354 final long curUptime = SystemClock.uptimeMillis(); 15355 final long uptimeSince = curUptime - service.mLastPowerCheckUptime; 15356 15357 for (int i=list.size()-1; i>=0; i--) { 15358 ProcessRecord r = list.get(i).first; 15359 String oomAdj = ProcessList.makeOomAdjString(r.setAdj); 15360 char schedGroup; 15361 switch (r.setSchedGroup) { 15362 case ProcessList.SCHED_GROUP_BACKGROUND: 15363 schedGroup = 'B'; 15364 break; 15365 case ProcessList.SCHED_GROUP_DEFAULT: 15366 schedGroup = 'F'; 15367 break; 15368 case ProcessList.SCHED_GROUP_TOP_APP: 15369 schedGroup = 'T'; 15370 break; 15371 default: 15372 schedGroup = '?'; 15373 break; 15374 } 15375 char foreground; 15376 if (r.foregroundActivities) { 15377 foreground = 'A'; 15378 } else if (r.foregroundServices) { 15379 foreground = 'S'; 15380 } else { 15381 foreground = ' '; 15382 } 15383 String procState = ProcessList.makeProcStateString(r.curProcState); 15384 pw.print(prefix); 15385 pw.print(r.persistent ? persistentLabel : normalLabel); 15386 pw.print(" #"); 15387 int num = (origList.size()-1)-list.get(i).second; 15388 if (num < 10) pw.print(' '); 15389 pw.print(num); 15390 pw.print(": "); 15391 pw.print(oomAdj); 15392 pw.print(' '); 15393 pw.print(schedGroup); 15394 pw.print('/'); 15395 pw.print(foreground); 15396 pw.print('/'); 15397 pw.print(procState); 15398 pw.print(" trm:"); 15399 if (r.trimMemoryLevel < 10) pw.print(' '); 15400 pw.print(r.trimMemoryLevel); 15401 pw.print(' '); 15402 pw.print(r.toShortString()); 15403 pw.print(" ("); 15404 pw.print(r.adjType); 15405 pw.println(')'); 15406 if (r.adjSource != null || r.adjTarget != null) { 15407 pw.print(prefix); 15408 pw.print(" "); 15409 if (r.adjTarget instanceof ComponentName) { 15410 pw.print(((ComponentName)r.adjTarget).flattenToShortString()); 15411 } else if (r.adjTarget != null) { 15412 pw.print(r.adjTarget.toString()); 15413 } else { 15414 pw.print("{null}"); 15415 } 15416 pw.print("<="); 15417 if (r.adjSource instanceof ProcessRecord) { 15418 pw.print("Proc{"); 15419 pw.print(((ProcessRecord)r.adjSource).toShortString()); 15420 pw.println("}"); 15421 } else if (r.adjSource != null) { 15422 pw.println(r.adjSource.toString()); 15423 } else { 15424 pw.println("{null}"); 15425 } 15426 } 15427 if (inclDetails) { 15428 pw.print(prefix); 15429 pw.print(" "); 15430 pw.print("oom: max="); pw.print(r.maxAdj); 15431 pw.print(" curRaw="); pw.print(r.curRawAdj); 15432 pw.print(" setRaw="); pw.print(r.setRawAdj); 15433 pw.print(" cur="); pw.print(r.curAdj); 15434 pw.print(" set="); pw.println(r.setAdj); 15435 pw.print(prefix); 15436 pw.print(" "); 15437 pw.print("state: cur="); pw.print(ProcessList.makeProcStateString(r.curProcState)); 15438 pw.print(" set="); pw.print(ProcessList.makeProcStateString(r.setProcState)); 15439 pw.print(" lastPss="); DebugUtils.printSizeValue(pw, r.lastPss*1024); 15440 pw.print(" lastSwapPss="); DebugUtils.printSizeValue(pw, r.lastSwapPss*1024); 15441 pw.print(" lastCachedPss="); DebugUtils.printSizeValue(pw, r.lastCachedPss*1024); 15442 pw.println(); 15443 pw.print(prefix); 15444 pw.print(" "); 15445 pw.print("cached="); pw.print(r.cached); 15446 pw.print(" empty="); pw.print(r.empty); 15447 pw.print(" hasAboveClient="); pw.println(r.hasAboveClient); 15448 15449 if (r.setProcState >= ActivityManager.PROCESS_STATE_SERVICE) { 15450 if (r.lastWakeTime != 0) { 15451 long wtime; 15452 BatteryStatsImpl stats = service.mBatteryStatsService.getActiveStatistics(); 15453 synchronized (stats) { 15454 wtime = stats.getProcessWakeTime(r.info.uid, 15455 r.pid, curRealtime); 15456 } 15457 long timeUsed = wtime - r.lastWakeTime; 15458 pw.print(prefix); 15459 pw.print(" "); 15460 pw.print("keep awake over "); 15461 TimeUtils.formatDuration(realtimeSince, pw); 15462 pw.print(" used "); 15463 TimeUtils.formatDuration(timeUsed, pw); 15464 pw.print(" ("); 15465 pw.print((timeUsed*100)/realtimeSince); 15466 pw.println("%)"); 15467 } 15468 if (r.lastCpuTime != 0) { 15469 long timeUsed = r.curCpuTime - r.lastCpuTime; 15470 pw.print(prefix); 15471 pw.print(" "); 15472 pw.print("run cpu over "); 15473 TimeUtils.formatDuration(uptimeSince, pw); 15474 pw.print(" used "); 15475 TimeUtils.formatDuration(timeUsed, pw); 15476 pw.print(" ("); 15477 pw.print((timeUsed*100)/uptimeSince); 15478 pw.println("%)"); 15479 } 15480 } 15481 } 15482 } 15483 return true; 15484 } 15485 15486 ArrayList<ProcessRecord> collectProcesses(PrintWriter pw, int start, boolean allPkgs, 15487 String[] args) { 15488 ArrayList<ProcessRecord> procs; 15489 synchronized (this) { 15490 if (args != null && args.length > start 15491 && args[start].charAt(0) != '-') { 15492 procs = new ArrayList<ProcessRecord>(); 15493 int pid = -1; 15494 try { 15495 pid = Integer.parseInt(args[start]); 15496 } catch (NumberFormatException e) { 15497 } 15498 for (int i=mLruProcesses.size()-1; i>=0; i--) { 15499 ProcessRecord proc = mLruProcesses.get(i); 15500 if (proc.pid == pid) { 15501 procs.add(proc); 15502 } else if (allPkgs && proc.pkgList != null 15503 && proc.pkgList.containsKey(args[start])) { 15504 procs.add(proc); 15505 } else if (proc.processName.equals(args[start])) { 15506 procs.add(proc); 15507 } 15508 } 15509 if (procs.size() <= 0) { 15510 return null; 15511 } 15512 } else { 15513 procs = new ArrayList<ProcessRecord>(mLruProcesses); 15514 } 15515 } 15516 return procs; 15517 } 15518 15519 final void dumpGraphicsHardwareUsage(FileDescriptor fd, 15520 PrintWriter pw, String[] args) { 15521 ArrayList<ProcessRecord> procs = collectProcesses(pw, 0, false, args); 15522 if (procs == null) { 15523 pw.println("No process found for: " + args[0]); 15524 return; 15525 } 15526 15527 long uptime = SystemClock.uptimeMillis(); 15528 long realtime = SystemClock.elapsedRealtime(); 15529 pw.println("Applications Graphics Acceleration Info:"); 15530 pw.println("Uptime: " + uptime + " Realtime: " + realtime); 15531 15532 for (int i = procs.size() - 1 ; i >= 0 ; i--) { 15533 ProcessRecord r = procs.get(i); 15534 if (r.thread != null) { 15535 pw.println("\n** Graphics info for pid " + r.pid + " [" + r.processName + "] **"); 15536 pw.flush(); 15537 try { 15538 TransferPipe tp = new TransferPipe(); 15539 try { 15540 r.thread.dumpGfxInfo(tp.getWriteFd(), args); 15541 tp.go(fd); 15542 } finally { 15543 tp.kill(); 15544 } 15545 } catch (IOException e) { 15546 pw.println("Failure while dumping the app: " + r); 15547 pw.flush(); 15548 } catch (RemoteException e) { 15549 pw.println("Got a RemoteException while dumping the app " + r); 15550 pw.flush(); 15551 } 15552 } 15553 } 15554 } 15555 15556 final void dumpDbInfo(FileDescriptor fd, PrintWriter pw, String[] args) { 15557 ArrayList<ProcessRecord> procs = collectProcesses(pw, 0, false, args); 15558 if (procs == null) { 15559 pw.println("No process found for: " + args[0]); 15560 return; 15561 } 15562 15563 pw.println("Applications Database Info:"); 15564 15565 for (int i = procs.size() - 1 ; i >= 0 ; i--) { 15566 ProcessRecord r = procs.get(i); 15567 if (r.thread != null) { 15568 pw.println("\n** Database info for pid " + r.pid + " [" + r.processName + "] **"); 15569 pw.flush(); 15570 try { 15571 TransferPipe tp = new TransferPipe(); 15572 try { 15573 r.thread.dumpDbInfo(tp.getWriteFd(), args); 15574 tp.go(fd); 15575 } finally { 15576 tp.kill(); 15577 } 15578 } catch (IOException e) { 15579 pw.println("Failure while dumping the app: " + r); 15580 pw.flush(); 15581 } catch (RemoteException e) { 15582 pw.println("Got a RemoteException while dumping the app " + r); 15583 pw.flush(); 15584 } 15585 } 15586 } 15587 } 15588 15589 final static class MemItem { 15590 final boolean isProc; 15591 final String label; 15592 final String shortLabel; 15593 final long pss; 15594 final long swapPss; 15595 final int id; 15596 final boolean hasActivities; 15597 ArrayList<MemItem> subitems; 15598 15599 public MemItem(String _label, String _shortLabel, long _pss, long _swapPss, int _id, 15600 boolean _hasActivities) { 15601 isProc = true; 15602 label = _label; 15603 shortLabel = _shortLabel; 15604 pss = _pss; 15605 swapPss = _swapPss; 15606 id = _id; 15607 hasActivities = _hasActivities; 15608 } 15609 15610 public MemItem(String _label, String _shortLabel, long _pss, long _swapPss, int _id) { 15611 isProc = false; 15612 label = _label; 15613 shortLabel = _shortLabel; 15614 pss = _pss; 15615 swapPss = _swapPss; 15616 id = _id; 15617 hasActivities = false; 15618 } 15619 } 15620 15621 static final void dumpMemItems(PrintWriter pw, String prefix, String tag, 15622 ArrayList<MemItem> items, boolean sort, boolean isCompact, boolean dumpSwapPss) { 15623 if (sort && !isCompact) { 15624 Collections.sort(items, new Comparator<MemItem>() { 15625 @Override 15626 public int compare(MemItem lhs, MemItem rhs) { 15627 if (lhs.pss < rhs.pss) { 15628 return 1; 15629 } else if (lhs.pss > rhs.pss) { 15630 return -1; 15631 } 15632 return 0; 15633 } 15634 }); 15635 } 15636 15637 for (int i=0; i<items.size(); i++) { 15638 MemItem mi = items.get(i); 15639 if (!isCompact) { 15640 if (dumpSwapPss) { 15641 pw.printf("%s%s: %-60s (%s in swap)\n", prefix, stringifyKBSize(mi.pss), 15642 mi.label, stringifyKBSize(mi.swapPss)); 15643 } else { 15644 pw.printf("%s%s: %s\n", prefix, stringifyKBSize(mi.pss), mi.label); 15645 } 15646 } else if (mi.isProc) { 15647 pw.print("proc,"); pw.print(tag); pw.print(","); pw.print(mi.shortLabel); 15648 pw.print(","); pw.print(mi.id); pw.print(","); pw.print(mi.pss); pw.print(","); 15649 pw.print(dumpSwapPss ? mi.swapPss : "N/A"); 15650 pw.println(mi.hasActivities ? ",a" : ",e"); 15651 } else { 15652 pw.print(tag); pw.print(","); pw.print(mi.shortLabel); pw.print(","); 15653 pw.print(mi.pss); pw.print(","); pw.println(dumpSwapPss ? mi.swapPss : "N/A"); 15654 } 15655 if (mi.subitems != null) { 15656 dumpMemItems(pw, prefix + " ", mi.shortLabel, mi.subitems, 15657 true, isCompact, dumpSwapPss); 15658 } 15659 } 15660 } 15661 15662 // These are in KB. 15663 static final long[] DUMP_MEM_BUCKETS = new long[] { 15664 5*1024, 7*1024, 10*1024, 15*1024, 20*1024, 30*1024, 40*1024, 80*1024, 15665 120*1024, 160*1024, 200*1024, 15666 250*1024, 300*1024, 350*1024, 400*1024, 500*1024, 600*1024, 800*1024, 15667 1*1024*1024, 2*1024*1024, 5*1024*1024, 10*1024*1024, 20*1024*1024 15668 }; 15669 15670 static final void appendMemBucket(StringBuilder out, long memKB, String label, 15671 boolean stackLike) { 15672 int start = label.lastIndexOf('.'); 15673 if (start >= 0) start++; 15674 else start = 0; 15675 int end = label.length(); 15676 for (int i=0; i<DUMP_MEM_BUCKETS.length; i++) { 15677 if (DUMP_MEM_BUCKETS[i] >= memKB) { 15678 long bucket = DUMP_MEM_BUCKETS[i]/1024; 15679 out.append(bucket); 15680 out.append(stackLike ? "MB." : "MB "); 15681 out.append(label, start, end); 15682 return; 15683 } 15684 } 15685 out.append(memKB/1024); 15686 out.append(stackLike ? "MB." : "MB "); 15687 out.append(label, start, end); 15688 } 15689 15690 static final int[] DUMP_MEM_OOM_ADJ = new int[] { 15691 ProcessList.NATIVE_ADJ, 15692 ProcessList.SYSTEM_ADJ, ProcessList.PERSISTENT_PROC_ADJ, 15693 ProcessList.PERSISTENT_SERVICE_ADJ, ProcessList.FOREGROUND_APP_ADJ, 15694 ProcessList.VISIBLE_APP_ADJ, ProcessList.PERCEPTIBLE_APP_ADJ, 15695 ProcessList.BACKUP_APP_ADJ, ProcessList.HEAVY_WEIGHT_APP_ADJ, 15696 ProcessList.SERVICE_ADJ, ProcessList.HOME_APP_ADJ, 15697 ProcessList.PREVIOUS_APP_ADJ, ProcessList.SERVICE_B_ADJ, ProcessList.CACHED_APP_MIN_ADJ 15698 }; 15699 static final String[] DUMP_MEM_OOM_LABEL = new String[] { 15700 "Native", 15701 "System", "Persistent", "Persistent Service", "Foreground", 15702 "Visible", "Perceptible", 15703 "Heavy Weight", "Backup", 15704 "A Services", "Home", 15705 "Previous", "B Services", "Cached" 15706 }; 15707 static final String[] DUMP_MEM_OOM_COMPACT_LABEL = new String[] { 15708 "native", 15709 "sys", "pers", "persvc", "fore", 15710 "vis", "percept", 15711 "heavy", "backup", 15712 "servicea", "home", 15713 "prev", "serviceb", "cached" 15714 }; 15715 15716 private final void dumpApplicationMemoryUsageHeader(PrintWriter pw, long uptime, 15717 long realtime, boolean isCheckinRequest, boolean isCompact) { 15718 if (isCompact) { 15719 pw.print("version,"); pw.println(MEMINFO_COMPACT_VERSION); 15720 } 15721 if (isCheckinRequest || isCompact) { 15722 // short checkin version 15723 pw.print("time,"); pw.print(uptime); pw.print(","); pw.println(realtime); 15724 } else { 15725 pw.println("Applications Memory Usage (in Kilobytes):"); 15726 pw.println("Uptime: " + uptime + " Realtime: " + realtime); 15727 } 15728 } 15729 15730 private static final int KSM_SHARED = 0; 15731 private static final int KSM_SHARING = 1; 15732 private static final int KSM_UNSHARED = 2; 15733 private static final int KSM_VOLATILE = 3; 15734 15735 private final long[] getKsmInfo() { 15736 long[] longOut = new long[4]; 15737 final int[] SINGLE_LONG_FORMAT = new int[] { 15738 Process.PROC_SPACE_TERM|Process.PROC_OUT_LONG 15739 }; 15740 long[] longTmp = new long[1]; 15741 Process.readProcFile("/sys/kernel/mm/ksm/pages_shared", 15742 SINGLE_LONG_FORMAT, null, longTmp, null); 15743 longOut[KSM_SHARED] = longTmp[0] * ProcessList.PAGE_SIZE / 1024; 15744 longTmp[0] = 0; 15745 Process.readProcFile("/sys/kernel/mm/ksm/pages_sharing", 15746 SINGLE_LONG_FORMAT, null, longTmp, null); 15747 longOut[KSM_SHARING] = longTmp[0] * ProcessList.PAGE_SIZE / 1024; 15748 longTmp[0] = 0; 15749 Process.readProcFile("/sys/kernel/mm/ksm/pages_unshared", 15750 SINGLE_LONG_FORMAT, null, longTmp, null); 15751 longOut[KSM_UNSHARED] = longTmp[0] * ProcessList.PAGE_SIZE / 1024; 15752 longTmp[0] = 0; 15753 Process.readProcFile("/sys/kernel/mm/ksm/pages_volatile", 15754 SINGLE_LONG_FORMAT, null, longTmp, null); 15755 longOut[KSM_VOLATILE] = longTmp[0] * ProcessList.PAGE_SIZE / 1024; 15756 return longOut; 15757 } 15758 15759 private static String stringifySize(long size, int order) { 15760 Locale locale = Locale.US; 15761 switch (order) { 15762 case 1: 15763 return String.format(locale, "%,13d", size); 15764 case 1024: 15765 return String.format(locale, "%,9dK", size / 1024); 15766 case 1024 * 1024: 15767 return String.format(locale, "%,5dM", size / 1024 / 1024); 15768 case 1024 * 1024 * 1024: 15769 return String.format(locale, "%,1dG", size / 1024 / 1024 / 1024); 15770 default: 15771 throw new IllegalArgumentException("Invalid size order"); 15772 } 15773 } 15774 15775 private static String stringifyKBSize(long size) { 15776 return stringifySize(size * 1024, 1024); 15777 } 15778 15779 // Update this version number in case you change the 'compact' format 15780 private static final int MEMINFO_COMPACT_VERSION = 1; 15781 15782 final void dumpApplicationMemoryUsage(FileDescriptor fd, 15783 PrintWriter pw, String prefix, String[] args, boolean brief, PrintWriter categoryPw) { 15784 boolean dumpDetails = false; 15785 boolean dumpFullDetails = false; 15786 boolean dumpDalvik = false; 15787 boolean dumpSummaryOnly = false; 15788 boolean dumpUnreachable = false; 15789 boolean oomOnly = false; 15790 boolean isCompact = false; 15791 boolean localOnly = false; 15792 boolean packages = false; 15793 boolean isCheckinRequest = false; 15794 boolean dumpSwapPss = false; 15795 15796 int opti = 0; 15797 while (opti < args.length) { 15798 String opt = args[opti]; 15799 if (opt == null || opt.length() <= 0 || opt.charAt(0) != '-') { 15800 break; 15801 } 15802 opti++; 15803 if ("-a".equals(opt)) { 15804 dumpDetails = true; 15805 dumpFullDetails = true; 15806 dumpDalvik = true; 15807 dumpSwapPss = true; 15808 } else if ("-d".equals(opt)) { 15809 dumpDalvik = true; 15810 } else if ("-c".equals(opt)) { 15811 isCompact = true; 15812 } else if ("-s".equals(opt)) { 15813 dumpDetails = true; 15814 dumpSummaryOnly = true; 15815 } else if ("-S".equals(opt)) { 15816 dumpSwapPss = true; 15817 } else if ("--unreachable".equals(opt)) { 15818 dumpUnreachable = true; 15819 } else if ("--oom".equals(opt)) { 15820 oomOnly = true; 15821 } else if ("--local".equals(opt)) { 15822 localOnly = true; 15823 } else if ("--package".equals(opt)) { 15824 packages = true; 15825 } else if ("--checkin".equals(opt)) { 15826 isCheckinRequest = true; 15827 15828 } else if ("-h".equals(opt)) { 15829 pw.println("meminfo dump options: [-a] [-d] [-c] [-s] [--oom] [process]"); 15830 pw.println(" -a: include all available information for each process."); 15831 pw.println(" -d: include dalvik details."); 15832 pw.println(" -c: dump in a compact machine-parseable representation."); 15833 pw.println(" -s: dump only summary of application memory usage."); 15834 pw.println(" -S: dump also SwapPss."); 15835 pw.println(" --oom: only show processes organized by oom adj."); 15836 pw.println(" --local: only collect details locally, don't call process."); 15837 pw.println(" --package: interpret process arg as package, dumping all"); 15838 pw.println(" processes that have loaded that package."); 15839 pw.println(" --checkin: dump data for a checkin"); 15840 pw.println("If [process] is specified it can be the name or "); 15841 pw.println("pid of a specific process to dump."); 15842 return; 15843 } else { 15844 pw.println("Unknown argument: " + opt + "; use -h for help"); 15845 } 15846 } 15847 15848 long uptime = SystemClock.uptimeMillis(); 15849 long realtime = SystemClock.elapsedRealtime(); 15850 final long[] tmpLong = new long[1]; 15851 15852 ArrayList<ProcessRecord> procs = collectProcesses(pw, opti, packages, args); 15853 if (procs == null) { 15854 // No Java processes. Maybe they want to print a native process. 15855 if (args != null && args.length > opti 15856 && args[opti].charAt(0) != '-') { 15857 ArrayList<ProcessCpuTracker.Stats> nativeProcs 15858 = new ArrayList<ProcessCpuTracker.Stats>(); 15859 updateCpuStatsNow(); 15860 int findPid = -1; 15861 try { 15862 findPid = Integer.parseInt(args[opti]); 15863 } catch (NumberFormatException e) { 15864 } 15865 synchronized (mProcessCpuTracker) { 15866 final int N = mProcessCpuTracker.countStats(); 15867 for (int i=0; i<N; i++) { 15868 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(i); 15869 if (st.pid == findPid || (st.baseName != null 15870 && st.baseName.equals(args[opti]))) { 15871 nativeProcs.add(st); 15872 } 15873 } 15874 } 15875 if (nativeProcs.size() > 0) { 15876 dumpApplicationMemoryUsageHeader(pw, uptime, realtime, isCheckinRequest, 15877 isCompact); 15878 Debug.MemoryInfo mi = null; 15879 for (int i = nativeProcs.size() - 1 ; i >= 0 ; i--) { 15880 final ProcessCpuTracker.Stats r = nativeProcs.get(i); 15881 final int pid = r.pid; 15882 if (!isCheckinRequest && dumpDetails) { 15883 pw.println("\n** MEMINFO in pid " + pid + " [" + r.baseName + "] **"); 15884 } 15885 if (mi == null) { 15886 mi = new Debug.MemoryInfo(); 15887 } 15888 if (dumpDetails || (!brief && !oomOnly)) { 15889 Debug.getMemoryInfo(pid, mi); 15890 } else { 15891 mi.dalvikPss = (int)Debug.getPss(pid, tmpLong, null); 15892 mi.dalvikPrivateDirty = (int)tmpLong[0]; 15893 } 15894 ActivityThread.dumpMemInfoTable(pw, mi, isCheckinRequest, dumpFullDetails, 15895 dumpDalvik, dumpSummaryOnly, pid, r.baseName, 0, 0, 0, 0, 0, 0); 15896 if (isCheckinRequest) { 15897 pw.println(); 15898 } 15899 } 15900 return; 15901 } 15902 } 15903 pw.println("No process found for: " + args[opti]); 15904 return; 15905 } 15906 15907 if (!brief && !oomOnly && (procs.size() == 1 || isCheckinRequest || packages)) { 15908 dumpDetails = true; 15909 } 15910 15911 dumpApplicationMemoryUsageHeader(pw, uptime, realtime, isCheckinRequest, isCompact); 15912 15913 String[] innerArgs = new String[args.length-opti]; 15914 System.arraycopy(args, opti, innerArgs, 0, args.length-opti); 15915 15916 ArrayList<MemItem> procMems = new ArrayList<MemItem>(); 15917 final SparseArray<MemItem> procMemsMap = new SparseArray<MemItem>(); 15918 long nativePss = 0; 15919 long nativeSwapPss = 0; 15920 long dalvikPss = 0; 15921 long dalvikSwapPss = 0; 15922 long[] dalvikSubitemPss = dumpDalvik ? new long[Debug.MemoryInfo.NUM_DVK_STATS] : 15923 EmptyArray.LONG; 15924 long[] dalvikSubitemSwapPss = dumpDalvik ? new long[Debug.MemoryInfo.NUM_DVK_STATS] : 15925 EmptyArray.LONG; 15926 long otherPss = 0; 15927 long otherSwapPss = 0; 15928 long[] miscPss = new long[Debug.MemoryInfo.NUM_OTHER_STATS]; 15929 long[] miscSwapPss = new long[Debug.MemoryInfo.NUM_OTHER_STATS]; 15930 15931 long oomPss[] = new long[DUMP_MEM_OOM_LABEL.length]; 15932 long oomSwapPss[] = new long[DUMP_MEM_OOM_LABEL.length]; 15933 ArrayList<MemItem>[] oomProcs = (ArrayList<MemItem>[]) 15934 new ArrayList[DUMP_MEM_OOM_LABEL.length]; 15935 15936 long totalPss = 0; 15937 long totalSwapPss = 0; 15938 long cachedPss = 0; 15939 long cachedSwapPss = 0; 15940 boolean hasSwapPss = false; 15941 15942 Debug.MemoryInfo mi = null; 15943 for (int i = procs.size() - 1 ; i >= 0 ; i--) { 15944 final ProcessRecord r = procs.get(i); 15945 final IApplicationThread thread; 15946 final int pid; 15947 final int oomAdj; 15948 final boolean hasActivities; 15949 synchronized (this) { 15950 thread = r.thread; 15951 pid = r.pid; 15952 oomAdj = r.getSetAdjWithServices(); 15953 hasActivities = r.activities.size() > 0; 15954 } 15955 if (thread != null) { 15956 if (!isCheckinRequest && dumpDetails) { 15957 pw.println("\n** MEMINFO in pid " + pid + " [" + r.processName + "] **"); 15958 } 15959 if (mi == null) { 15960 mi = new Debug.MemoryInfo(); 15961 } 15962 if (dumpDetails || (!brief && !oomOnly)) { 15963 Debug.getMemoryInfo(pid, mi); 15964 hasSwapPss = mi.hasSwappedOutPss; 15965 } else { 15966 mi.dalvikPss = (int)Debug.getPss(pid, tmpLong, null); 15967 mi.dalvikPrivateDirty = (int)tmpLong[0]; 15968 } 15969 if (dumpDetails) { 15970 if (localOnly) { 15971 ActivityThread.dumpMemInfoTable(pw, mi, isCheckinRequest, dumpFullDetails, 15972 dumpDalvik, dumpSummaryOnly, pid, r.processName, 0, 0, 0, 0, 0, 0); 15973 if (isCheckinRequest) { 15974 pw.println(); 15975 } 15976 } else { 15977 pw.flush(); 15978 try { 15979 TransferPipe tp = new TransferPipe(); 15980 try { 15981 thread.dumpMemInfo(tp.getWriteFd(), 15982 mi, isCheckinRequest, dumpFullDetails, 15983 dumpDalvik, dumpSummaryOnly, dumpUnreachable, innerArgs); 15984 tp.go(fd); 15985 } finally { 15986 tp.kill(); 15987 } 15988 } catch (IOException e) { 15989 if (!isCheckinRequest) { 15990 pw.println("Got IoException!"); 15991 pw.flush(); 15992 } 15993 } catch (RemoteException e) { 15994 if (!isCheckinRequest) { 15995 pw.println("Got RemoteException!"); 15996 pw.flush(); 15997 } 15998 } 15999 } 16000 } 16001 16002 final long myTotalPss = mi.getTotalPss(); 16003 final long myTotalUss = mi.getTotalUss(); 16004 final long myTotalSwapPss = mi.getTotalSwappedOutPss(); 16005 16006 synchronized (this) { 16007 if (r.thread != null && oomAdj == r.getSetAdjWithServices()) { 16008 // Record this for posterity if the process has been stable. 16009 r.baseProcessTracker.addPss(myTotalPss, myTotalUss, true, r.pkgList); 16010 } 16011 } 16012 16013 if (!isCheckinRequest && mi != null) { 16014 totalPss += myTotalPss; 16015 totalSwapPss += myTotalSwapPss; 16016 MemItem pssItem = new MemItem(r.processName + " (pid " + pid + 16017 (hasActivities ? " / activities)" : ")"), r.processName, myTotalPss, 16018 myTotalSwapPss, pid, hasActivities); 16019 procMems.add(pssItem); 16020 procMemsMap.put(pid, pssItem); 16021 16022 nativePss += mi.nativePss; 16023 nativeSwapPss += mi.nativeSwappedOutPss; 16024 dalvikPss += mi.dalvikPss; 16025 dalvikSwapPss += mi.dalvikSwappedOutPss; 16026 for (int j=0; j<dalvikSubitemPss.length; j++) { 16027 dalvikSubitemPss[j] += mi.getOtherPss(Debug.MemoryInfo.NUM_OTHER_STATS + j); 16028 dalvikSubitemSwapPss[j] += 16029 mi.getOtherSwappedOutPss(Debug.MemoryInfo.NUM_OTHER_STATS + j); 16030 } 16031 otherPss += mi.otherPss; 16032 otherSwapPss += mi.otherSwappedOutPss; 16033 for (int j=0; j<Debug.MemoryInfo.NUM_OTHER_STATS; j++) { 16034 long mem = mi.getOtherPss(j); 16035 miscPss[j] += mem; 16036 otherPss -= mem; 16037 mem = mi.getOtherSwappedOutPss(j); 16038 miscSwapPss[j] += mem; 16039 otherSwapPss -= mem; 16040 } 16041 16042 if (oomAdj >= ProcessList.CACHED_APP_MIN_ADJ) { 16043 cachedPss += myTotalPss; 16044 cachedSwapPss += myTotalSwapPss; 16045 } 16046 16047 for (int oomIndex=0; oomIndex<oomPss.length; oomIndex++) { 16048 if (oomIndex == (oomPss.length - 1) 16049 || (oomAdj >= DUMP_MEM_OOM_ADJ[oomIndex] 16050 && oomAdj < DUMP_MEM_OOM_ADJ[oomIndex + 1])) { 16051 oomPss[oomIndex] += myTotalPss; 16052 oomSwapPss[oomIndex] += myTotalSwapPss; 16053 if (oomProcs[oomIndex] == null) { 16054 oomProcs[oomIndex] = new ArrayList<MemItem>(); 16055 } 16056 oomProcs[oomIndex].add(pssItem); 16057 break; 16058 } 16059 } 16060 } 16061 } 16062 } 16063 16064 long nativeProcTotalPss = 0; 16065 16066 if (!isCheckinRequest && procs.size() > 1 && !packages) { 16067 // If we are showing aggregations, also look for native processes to 16068 // include so that our aggregations are more accurate. 16069 updateCpuStatsNow(); 16070 mi = null; 16071 synchronized (mProcessCpuTracker) { 16072 final int N = mProcessCpuTracker.countStats(); 16073 for (int i=0; i<N; i++) { 16074 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(i); 16075 if (st.vsize > 0 && procMemsMap.indexOfKey(st.pid) < 0) { 16076 if (mi == null) { 16077 mi = new Debug.MemoryInfo(); 16078 } 16079 if (!brief && !oomOnly) { 16080 Debug.getMemoryInfo(st.pid, mi); 16081 } else { 16082 mi.nativePss = (int)Debug.getPss(st.pid, tmpLong, null); 16083 mi.nativePrivateDirty = (int)tmpLong[0]; 16084 } 16085 16086 final long myTotalPss = mi.getTotalPss(); 16087 final long myTotalSwapPss = mi.getTotalSwappedOutPss(); 16088 totalPss += myTotalPss; 16089 nativeProcTotalPss += myTotalPss; 16090 16091 MemItem pssItem = new MemItem(st.name + " (pid " + st.pid + ")", 16092 st.name, myTotalPss, mi.getSummaryTotalSwapPss(), st.pid, false); 16093 procMems.add(pssItem); 16094 16095 nativePss += mi.nativePss; 16096 nativeSwapPss += mi.nativeSwappedOutPss; 16097 dalvikPss += mi.dalvikPss; 16098 dalvikSwapPss += mi.dalvikSwappedOutPss; 16099 for (int j=0; j<dalvikSubitemPss.length; j++) { 16100 dalvikSubitemPss[j] += mi.getOtherPss(Debug.MemoryInfo.NUM_OTHER_STATS + j); 16101 dalvikSubitemSwapPss[j] += 16102 mi.getOtherSwappedOutPss(Debug.MemoryInfo.NUM_OTHER_STATS + j); 16103 } 16104 otherPss += mi.otherPss; 16105 otherSwapPss += mi.otherSwappedOutPss; 16106 for (int j=0; j<Debug.MemoryInfo.NUM_OTHER_STATS; j++) { 16107 long mem = mi.getOtherPss(j); 16108 miscPss[j] += mem; 16109 otherPss -= mem; 16110 mem = mi.getOtherSwappedOutPss(j); 16111 miscSwapPss[j] += mem; 16112 otherSwapPss -= mem; 16113 } 16114 oomPss[0] += myTotalPss; 16115 oomSwapPss[0] += myTotalSwapPss; 16116 if (oomProcs[0] == null) { 16117 oomProcs[0] = new ArrayList<MemItem>(); 16118 } 16119 oomProcs[0].add(pssItem); 16120 } 16121 } 16122 } 16123 16124 ArrayList<MemItem> catMems = new ArrayList<MemItem>(); 16125 16126 catMems.add(new MemItem("Native", "Native", nativePss, nativeSwapPss, -1)); 16127 final MemItem dalvikItem = 16128 new MemItem("Dalvik", "Dalvik", dalvikPss, dalvikSwapPss, -2); 16129 if (dalvikSubitemPss.length > 0) { 16130 dalvikItem.subitems = new ArrayList<MemItem>(); 16131 for (int j=0; j<dalvikSubitemPss.length; j++) { 16132 final String name = Debug.MemoryInfo.getOtherLabel( 16133 Debug.MemoryInfo.NUM_OTHER_STATS + j); 16134 dalvikItem.subitems.add(new MemItem(name, name, dalvikSubitemPss[j], 16135 dalvikSubitemSwapPss[j], j)); 16136 } 16137 } 16138 catMems.add(dalvikItem); 16139 catMems.add(new MemItem("Unknown", "Unknown", otherPss, otherSwapPss, -3)); 16140 for (int j=0; j<Debug.MemoryInfo.NUM_OTHER_STATS; j++) { 16141 String label = Debug.MemoryInfo.getOtherLabel(j); 16142 catMems.add(new MemItem(label, label, miscPss[j], miscSwapPss[j], j)); 16143 } 16144 16145 ArrayList<MemItem> oomMems = new ArrayList<MemItem>(); 16146 for (int j=0; j<oomPss.length; j++) { 16147 if (oomPss[j] != 0) { 16148 String label = isCompact ? DUMP_MEM_OOM_COMPACT_LABEL[j] 16149 : DUMP_MEM_OOM_LABEL[j]; 16150 MemItem item = new MemItem(label, label, oomPss[j], oomSwapPss[j], 16151 DUMP_MEM_OOM_ADJ[j]); 16152 item.subitems = oomProcs[j]; 16153 oomMems.add(item); 16154 } 16155 } 16156 16157 dumpSwapPss = dumpSwapPss && hasSwapPss && totalSwapPss != 0; 16158 if (!brief && !oomOnly && !isCompact) { 16159 pw.println(); 16160 pw.println("Total PSS by process:"); 16161 dumpMemItems(pw, " ", "proc", procMems, true, isCompact, dumpSwapPss); 16162 pw.println(); 16163 } 16164 if (!isCompact) { 16165 pw.println("Total PSS by OOM adjustment:"); 16166 } 16167 dumpMemItems(pw, " ", "oom", oomMems, false, isCompact, dumpSwapPss); 16168 if (!brief && !oomOnly) { 16169 PrintWriter out = categoryPw != null ? categoryPw : pw; 16170 if (!isCompact) { 16171 out.println(); 16172 out.println("Total PSS by category:"); 16173 } 16174 dumpMemItems(out, " ", "cat", catMems, true, isCompact, dumpSwapPss); 16175 } 16176 if (!isCompact) { 16177 pw.println(); 16178 } 16179 MemInfoReader memInfo = new MemInfoReader(); 16180 memInfo.readMemInfo(); 16181 if (nativeProcTotalPss > 0) { 16182 synchronized (this) { 16183 final long cachedKb = memInfo.getCachedSizeKb(); 16184 final long freeKb = memInfo.getFreeSizeKb(); 16185 final long zramKb = memInfo.getZramTotalSizeKb(); 16186 final long kernelKb = memInfo.getKernelUsedSizeKb(); 16187 EventLogTags.writeAmMeminfo(cachedKb*1024, freeKb*1024, zramKb*1024, 16188 kernelKb*1024, nativeProcTotalPss*1024); 16189 mProcessStats.addSysMemUsageLocked(cachedKb, freeKb, zramKb, kernelKb, 16190 nativeProcTotalPss); 16191 } 16192 } 16193 if (!brief) { 16194 if (!isCompact) { 16195 pw.print("Total RAM: "); pw.print(stringifyKBSize(memInfo.getTotalSizeKb())); 16196 pw.print(" (status "); 16197 switch (mLastMemoryLevel) { 16198 case ProcessStats.ADJ_MEM_FACTOR_NORMAL: 16199 pw.println("normal)"); 16200 break; 16201 case ProcessStats.ADJ_MEM_FACTOR_MODERATE: 16202 pw.println("moderate)"); 16203 break; 16204 case ProcessStats.ADJ_MEM_FACTOR_LOW: 16205 pw.println("low)"); 16206 break; 16207 case ProcessStats.ADJ_MEM_FACTOR_CRITICAL: 16208 pw.println("critical)"); 16209 break; 16210 default: 16211 pw.print(mLastMemoryLevel); 16212 pw.println(")"); 16213 break; 16214 } 16215 pw.print(" Free RAM: "); 16216 pw.print(stringifyKBSize(cachedPss + memInfo.getCachedSizeKb() 16217 + memInfo.getFreeSizeKb())); 16218 pw.print(" ("); 16219 pw.print(stringifyKBSize(cachedPss)); 16220 pw.print(" cached pss + "); 16221 pw.print(stringifyKBSize(memInfo.getCachedSizeKb())); 16222 pw.print(" cached kernel + "); 16223 pw.print(stringifyKBSize(memInfo.getFreeSizeKb())); 16224 pw.println(" free)"); 16225 } else { 16226 pw.print("ram,"); pw.print(memInfo.getTotalSizeKb()); pw.print(","); 16227 pw.print(cachedPss + memInfo.getCachedSizeKb() 16228 + memInfo.getFreeSizeKb()); pw.print(","); 16229 pw.println(totalPss - cachedPss); 16230 } 16231 } 16232 long lostRAM = memInfo.getTotalSizeKb() - (totalPss - totalSwapPss) 16233 - memInfo.getFreeSizeKb() - memInfo.getCachedSizeKb() 16234 - memInfo.getKernelUsedSizeKb() - memInfo.getZramTotalSizeKb(); 16235 if (!isCompact) { 16236 pw.print(" Used RAM: "); pw.print(stringifyKBSize(totalPss - cachedPss 16237 + memInfo.getKernelUsedSizeKb())); pw.print(" ("); 16238 pw.print(stringifyKBSize(totalPss - cachedPss)); pw.print(" used pss + "); 16239 pw.print(stringifyKBSize(memInfo.getKernelUsedSizeKb())); pw.print(" kernel)\n"); 16240 pw.print(" Lost RAM: "); pw.println(stringifyKBSize(lostRAM)); 16241 } else { 16242 pw.print("lostram,"); pw.println(lostRAM); 16243 } 16244 if (!brief) { 16245 if (memInfo.getZramTotalSizeKb() != 0) { 16246 if (!isCompact) { 16247 pw.print(" ZRAM: "); 16248 pw.print(stringifyKBSize(memInfo.getZramTotalSizeKb())); 16249 pw.print(" physical used for "); 16250 pw.print(stringifyKBSize(memInfo.getSwapTotalSizeKb() 16251 - memInfo.getSwapFreeSizeKb())); 16252 pw.print(" in swap ("); 16253 pw.print(stringifyKBSize(memInfo.getSwapTotalSizeKb())); 16254 pw.println(" total swap)"); 16255 } else { 16256 pw.print("zram,"); pw.print(memInfo.getZramTotalSizeKb()); pw.print(","); 16257 pw.print(memInfo.getSwapTotalSizeKb()); pw.print(","); 16258 pw.println(memInfo.getSwapFreeSizeKb()); 16259 } 16260 } 16261 final long[] ksm = getKsmInfo(); 16262 if (!isCompact) { 16263 if (ksm[KSM_SHARING] != 0 || ksm[KSM_SHARED] != 0 || ksm[KSM_UNSHARED] != 0 16264 || ksm[KSM_VOLATILE] != 0) { 16265 pw.print(" KSM: "); pw.print(stringifyKBSize(ksm[KSM_SHARING])); 16266 pw.print(" saved from shared "); 16267 pw.print(stringifyKBSize(ksm[KSM_SHARED])); 16268 pw.print(" "); pw.print(stringifyKBSize(ksm[KSM_UNSHARED])); 16269 pw.print(" unshared; "); 16270 pw.print(stringifyKBSize( 16271 ksm[KSM_VOLATILE])); pw.println(" volatile"); 16272 } 16273 pw.print(" Tuning: "); 16274 pw.print(ActivityManager.staticGetMemoryClass()); 16275 pw.print(" (large "); 16276 pw.print(ActivityManager.staticGetLargeMemoryClass()); 16277 pw.print("), oom "); 16278 pw.print(stringifySize( 16279 mProcessList.getMemLevel(ProcessList.CACHED_APP_MAX_ADJ), 1024)); 16280 pw.print(", restore limit "); 16281 pw.print(stringifyKBSize(mProcessList.getCachedRestoreThresholdKb())); 16282 if (ActivityManager.isLowRamDeviceStatic()) { 16283 pw.print(" (low-ram)"); 16284 } 16285 if (ActivityManager.isHighEndGfx()) { 16286 pw.print(" (high-end-gfx)"); 16287 } 16288 pw.println(); 16289 } else { 16290 pw.print("ksm,"); pw.print(ksm[KSM_SHARING]); pw.print(","); 16291 pw.print(ksm[KSM_SHARED]); pw.print(","); pw.print(ksm[KSM_UNSHARED]); 16292 pw.print(","); pw.println(ksm[KSM_VOLATILE]); 16293 pw.print("tuning,"); 16294 pw.print(ActivityManager.staticGetMemoryClass()); 16295 pw.print(','); 16296 pw.print(ActivityManager.staticGetLargeMemoryClass()); 16297 pw.print(','); 16298 pw.print(mProcessList.getMemLevel(ProcessList.CACHED_APP_MAX_ADJ)/1024); 16299 if (ActivityManager.isLowRamDeviceStatic()) { 16300 pw.print(",low-ram"); 16301 } 16302 if (ActivityManager.isHighEndGfx()) { 16303 pw.print(",high-end-gfx"); 16304 } 16305 pw.println(); 16306 } 16307 } 16308 } 16309 } 16310 16311 private void appendBasicMemEntry(StringBuilder sb, int oomAdj, int procState, long pss, 16312 long memtrack, String name) { 16313 sb.append(" "); 16314 sb.append(ProcessList.makeOomAdjString(oomAdj)); 16315 sb.append(' '); 16316 sb.append(ProcessList.makeProcStateString(procState)); 16317 sb.append(' '); 16318 ProcessList.appendRamKb(sb, pss); 16319 sb.append(": "); 16320 sb.append(name); 16321 if (memtrack > 0) { 16322 sb.append(" ("); 16323 sb.append(stringifyKBSize(memtrack)); 16324 sb.append(" memtrack)"); 16325 } 16326 } 16327 16328 private void appendMemInfo(StringBuilder sb, ProcessMemInfo mi) { 16329 appendBasicMemEntry(sb, mi.oomAdj, mi.procState, mi.pss, mi.memtrack, mi.name); 16330 sb.append(" (pid "); 16331 sb.append(mi.pid); 16332 sb.append(") "); 16333 sb.append(mi.adjType); 16334 sb.append('\n'); 16335 if (mi.adjReason != null) { 16336 sb.append(" "); 16337 sb.append(mi.adjReason); 16338 sb.append('\n'); 16339 } 16340 } 16341 16342 void reportMemUsage(ArrayList<ProcessMemInfo> memInfos) { 16343 final SparseArray<ProcessMemInfo> infoMap = new SparseArray<>(memInfos.size()); 16344 for (int i=0, N=memInfos.size(); i<N; i++) { 16345 ProcessMemInfo mi = memInfos.get(i); 16346 infoMap.put(mi.pid, mi); 16347 } 16348 updateCpuStatsNow(); 16349 long[] memtrackTmp = new long[1]; 16350 final List<ProcessCpuTracker.Stats> stats; 16351 // Get a list of Stats that have vsize > 0 16352 synchronized (mProcessCpuTracker) { 16353 stats = mProcessCpuTracker.getStats((st) -> { 16354 return st.vsize > 0; 16355 }); 16356 } 16357 final int statsCount = stats.size(); 16358 for (int i = 0; i < statsCount; i++) { 16359 ProcessCpuTracker.Stats st = stats.get(i); 16360 long pss = Debug.getPss(st.pid, null, memtrackTmp); 16361 if (pss > 0) { 16362 if (infoMap.indexOfKey(st.pid) < 0) { 16363 ProcessMemInfo mi = new ProcessMemInfo(st.name, st.pid, 16364 ProcessList.NATIVE_ADJ, -1, "native", null); 16365 mi.pss = pss; 16366 mi.memtrack = memtrackTmp[0]; 16367 memInfos.add(mi); 16368 } 16369 } 16370 } 16371 16372 long totalPss = 0; 16373 long totalMemtrack = 0; 16374 for (int i=0, N=memInfos.size(); i<N; i++) { 16375 ProcessMemInfo mi = memInfos.get(i); 16376 if (mi.pss == 0) { 16377 mi.pss = Debug.getPss(mi.pid, null, memtrackTmp); 16378 mi.memtrack = memtrackTmp[0]; 16379 } 16380 totalPss += mi.pss; 16381 totalMemtrack += mi.memtrack; 16382 } 16383 Collections.sort(memInfos, new Comparator<ProcessMemInfo>() { 16384 @Override public int compare(ProcessMemInfo lhs, ProcessMemInfo rhs) { 16385 if (lhs.oomAdj != rhs.oomAdj) { 16386 return lhs.oomAdj < rhs.oomAdj ? -1 : 1; 16387 } 16388 if (lhs.pss != rhs.pss) { 16389 return lhs.pss < rhs.pss ? 1 : -1; 16390 } 16391 return 0; 16392 } 16393 }); 16394 16395 StringBuilder tag = new StringBuilder(128); 16396 StringBuilder stack = new StringBuilder(128); 16397 tag.append("Low on memory -- "); 16398 appendMemBucket(tag, totalPss, "total", false); 16399 appendMemBucket(stack, totalPss, "total", true); 16400 16401 StringBuilder fullNativeBuilder = new StringBuilder(1024); 16402 StringBuilder shortNativeBuilder = new StringBuilder(1024); 16403 StringBuilder fullJavaBuilder = new StringBuilder(1024); 16404 16405 boolean firstLine = true; 16406 int lastOomAdj = Integer.MIN_VALUE; 16407 long extraNativeRam = 0; 16408 long extraNativeMemtrack = 0; 16409 long cachedPss = 0; 16410 for (int i=0, N=memInfos.size(); i<N; i++) { 16411 ProcessMemInfo mi = memInfos.get(i); 16412 16413 if (mi.oomAdj >= ProcessList.CACHED_APP_MIN_ADJ) { 16414 cachedPss += mi.pss; 16415 } 16416 16417 if (mi.oomAdj != ProcessList.NATIVE_ADJ 16418 && (mi.oomAdj < ProcessList.SERVICE_ADJ 16419 || mi.oomAdj == ProcessList.HOME_APP_ADJ 16420 || mi.oomAdj == ProcessList.PREVIOUS_APP_ADJ)) { 16421 if (lastOomAdj != mi.oomAdj) { 16422 lastOomAdj = mi.oomAdj; 16423 if (mi.oomAdj <= ProcessList.FOREGROUND_APP_ADJ) { 16424 tag.append(" / "); 16425 } 16426 if (mi.oomAdj >= ProcessList.FOREGROUND_APP_ADJ) { 16427 if (firstLine) { 16428 stack.append(":"); 16429 firstLine = false; 16430 } 16431 stack.append("\n\t at "); 16432 } else { 16433 stack.append("$"); 16434 } 16435 } else { 16436 tag.append(" "); 16437 stack.append("$"); 16438 } 16439 if (mi.oomAdj <= ProcessList.FOREGROUND_APP_ADJ) { 16440 appendMemBucket(tag, mi.pss, mi.name, false); 16441 } 16442 appendMemBucket(stack, mi.pss, mi.name, true); 16443 if (mi.oomAdj >= ProcessList.FOREGROUND_APP_ADJ 16444 && ((i+1) >= N || memInfos.get(i+1).oomAdj != lastOomAdj)) { 16445 stack.append("("); 16446 for (int k=0; k<DUMP_MEM_OOM_ADJ.length; k++) { 16447 if (DUMP_MEM_OOM_ADJ[k] == mi.oomAdj) { 16448 stack.append(DUMP_MEM_OOM_LABEL[k]); 16449 stack.append(":"); 16450 stack.append(DUMP_MEM_OOM_ADJ[k]); 16451 } 16452 } 16453 stack.append(")"); 16454 } 16455 } 16456 16457 appendMemInfo(fullNativeBuilder, mi); 16458 if (mi.oomAdj == ProcessList.NATIVE_ADJ) { 16459 // The short form only has native processes that are >= 512K. 16460 if (mi.pss >= 512) { 16461 appendMemInfo(shortNativeBuilder, mi); 16462 } else { 16463 extraNativeRam += mi.pss; 16464 extraNativeMemtrack += mi.memtrack; 16465 } 16466 } else { 16467 // Short form has all other details, but if we have collected RAM 16468 // from smaller native processes let's dump a summary of that. 16469 if (extraNativeRam > 0) { 16470 appendBasicMemEntry(shortNativeBuilder, ProcessList.NATIVE_ADJ, 16471 -1, extraNativeRam, extraNativeMemtrack, "(Other native)"); 16472 shortNativeBuilder.append('\n'); 16473 extraNativeRam = 0; 16474 } 16475 appendMemInfo(fullJavaBuilder, mi); 16476 } 16477 } 16478 16479 fullJavaBuilder.append(" "); 16480 ProcessList.appendRamKb(fullJavaBuilder, totalPss); 16481 fullJavaBuilder.append(": TOTAL"); 16482 if (totalMemtrack > 0) { 16483 fullJavaBuilder.append(" ("); 16484 fullJavaBuilder.append(stringifyKBSize(totalMemtrack)); 16485 fullJavaBuilder.append(" memtrack)"); 16486 } else { 16487 } 16488 fullJavaBuilder.append("\n"); 16489 16490 MemInfoReader memInfo = new MemInfoReader(); 16491 memInfo.readMemInfo(); 16492 final long[] infos = memInfo.getRawInfo(); 16493 16494 StringBuilder memInfoBuilder = new StringBuilder(1024); 16495 Debug.getMemInfo(infos); 16496 memInfoBuilder.append(" MemInfo: "); 16497 memInfoBuilder.append(stringifyKBSize(infos[Debug.MEMINFO_SLAB])).append(" slab, "); 16498 memInfoBuilder.append(stringifyKBSize(infos[Debug.MEMINFO_SHMEM])).append(" shmem, "); 16499 memInfoBuilder.append(stringifyKBSize( 16500 infos[Debug.MEMINFO_VM_ALLOC_USED])).append(" vm alloc, "); 16501 memInfoBuilder.append(stringifyKBSize( 16502 infos[Debug.MEMINFO_PAGE_TABLES])).append(" page tables "); 16503 memInfoBuilder.append(stringifyKBSize( 16504 infos[Debug.MEMINFO_KERNEL_STACK])).append(" kernel stack\n"); 16505 memInfoBuilder.append(" "); 16506 memInfoBuilder.append(stringifyKBSize(infos[Debug.MEMINFO_BUFFERS])).append(" buffers, "); 16507 memInfoBuilder.append(stringifyKBSize(infos[Debug.MEMINFO_CACHED])).append(" cached, "); 16508 memInfoBuilder.append(stringifyKBSize(infos[Debug.MEMINFO_MAPPED])).append(" mapped, "); 16509 memInfoBuilder.append(stringifyKBSize(infos[Debug.MEMINFO_FREE])).append(" free\n"); 16510 if (infos[Debug.MEMINFO_ZRAM_TOTAL] != 0) { 16511 memInfoBuilder.append(" ZRAM: "); 16512 memInfoBuilder.append(stringifyKBSize(infos[Debug.MEMINFO_ZRAM_TOTAL])); 16513 memInfoBuilder.append(" RAM, "); 16514 memInfoBuilder.append(stringifyKBSize(infos[Debug.MEMINFO_SWAP_TOTAL])); 16515 memInfoBuilder.append(" swap total, "); 16516 memInfoBuilder.append(stringifyKBSize(infos[Debug.MEMINFO_SWAP_FREE])); 16517 memInfoBuilder.append(" swap free\n"); 16518 } 16519 final long[] ksm = getKsmInfo(); 16520 if (ksm[KSM_SHARING] != 0 || ksm[KSM_SHARED] != 0 || ksm[KSM_UNSHARED] != 0 16521 || ksm[KSM_VOLATILE] != 0) { 16522 memInfoBuilder.append(" KSM: "); 16523 memInfoBuilder.append(stringifyKBSize(ksm[KSM_SHARING])); 16524 memInfoBuilder.append(" saved from shared "); 16525 memInfoBuilder.append(stringifyKBSize(ksm[KSM_SHARED])); 16526 memInfoBuilder.append("\n "); 16527 memInfoBuilder.append(stringifyKBSize(ksm[KSM_UNSHARED])); 16528 memInfoBuilder.append(" unshared; "); 16529 memInfoBuilder.append(stringifyKBSize(ksm[KSM_VOLATILE])); 16530 memInfoBuilder.append(" volatile\n"); 16531 } 16532 memInfoBuilder.append(" Free RAM: "); 16533 memInfoBuilder.append(stringifyKBSize(cachedPss + memInfo.getCachedSizeKb() 16534 + memInfo.getFreeSizeKb())); 16535 memInfoBuilder.append("\n"); 16536 memInfoBuilder.append(" Used RAM: "); 16537 memInfoBuilder.append(stringifyKBSize( 16538 totalPss - cachedPss + memInfo.getKernelUsedSizeKb())); 16539 memInfoBuilder.append("\n"); 16540 memInfoBuilder.append(" Lost RAM: "); 16541 memInfoBuilder.append(stringifyKBSize(memInfo.getTotalSizeKb() 16542 - totalPss - memInfo.getFreeSizeKb() - memInfo.getCachedSizeKb() 16543 - memInfo.getKernelUsedSizeKb() - memInfo.getZramTotalSizeKb())); 16544 memInfoBuilder.append("\n"); 16545 Slog.i(TAG, "Low on memory:"); 16546 Slog.i(TAG, shortNativeBuilder.toString()); 16547 Slog.i(TAG, fullJavaBuilder.toString()); 16548 Slog.i(TAG, memInfoBuilder.toString()); 16549 16550 StringBuilder dropBuilder = new StringBuilder(1024); 16551 /* 16552 StringWriter oomSw = new StringWriter(); 16553 PrintWriter oomPw = new FastPrintWriter(oomSw, false, 256); 16554 StringWriter catSw = new StringWriter(); 16555 PrintWriter catPw = new FastPrintWriter(catSw, false, 256); 16556 String[] emptyArgs = new String[] { }; 16557 dumpApplicationMemoryUsage(null, oomPw, " ", emptyArgs, true, catPw); 16558 oomPw.flush(); 16559 String oomString = oomSw.toString(); 16560 */ 16561 dropBuilder.append("Low on memory:"); 16562 dropBuilder.append(stack); 16563 dropBuilder.append('\n'); 16564 dropBuilder.append(fullNativeBuilder); 16565 dropBuilder.append(fullJavaBuilder); 16566 dropBuilder.append('\n'); 16567 dropBuilder.append(memInfoBuilder); 16568 dropBuilder.append('\n'); 16569 /* 16570 dropBuilder.append(oomString); 16571 dropBuilder.append('\n'); 16572 */ 16573 StringWriter catSw = new StringWriter(); 16574 synchronized (ActivityManagerService.this) { 16575 PrintWriter catPw = new FastPrintWriter(catSw, false, 256); 16576 String[] emptyArgs = new String[] { }; 16577 catPw.println(); 16578 dumpProcessesLocked(null, catPw, emptyArgs, 0, false, null); 16579 catPw.println(); 16580 mServices.newServiceDumperLocked(null, catPw, emptyArgs, 0, 16581 false, null).dumpLocked(); 16582 catPw.println(); 16583 dumpActivitiesLocked(null, catPw, emptyArgs, 0, false, false, null); 16584 catPw.flush(); 16585 } 16586 dropBuilder.append(catSw.toString()); 16587 addErrorToDropBox("lowmem", null, "system_server", null, 16588 null, tag.toString(), dropBuilder.toString(), null, null); 16589 //Slog.i(TAG, "Sent to dropbox:"); 16590 //Slog.i(TAG, dropBuilder.toString()); 16591 synchronized (ActivityManagerService.this) { 16592 long now = SystemClock.uptimeMillis(); 16593 if (mLastMemUsageReportTime < now) { 16594 mLastMemUsageReportTime = now; 16595 } 16596 } 16597 } 16598 16599 /** 16600 * Searches array of arguments for the specified string 16601 * @param args array of argument strings 16602 * @param value value to search for 16603 * @return true if the value is contained in the array 16604 */ 16605 private static boolean scanArgs(String[] args, String value) { 16606 if (args != null) { 16607 for (String arg : args) { 16608 if (value.equals(arg)) { 16609 return true; 16610 } 16611 } 16612 } 16613 return false; 16614 } 16615 16616 private final boolean removeDyingProviderLocked(ProcessRecord proc, 16617 ContentProviderRecord cpr, boolean always) { 16618 final boolean inLaunching = mLaunchingProviders.contains(cpr); 16619 16620 if (!inLaunching || always) { 16621 synchronized (cpr) { 16622 cpr.launchingApp = null; 16623 cpr.notifyAll(); 16624 } 16625 mProviderMap.removeProviderByClass(cpr.name, UserHandle.getUserId(cpr.uid)); 16626 String names[] = cpr.info.authority.split(";"); 16627 for (int j = 0; j < names.length; j++) { 16628 mProviderMap.removeProviderByName(names[j], UserHandle.getUserId(cpr.uid)); 16629 } 16630 } 16631 16632 for (int i = cpr.connections.size() - 1; i >= 0; i--) { 16633 ContentProviderConnection conn = cpr.connections.get(i); 16634 if (conn.waiting) { 16635 // If this connection is waiting for the provider, then we don't 16636 // need to mess with its process unless we are always removing 16637 // or for some reason the provider is not currently launching. 16638 if (inLaunching && !always) { 16639 continue; 16640 } 16641 } 16642 ProcessRecord capp = conn.client; 16643 conn.dead = true; 16644 if (conn.stableCount > 0) { 16645 if (!capp.persistent && capp.thread != null 16646 && capp.pid != 0 16647 && capp.pid != MY_PID) { 16648 capp.kill("depends on provider " 16649 + cpr.name.flattenToShortString() 16650 + " in dying proc " + (proc != null ? proc.processName : "??") 16651 + " (adj " + (proc != null ? proc.setAdj : "??") + ")", true); 16652 } 16653 } else if (capp.thread != null && conn.provider.provider != null) { 16654 try { 16655 capp.thread.unstableProviderDied(conn.provider.provider.asBinder()); 16656 } catch (RemoteException e) { 16657 } 16658 // In the protocol here, we don't expect the client to correctly 16659 // clean up this connection, we'll just remove it. 16660 cpr.connections.remove(i); 16661 if (conn.client.conProviders.remove(conn)) { 16662 stopAssociationLocked(capp.uid, capp.processName, cpr.uid, cpr.name); 16663 } 16664 } 16665 } 16666 16667 if (inLaunching && always) { 16668 mLaunchingProviders.remove(cpr); 16669 } 16670 return inLaunching; 16671 } 16672 16673 /** 16674 * Main code for cleaning up a process when it has gone away. This is 16675 * called both as a result of the process dying, or directly when stopping 16676 * a process when running in single process mode. 16677 * 16678 * @return Returns true if the given process has been restarted, so the 16679 * app that was passed in must remain on the process lists. 16680 */ 16681 private final boolean cleanUpApplicationRecordLocked(ProcessRecord app, 16682 boolean restarting, boolean allowRestart, int index, boolean replacingPid) { 16683 Slog.d(TAG, "cleanUpApplicationRecord -- " + app.pid); 16684 if (index >= 0) { 16685 removeLruProcessLocked(app); 16686 ProcessList.remove(app.pid); 16687 } 16688 16689 mProcessesToGc.remove(app); 16690 mPendingPssProcesses.remove(app); 16691 16692 // Dismiss any open dialogs. 16693 if (app.crashDialog != null && !app.forceCrashReport) { 16694 app.crashDialog.dismiss(); 16695 app.crashDialog = null; 16696 } 16697 if (app.anrDialog != null) { 16698 app.anrDialog.dismiss(); 16699 app.anrDialog = null; 16700 } 16701 if (app.waitDialog != null) { 16702 app.waitDialog.dismiss(); 16703 app.waitDialog = null; 16704 } 16705 16706 app.crashing = false; 16707 app.notResponding = false; 16708 16709 app.resetPackageList(mProcessStats); 16710 app.unlinkDeathRecipient(); 16711 app.makeInactive(mProcessStats); 16712 app.waitingToKill = null; 16713 app.forcingToForeground = null; 16714 updateProcessForegroundLocked(app, false, false); 16715 app.foregroundActivities = false; 16716 app.hasShownUi = false; 16717 app.treatLikeActivity = false; 16718 app.hasAboveClient = false; 16719 app.hasClientActivities = false; 16720 16721 mServices.killServicesLocked(app, allowRestart); 16722 16723 boolean restart = false; 16724 16725 // Remove published content providers. 16726 for (int i = app.pubProviders.size() - 1; i >= 0; i--) { 16727 ContentProviderRecord cpr = app.pubProviders.valueAt(i); 16728 final boolean always = app.bad || !allowRestart; 16729 boolean inLaunching = removeDyingProviderLocked(app, cpr, always); 16730 if ((inLaunching || always) && cpr.hasConnectionOrHandle()) { 16731 // We left the provider in the launching list, need to 16732 // restart it. 16733 restart = true; 16734 } 16735 16736 cpr.provider = null; 16737 cpr.proc = null; 16738 } 16739 app.pubProviders.clear(); 16740 16741 // Take care of any launching providers waiting for this process. 16742 if (cleanupAppInLaunchingProvidersLocked(app, false)) { 16743 restart = true; 16744 } 16745 16746 // Unregister from connected content providers. 16747 if (!app.conProviders.isEmpty()) { 16748 for (int i = app.conProviders.size() - 1; i >= 0; i--) { 16749 ContentProviderConnection conn = app.conProviders.get(i); 16750 conn.provider.connections.remove(conn); 16751 stopAssociationLocked(app.uid, app.processName, conn.provider.uid, 16752 conn.provider.name); 16753 } 16754 app.conProviders.clear(); 16755 } 16756 16757 // At this point there may be remaining entries in mLaunchingProviders 16758 // where we were the only one waiting, so they are no longer of use. 16759 // Look for these and clean up if found. 16760 // XXX Commented out for now. Trying to figure out a way to reproduce 16761 // the actual situation to identify what is actually going on. 16762 if (false) { 16763 for (int i = mLaunchingProviders.size() - 1; i >= 0; i--) { 16764 ContentProviderRecord cpr = mLaunchingProviders.get(i); 16765 if (cpr.connections.size() <= 0 && !cpr.hasExternalProcessHandles()) { 16766 synchronized (cpr) { 16767 cpr.launchingApp = null; 16768 cpr.notifyAll(); 16769 } 16770 } 16771 } 16772 } 16773 16774 skipCurrentReceiverLocked(app); 16775 16776 // Unregister any receivers. 16777 for (int i = app.receivers.size() - 1; i >= 0; i--) { 16778 removeReceiverLocked(app.receivers.valueAt(i)); 16779 } 16780 app.receivers.clear(); 16781 16782 // If the app is undergoing backup, tell the backup manager about it 16783 if (mBackupTarget != null && app.pid == mBackupTarget.app.pid) { 16784 if (DEBUG_BACKUP || DEBUG_CLEANUP) Slog.d(TAG_CLEANUP, "App " 16785 + mBackupTarget.appInfo + " died during backup"); 16786 try { 16787 IBackupManager bm = IBackupManager.Stub.asInterface( 16788 ServiceManager.getService(Context.BACKUP_SERVICE)); 16789 bm.agentDisconnected(app.info.packageName); 16790 } catch (RemoteException e) { 16791 // can't happen; backup manager is local 16792 } 16793 } 16794 16795 for (int i = mPendingProcessChanges.size() - 1; i >= 0; i--) { 16796 ProcessChangeItem item = mPendingProcessChanges.get(i); 16797 if (item.pid == app.pid) { 16798 mPendingProcessChanges.remove(i); 16799 mAvailProcessChanges.add(item); 16800 } 16801 } 16802 mUiHandler.obtainMessage(DISPATCH_PROCESS_DIED_UI_MSG, app.pid, app.info.uid, 16803 null).sendToTarget(); 16804 16805 // If the caller is restarting this app, then leave it in its 16806 // current lists and let the caller take care of it. 16807 if (restarting) { 16808 return false; 16809 } 16810 16811 if (!app.persistent || app.isolated) { 16812 if (DEBUG_PROCESSES || DEBUG_CLEANUP) Slog.v(TAG_CLEANUP, 16813 "Removing non-persistent process during cleanup: " + app); 16814 if (!replacingPid) { 16815 removeProcessNameLocked(app.processName, app.uid); 16816 } 16817 if (mHeavyWeightProcess == app) { 16818 mHandler.sendMessage(mHandler.obtainMessage(CANCEL_HEAVY_NOTIFICATION_MSG, 16819 mHeavyWeightProcess.userId, 0)); 16820 mHeavyWeightProcess = null; 16821 } 16822 } else if (!app.removed) { 16823 // This app is persistent, so we need to keep its record around. 16824 // If it is not already on the pending app list, add it there 16825 // and start a new process for it. 16826 if (mPersistentStartingProcesses.indexOf(app) < 0) { 16827 mPersistentStartingProcesses.add(app); 16828 restart = true; 16829 } 16830 } 16831 if ((DEBUG_PROCESSES || DEBUG_CLEANUP) && mProcessesOnHold.contains(app)) Slog.v( 16832 TAG_CLEANUP, "Clean-up removing on hold: " + app); 16833 mProcessesOnHold.remove(app); 16834 16835 if (app == mHomeProcess) { 16836 mHomeProcess = null; 16837 } 16838 if (app == mPreviousProcess) { 16839 mPreviousProcess = null; 16840 } 16841 16842 if (restart && !app.isolated) { 16843 // We have components that still need to be running in the 16844 // process, so re-launch it. 16845 if (index < 0) { 16846 ProcessList.remove(app.pid); 16847 } 16848 addProcessNameLocked(app); 16849 startProcessLocked(app, "restart", app.processName); 16850 return true; 16851 } else if (app.pid > 0 && app.pid != MY_PID) { 16852 // Goodbye! 16853 boolean removed; 16854 synchronized (mPidsSelfLocked) { 16855 mPidsSelfLocked.remove(app.pid); 16856 mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app); 16857 } 16858 mBatteryStatsService.noteProcessFinish(app.processName, app.info.uid); 16859 if (app.isolated) { 16860 mBatteryStatsService.removeIsolatedUid(app.uid, app.info.uid); 16861 } 16862 app.setPid(0); 16863 } 16864 return false; 16865 } 16866 16867 boolean checkAppInLaunchingProvidersLocked(ProcessRecord app) { 16868 for (int i = mLaunchingProviders.size() - 1; i >= 0; i--) { 16869 ContentProviderRecord cpr = mLaunchingProviders.get(i); 16870 if (cpr.launchingApp == app) { 16871 return true; 16872 } 16873 } 16874 return false; 16875 } 16876 16877 boolean cleanupAppInLaunchingProvidersLocked(ProcessRecord app, boolean alwaysBad) { 16878 // Look through the content providers we are waiting to have launched, 16879 // and if any run in this process then either schedule a restart of 16880 // the process or kill the client waiting for it if this process has 16881 // gone bad. 16882 boolean restart = false; 16883 for (int i = mLaunchingProviders.size() - 1; i >= 0; i--) { 16884 ContentProviderRecord cpr = mLaunchingProviders.get(i); 16885 if (cpr.launchingApp == app) { 16886 if (!alwaysBad && !app.bad && cpr.hasConnectionOrHandle()) { 16887 restart = true; 16888 } else { 16889 removeDyingProviderLocked(app, cpr, true); 16890 } 16891 } 16892 } 16893 return restart; 16894 } 16895 16896 // ========================================================= 16897 // SERVICES 16898 // ========================================================= 16899 16900 @Override 16901 public List<ActivityManager.RunningServiceInfo> getServices(int maxNum, 16902 int flags) { 16903 enforceNotIsolatedCaller("getServices"); 16904 synchronized (this) { 16905 return mServices.getRunningServiceInfoLocked(maxNum, flags); 16906 } 16907 } 16908 16909 @Override 16910 public PendingIntent getRunningServiceControlPanel(ComponentName name) { 16911 enforceNotIsolatedCaller("getRunningServiceControlPanel"); 16912 synchronized (this) { 16913 return mServices.getRunningServiceControlPanelLocked(name); 16914 } 16915 } 16916 16917 @Override 16918 public ComponentName startService(IApplicationThread caller, Intent service, 16919 String resolvedType, String callingPackage, int userId) 16920 throws TransactionTooLargeException { 16921 enforceNotIsolatedCaller("startService"); 16922 // Refuse possible leaked file descriptors 16923 if (service != null && service.hasFileDescriptors() == true) { 16924 throw new IllegalArgumentException("File descriptors passed in Intent"); 16925 } 16926 16927 if (callingPackage == null) { 16928 throw new IllegalArgumentException("callingPackage cannot be null"); 16929 } 16930 16931 if (DEBUG_SERVICE) Slog.v(TAG_SERVICE, 16932 "startService: " + service + " type=" + resolvedType); 16933 synchronized(this) { 16934 final int callingPid = Binder.getCallingPid(); 16935 final int callingUid = Binder.getCallingUid(); 16936 final long origId = Binder.clearCallingIdentity(); 16937 ComponentName res = mServices.startServiceLocked(caller, service, 16938 resolvedType, callingPid, callingUid, callingPackage, userId); 16939 Binder.restoreCallingIdentity(origId); 16940 return res; 16941 } 16942 } 16943 16944 ComponentName startServiceInPackage(int uid, Intent service, String resolvedType, 16945 String callingPackage, int userId) 16946 throws TransactionTooLargeException { 16947 synchronized(this) { 16948 if (DEBUG_SERVICE) Slog.v(TAG_SERVICE, 16949 "startServiceInPackage: " + service + " type=" + resolvedType); 16950 final long origId = Binder.clearCallingIdentity(); 16951 ComponentName res = mServices.startServiceLocked(null, service, 16952 resolvedType, -1, uid, callingPackage, userId); 16953 Binder.restoreCallingIdentity(origId); 16954 return res; 16955 } 16956 } 16957 16958 @Override 16959 public int stopService(IApplicationThread caller, Intent service, 16960 String resolvedType, int userId) { 16961 enforceNotIsolatedCaller("stopService"); 16962 // Refuse possible leaked file descriptors 16963 if (service != null && service.hasFileDescriptors() == true) { 16964 throw new IllegalArgumentException("File descriptors passed in Intent"); 16965 } 16966 16967 synchronized(this) { 16968 return mServices.stopServiceLocked(caller, service, resolvedType, userId); 16969 } 16970 } 16971 16972 @Override 16973 public IBinder peekService(Intent service, String resolvedType, String callingPackage) { 16974 enforceNotIsolatedCaller("peekService"); 16975 // Refuse possible leaked file descriptors 16976 if (service != null && service.hasFileDescriptors() == true) { 16977 throw new IllegalArgumentException("File descriptors passed in Intent"); 16978 } 16979 16980 if (callingPackage == null) { 16981 throw new IllegalArgumentException("callingPackage cannot be null"); 16982 } 16983 16984 synchronized(this) { 16985 return mServices.peekServiceLocked(service, resolvedType, callingPackage); 16986 } 16987 } 16988 16989 @Override 16990 public boolean stopServiceToken(ComponentName className, IBinder token, 16991 int startId) { 16992 synchronized(this) { 16993 return mServices.stopServiceTokenLocked(className, token, startId); 16994 } 16995 } 16996 16997 @Override 16998 public void setServiceForeground(ComponentName className, IBinder token, 16999 int id, Notification notification, int flags) { 17000 synchronized(this) { 17001 mServices.setServiceForegroundLocked(className, token, id, notification, flags); 17002 } 17003 } 17004 17005 @Override 17006 public int handleIncomingUser(int callingPid, int callingUid, int userId, boolean allowAll, 17007 boolean requireFull, String name, String callerPackage) { 17008 return mUserController.handleIncomingUser(callingPid, callingUid, userId, allowAll, 17009 requireFull ? ALLOW_FULL_ONLY : ALLOW_NON_FULL, name, callerPackage); 17010 } 17011 17012 boolean isSingleton(String componentProcessName, ApplicationInfo aInfo, 17013 String className, int flags) { 17014 boolean result = false; 17015 // For apps that don't have pre-defined UIDs, check for permission 17016 if (UserHandle.getAppId(aInfo.uid) >= Process.FIRST_APPLICATION_UID) { 17017 if ((flags & ServiceInfo.FLAG_SINGLE_USER) != 0) { 17018 if (ActivityManager.checkUidPermission( 17019 INTERACT_ACROSS_USERS, 17020 aInfo.uid) != PackageManager.PERMISSION_GRANTED) { 17021 ComponentName comp = new ComponentName(aInfo.packageName, className); 17022 String msg = "Permission Denial: Component " + comp.flattenToShortString() 17023 + " requests FLAG_SINGLE_USER, but app does not hold " 17024 + INTERACT_ACROSS_USERS; 17025 Slog.w(TAG, msg); 17026 throw new SecurityException(msg); 17027 } 17028 // Permission passed 17029 result = true; 17030 } 17031 } else if ("system".equals(componentProcessName)) { 17032 result = true; 17033 } else if ((flags & ServiceInfo.FLAG_SINGLE_USER) != 0) { 17034 // Phone app and persistent apps are allowed to export singleuser providers. 17035 result = UserHandle.isSameApp(aInfo.uid, Process.PHONE_UID) 17036 || (aInfo.flags & ApplicationInfo.FLAG_PERSISTENT) != 0; 17037 } 17038 if (DEBUG_MU) Slog.v(TAG_MU, 17039 "isSingleton(" + componentProcessName + ", " + aInfo + ", " + className + ", 0x" 17040 + Integer.toHexString(flags) + ") = " + result); 17041 return result; 17042 } 17043 17044 /** 17045 * Checks to see if the caller is in the same app as the singleton 17046 * component, or the component is in a special app. It allows special apps 17047 * to export singleton components but prevents exporting singleton 17048 * components for regular apps. 17049 */ 17050 boolean isValidSingletonCall(int callingUid, int componentUid) { 17051 int componentAppId = UserHandle.getAppId(componentUid); 17052 return UserHandle.isSameApp(callingUid, componentUid) 17053 || componentAppId == Process.SYSTEM_UID 17054 || componentAppId == Process.PHONE_UID 17055 || ActivityManager.checkUidPermission(INTERACT_ACROSS_USERS_FULL, componentUid) 17056 == PackageManager.PERMISSION_GRANTED; 17057 } 17058 17059 public int bindService(IApplicationThread caller, IBinder token, Intent service, 17060 String resolvedType, IServiceConnection connection, int flags, String callingPackage, 17061 int userId) throws TransactionTooLargeException { 17062 enforceNotIsolatedCaller("bindService"); 17063 17064 // Refuse possible leaked file descriptors 17065 if (service != null && service.hasFileDescriptors() == true) { 17066 throw new IllegalArgumentException("File descriptors passed in Intent"); 17067 } 17068 17069 if (callingPackage == null) { 17070 throw new IllegalArgumentException("callingPackage cannot be null"); 17071 } 17072 17073 synchronized(this) { 17074 return mServices.bindServiceLocked(caller, token, service, 17075 resolvedType, connection, flags, callingPackage, userId); 17076 } 17077 } 17078 17079 public boolean unbindService(IServiceConnection connection) { 17080 synchronized (this) { 17081 return mServices.unbindServiceLocked(connection); 17082 } 17083 } 17084 17085 public void publishService(IBinder token, Intent intent, IBinder service) { 17086 // Refuse possible leaked file descriptors 17087 if (intent != null && intent.hasFileDescriptors() == true) { 17088 throw new IllegalArgumentException("File descriptors passed in Intent"); 17089 } 17090 17091 synchronized(this) { 17092 if (!(token instanceof ServiceRecord)) { 17093 throw new IllegalArgumentException("Invalid service token"); 17094 } 17095 mServices.publishServiceLocked((ServiceRecord)token, intent, service); 17096 } 17097 } 17098 17099 public void unbindFinished(IBinder token, Intent intent, boolean doRebind) { 17100 // Refuse possible leaked file descriptors 17101 if (intent != null && intent.hasFileDescriptors() == true) { 17102 throw new IllegalArgumentException("File descriptors passed in Intent"); 17103 } 17104 17105 synchronized(this) { 17106 mServices.unbindFinishedLocked((ServiceRecord)token, intent, doRebind); 17107 } 17108 } 17109 17110 public void serviceDoneExecuting(IBinder token, int type, int startId, int res) { 17111 synchronized(this) { 17112 if (!(token instanceof ServiceRecord)) { 17113 Slog.e(TAG, "serviceDoneExecuting: Invalid service token=" + token); 17114 throw new IllegalArgumentException("Invalid service token"); 17115 } 17116 mServices.serviceDoneExecutingLocked((ServiceRecord)token, type, startId, res); 17117 } 17118 } 17119 17120 // ========================================================= 17121 // BACKUP AND RESTORE 17122 // ========================================================= 17123 17124 // Cause the target app to be launched if necessary and its backup agent 17125 // instantiated. The backup agent will invoke backupAgentCreated() on the 17126 // activity manager to announce its creation. 17127 public boolean bindBackupAgent(String packageName, int backupMode, int userId) { 17128 if (DEBUG_BACKUP) Slog.v(TAG, "bindBackupAgent: app=" + packageName + " mode=" + backupMode); 17129 enforceCallingPermission("android.permission.CONFIRM_FULL_BACKUP", "bindBackupAgent"); 17130 17131 IPackageManager pm = AppGlobals.getPackageManager(); 17132 ApplicationInfo app = null; 17133 try { 17134 app = pm.getApplicationInfo(packageName, 0, userId); 17135 } catch (RemoteException e) { 17136 // can't happen; package manager is process-local 17137 } 17138 if (app == null) { 17139 Slog.w(TAG, "Unable to bind backup agent for " + packageName); 17140 return false; 17141 } 17142 17143 synchronized(this) { 17144 // !!! TODO: currently no check here that we're already bound 17145 BatteryStatsImpl.Uid.Pkg.Serv ss = null; 17146 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 17147 synchronized (stats) { 17148 ss = stats.getServiceStatsLocked(app.uid, app.packageName, app.name); 17149 } 17150 17151 // Backup agent is now in use, its package can't be stopped. 17152 try { 17153 AppGlobals.getPackageManager().setPackageStoppedState( 17154 app.packageName, false, UserHandle.getUserId(app.uid)); 17155 } catch (RemoteException e) { 17156 } catch (IllegalArgumentException e) { 17157 Slog.w(TAG, "Failed trying to unstop package " 17158 + app.packageName + ": " + e); 17159 } 17160 17161 BackupRecord r = new BackupRecord(ss, app, backupMode); 17162 ComponentName hostingName = 17163 (backupMode == ApplicationThreadConstants.BACKUP_MODE_INCREMENTAL) 17164 ? new ComponentName(app.packageName, app.backupAgentName) 17165 : new ComponentName("android", "FullBackupAgent"); 17166 // startProcessLocked() returns existing proc's record if it's already running 17167 ProcessRecord proc = startProcessLocked(app.processName, app, 17168 false, 0, "backup", hostingName, false, false, false); 17169 if (proc == null) { 17170 Slog.e(TAG, "Unable to start backup agent process " + r); 17171 return false; 17172 } 17173 17174 // If the app is a regular app (uid >= 10000) and not the system server or phone 17175 // process, etc, then mark it as being in full backup so that certain calls to the 17176 // process can be blocked. This is not reset to false anywhere because we kill the 17177 // process after the full backup is done and the ProcessRecord will vaporize anyway. 17178 if (UserHandle.isApp(app.uid) && 17179 backupMode == ApplicationThreadConstants.BACKUP_MODE_FULL) { 17180 proc.inFullBackup = true; 17181 } 17182 r.app = proc; 17183 mBackupTarget = r; 17184 mBackupAppName = app.packageName; 17185 17186 // Try not to kill the process during backup 17187 updateOomAdjLocked(proc); 17188 17189 // If the process is already attached, schedule the creation of the backup agent now. 17190 // If it is not yet live, this will be done when it attaches to the framework. 17191 if (proc.thread != null) { 17192 if (DEBUG_BACKUP) Slog.v(TAG_BACKUP, "Agent proc already running: " + proc); 17193 try { 17194 proc.thread.scheduleCreateBackupAgent(app, 17195 compatibilityInfoForPackageLocked(app), backupMode); 17196 } catch (RemoteException e) { 17197 // Will time out on the backup manager side 17198 } 17199 } else { 17200 if (DEBUG_BACKUP) Slog.v(TAG_BACKUP, "Agent proc not running, waiting for attach"); 17201 } 17202 // Invariants: at this point, the target app process exists and the application 17203 // is either already running or in the process of coming up. mBackupTarget and 17204 // mBackupAppName describe the app, so that when it binds back to the AM we 17205 // know that it's scheduled for a backup-agent operation. 17206 } 17207 17208 return true; 17209 } 17210 17211 @Override 17212 public void clearPendingBackup() { 17213 if (DEBUG_BACKUP) Slog.v(TAG_BACKUP, "clearPendingBackup"); 17214 enforceCallingPermission("android.permission.BACKUP", "clearPendingBackup"); 17215 17216 synchronized (this) { 17217 mBackupTarget = null; 17218 mBackupAppName = null; 17219 } 17220 } 17221 17222 // A backup agent has just come up 17223 public void backupAgentCreated(String agentPackageName, IBinder agent) { 17224 if (DEBUG_BACKUP) Slog.v(TAG_BACKUP, "backupAgentCreated: " + agentPackageName 17225 + " = " + agent); 17226 17227 synchronized(this) { 17228 if (!agentPackageName.equals(mBackupAppName)) { 17229 Slog.e(TAG, "Backup agent created for " + agentPackageName + " but not requested!"); 17230 return; 17231 } 17232 } 17233 17234 long oldIdent = Binder.clearCallingIdentity(); 17235 try { 17236 IBackupManager bm = IBackupManager.Stub.asInterface( 17237 ServiceManager.getService(Context.BACKUP_SERVICE)); 17238 bm.agentConnected(agentPackageName, agent); 17239 } catch (RemoteException e) { 17240 // can't happen; the backup manager service is local 17241 } catch (Exception e) { 17242 Slog.w(TAG, "Exception trying to deliver BackupAgent binding: "); 17243 e.printStackTrace(); 17244 } finally { 17245 Binder.restoreCallingIdentity(oldIdent); 17246 } 17247 } 17248 17249 // done with this agent 17250 public void unbindBackupAgent(ApplicationInfo appInfo) { 17251 if (DEBUG_BACKUP) Slog.v(TAG_BACKUP, "unbindBackupAgent: " + appInfo); 17252 if (appInfo == null) { 17253 Slog.w(TAG, "unbind backup agent for null app"); 17254 return; 17255 } 17256 17257 synchronized(this) { 17258 try { 17259 if (mBackupAppName == null) { 17260 Slog.w(TAG, "Unbinding backup agent with no active backup"); 17261 return; 17262 } 17263 17264 if (!mBackupAppName.equals(appInfo.packageName)) { 17265 Slog.e(TAG, "Unbind of " + appInfo + " but is not the current backup target"); 17266 return; 17267 } 17268 17269 // Not backing this app up any more; reset its OOM adjustment 17270 final ProcessRecord proc = mBackupTarget.app; 17271 updateOomAdjLocked(proc); 17272 17273 // If the app crashed during backup, 'thread' will be null here 17274 if (proc.thread != null) { 17275 try { 17276 proc.thread.scheduleDestroyBackupAgent(appInfo, 17277 compatibilityInfoForPackageLocked(appInfo)); 17278 } catch (Exception e) { 17279 Slog.e(TAG, "Exception when unbinding backup agent:"); 17280 e.printStackTrace(); 17281 } 17282 } 17283 } finally { 17284 mBackupTarget = null; 17285 mBackupAppName = null; 17286 } 17287 } 17288 } 17289 // ========================================================= 17290 // BROADCASTS 17291 // ========================================================= 17292 17293 boolean isPendingBroadcastProcessLocked(int pid) { 17294 return mFgBroadcastQueue.isPendingBroadcastProcessLocked(pid) 17295 || mBgBroadcastQueue.isPendingBroadcastProcessLocked(pid); 17296 } 17297 17298 void skipPendingBroadcastLocked(int pid) { 17299 Slog.w(TAG, "Unattached app died before broadcast acknowledged, skipping"); 17300 for (BroadcastQueue queue : mBroadcastQueues) { 17301 queue.skipPendingBroadcastLocked(pid); 17302 } 17303 } 17304 17305 // The app just attached; send any pending broadcasts that it should receive 17306 boolean sendPendingBroadcastsLocked(ProcessRecord app) { 17307 boolean didSomething = false; 17308 for (BroadcastQueue queue : mBroadcastQueues) { 17309 didSomething |= queue.sendPendingBroadcastsLocked(app); 17310 } 17311 return didSomething; 17312 } 17313 17314 public Intent registerReceiver(IApplicationThread caller, String callerPackage, 17315 IIntentReceiver receiver, IntentFilter filter, String permission, int userId) { 17316 enforceNotIsolatedCaller("registerReceiver"); 17317 ArrayList<Intent> stickyIntents = null; 17318 ProcessRecord callerApp = null; 17319 int callingUid; 17320 int callingPid; 17321 synchronized(this) { 17322 if (caller != null) { 17323 callerApp = getRecordForAppLocked(caller); 17324 if (callerApp == null) { 17325 throw new SecurityException( 17326 "Unable to find app for caller " + caller 17327 + " (pid=" + Binder.getCallingPid() 17328 + ") when registering receiver " + receiver); 17329 } 17330 if (callerApp.info.uid != Process.SYSTEM_UID && 17331 !callerApp.pkgList.containsKey(callerPackage) && 17332 !"android".equals(callerPackage)) { 17333 throw new SecurityException("Given caller package " + callerPackage 17334 + " is not running in process " + callerApp); 17335 } 17336 callingUid = callerApp.info.uid; 17337 callingPid = callerApp.pid; 17338 } else { 17339 callerPackage = null; 17340 callingUid = Binder.getCallingUid(); 17341 callingPid = Binder.getCallingPid(); 17342 } 17343 17344 userId = mUserController.handleIncomingUser(callingPid, callingUid, userId, true, 17345 ALLOW_FULL_ONLY, "registerReceiver", callerPackage); 17346 17347 Iterator<String> actions = filter.actionsIterator(); 17348 if (actions == null) { 17349 ArrayList<String> noAction = new ArrayList<String>(1); 17350 noAction.add(null); 17351 actions = noAction.iterator(); 17352 } 17353 17354 // Collect stickies of users 17355 int[] userIds = { UserHandle.USER_ALL, UserHandle.getUserId(callingUid) }; 17356 while (actions.hasNext()) { 17357 String action = actions.next(); 17358 for (int id : userIds) { 17359 ArrayMap<String, ArrayList<Intent>> stickies = mStickyBroadcasts.get(id); 17360 if (stickies != null) { 17361 ArrayList<Intent> intents = stickies.get(action); 17362 if (intents != null) { 17363 if (stickyIntents == null) { 17364 stickyIntents = new ArrayList<Intent>(); 17365 } 17366 stickyIntents.addAll(intents); 17367 } 17368 } 17369 } 17370 } 17371 } 17372 17373 ArrayList<Intent> allSticky = null; 17374 if (stickyIntents != null) { 17375 final ContentResolver resolver = mContext.getContentResolver(); 17376 // Look for any matching sticky broadcasts... 17377 for (int i = 0, N = stickyIntents.size(); i < N; i++) { 17378 Intent intent = stickyIntents.get(i); 17379 // If intent has scheme "content", it will need to acccess 17380 // provider that needs to lock mProviderMap in ActivityThread 17381 // and also it may need to wait application response, so we 17382 // cannot lock ActivityManagerService here. 17383 if (filter.match(resolver, intent, true, TAG) >= 0) { 17384 if (allSticky == null) { 17385 allSticky = new ArrayList<Intent>(); 17386 } 17387 allSticky.add(intent); 17388 } 17389 } 17390 } 17391 17392 // The first sticky in the list is returned directly back to the client. 17393 Intent sticky = allSticky != null ? allSticky.get(0) : null; 17394 if (DEBUG_BROADCAST) Slog.v(TAG_BROADCAST, "Register receiver " + filter + ": " + sticky); 17395 if (receiver == null) { 17396 return sticky; 17397 } 17398 17399 synchronized (this) { 17400 if (callerApp != null && (callerApp.thread == null 17401 || callerApp.thread.asBinder() != caller.asBinder())) { 17402 // Original caller already died 17403 return null; 17404 } 17405 ReceiverList rl = mRegisteredReceivers.get(receiver.asBinder()); 17406 if (rl == null) { 17407 rl = new ReceiverList(this, callerApp, callingPid, callingUid, 17408 userId, receiver); 17409 if (rl.app != null) { 17410 rl.app.receivers.add(rl); 17411 } else { 17412 try { 17413 receiver.asBinder().linkToDeath(rl, 0); 17414 } catch (RemoteException e) { 17415 return sticky; 17416 } 17417 rl.linkedToDeath = true; 17418 } 17419 mRegisteredReceivers.put(receiver.asBinder(), rl); 17420 } else if (rl.uid != callingUid) { 17421 throw new IllegalArgumentException( 17422 "Receiver requested to register for uid " + callingUid 17423 + " was previously registered for uid " + rl.uid); 17424 } else if (rl.pid != callingPid) { 17425 throw new IllegalArgumentException( 17426 "Receiver requested to register for pid " + callingPid 17427 + " was previously registered for pid " + rl.pid); 17428 } else if (rl.userId != userId) { 17429 throw new IllegalArgumentException( 17430 "Receiver requested to register for user " + userId 17431 + " was previously registered for user " + rl.userId); 17432 } 17433 BroadcastFilter bf = new BroadcastFilter(filter, rl, callerPackage, 17434 permission, callingUid, userId); 17435 rl.add(bf); 17436 if (!bf.debugCheck()) { 17437 Slog.w(TAG, "==> For Dynamic broadcast"); 17438 } 17439 mReceiverResolver.addFilter(bf); 17440 17441 // Enqueue broadcasts for all existing stickies that match 17442 // this filter. 17443 if (allSticky != null) { 17444 ArrayList receivers = new ArrayList(); 17445 receivers.add(bf); 17446 17447 final int stickyCount = allSticky.size(); 17448 for (int i = 0; i < stickyCount; i++) { 17449 Intent intent = allSticky.get(i); 17450 BroadcastQueue queue = broadcastQueueForIntent(intent); 17451 BroadcastRecord r = new BroadcastRecord(queue, intent, null, 17452 null, -1, -1, null, null, AppOpsManager.OP_NONE, null, receivers, 17453 null, 0, null, null, false, true, true, -1); 17454 queue.enqueueParallelBroadcastLocked(r); 17455 queue.scheduleBroadcastsLocked(); 17456 } 17457 } 17458 17459 return sticky; 17460 } 17461 } 17462 17463 public void unregisterReceiver(IIntentReceiver receiver) { 17464 if (DEBUG_BROADCAST) Slog.v(TAG_BROADCAST, "Unregister receiver: " + receiver); 17465 17466 final long origId = Binder.clearCallingIdentity(); 17467 try { 17468 boolean doTrim = false; 17469 17470 synchronized(this) { 17471 ReceiverList rl = mRegisteredReceivers.get(receiver.asBinder()); 17472 if (rl != null) { 17473 final BroadcastRecord r = rl.curBroadcast; 17474 if (r != null && r == r.queue.getMatchingOrderedReceiver(r)) { 17475 final boolean doNext = r.queue.finishReceiverLocked( 17476 r, r.resultCode, r.resultData, r.resultExtras, 17477 r.resultAbort, false); 17478 if (doNext) { 17479 doTrim = true; 17480 r.queue.processNextBroadcast(false); 17481 } 17482 } 17483 17484 if (rl.app != null) { 17485 rl.app.receivers.remove(rl); 17486 } 17487 removeReceiverLocked(rl); 17488 if (rl.linkedToDeath) { 17489 rl.linkedToDeath = false; 17490 rl.receiver.asBinder().unlinkToDeath(rl, 0); 17491 } 17492 } 17493 } 17494 17495 // If we actually concluded any broadcasts, we might now be able 17496 // to trim the recipients' apps from our working set 17497 if (doTrim) { 17498 trimApplications(); 17499 return; 17500 } 17501 17502 } finally { 17503 Binder.restoreCallingIdentity(origId); 17504 } 17505 } 17506 17507 void removeReceiverLocked(ReceiverList rl) { 17508 mRegisteredReceivers.remove(rl.receiver.asBinder()); 17509 for (int i = rl.size() - 1; i >= 0; i--) { 17510 mReceiverResolver.removeFilter(rl.get(i)); 17511 } 17512 } 17513 17514 private final void sendPackageBroadcastLocked(int cmd, String[] packages, int userId) { 17515 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 17516 ProcessRecord r = mLruProcesses.get(i); 17517 if (r.thread != null && (userId == UserHandle.USER_ALL || r.userId == userId)) { 17518 try { 17519 r.thread.dispatchPackageBroadcast(cmd, packages); 17520 } catch (RemoteException ex) { 17521 } 17522 } 17523 } 17524 } 17525 17526 private List<ResolveInfo> collectReceiverComponents(Intent intent, String resolvedType, 17527 int callingUid, int[] users) { 17528 // TODO: come back and remove this assumption to triage all broadcasts 17529 int pmFlags = STOCK_PM_FLAGS | MATCH_DEBUG_TRIAGED_MISSING; 17530 17531 List<ResolveInfo> receivers = null; 17532 try { 17533 HashSet<ComponentName> singleUserReceivers = null; 17534 boolean scannedFirstReceivers = false; 17535 for (int user : users) { 17536 // Skip users that have Shell restrictions, with exception of always permitted 17537 // Shell broadcasts 17538 if (callingUid == Process.SHELL_UID 17539 && mUserController.hasUserRestriction( 17540 UserManager.DISALLOW_DEBUGGING_FEATURES, user) 17541 && !isPermittedShellBroadcast(intent)) { 17542 continue; 17543 } 17544 List<ResolveInfo> newReceivers = AppGlobals.getPackageManager() 17545 .queryIntentReceivers(intent, resolvedType, pmFlags, user).getList(); 17546 if (user != UserHandle.USER_SYSTEM && newReceivers != null) { 17547 // If this is not the system user, we need to check for 17548 // any receivers that should be filtered out. 17549 for (int i=0; i<newReceivers.size(); i++) { 17550 ResolveInfo ri = newReceivers.get(i); 17551 if ((ri.activityInfo.flags&ActivityInfo.FLAG_SYSTEM_USER_ONLY) != 0) { 17552 newReceivers.remove(i); 17553 i--; 17554 } 17555 } 17556 } 17557 if (newReceivers != null && newReceivers.size() == 0) { 17558 newReceivers = null; 17559 } 17560 if (receivers == null) { 17561 receivers = newReceivers; 17562 } else if (newReceivers != null) { 17563 // We need to concatenate the additional receivers 17564 // found with what we have do far. This would be easy, 17565 // but we also need to de-dup any receivers that are 17566 // singleUser. 17567 if (!scannedFirstReceivers) { 17568 // Collect any single user receivers we had already retrieved. 17569 scannedFirstReceivers = true; 17570 for (int i=0; i<receivers.size(); i++) { 17571 ResolveInfo ri = receivers.get(i); 17572 if ((ri.activityInfo.flags&ActivityInfo.FLAG_SINGLE_USER) != 0) { 17573 ComponentName cn = new ComponentName( 17574 ri.activityInfo.packageName, ri.activityInfo.name); 17575 if (singleUserReceivers == null) { 17576 singleUserReceivers = new HashSet<ComponentName>(); 17577 } 17578 singleUserReceivers.add(cn); 17579 } 17580 } 17581 } 17582 // Add the new results to the existing results, tracking 17583 // and de-dupping single user receivers. 17584 for (int i=0; i<newReceivers.size(); i++) { 17585 ResolveInfo ri = newReceivers.get(i); 17586 if ((ri.activityInfo.flags&ActivityInfo.FLAG_SINGLE_USER) != 0) { 17587 ComponentName cn = new ComponentName( 17588 ri.activityInfo.packageName, ri.activityInfo.name); 17589 if (singleUserReceivers == null) { 17590 singleUserReceivers = new HashSet<ComponentName>(); 17591 } 17592 if (!singleUserReceivers.contains(cn)) { 17593 singleUserReceivers.add(cn); 17594 receivers.add(ri); 17595 } 17596 } else { 17597 receivers.add(ri); 17598 } 17599 } 17600 } 17601 } 17602 } catch (RemoteException ex) { 17603 // pm is in same process, this will never happen. 17604 } 17605 return receivers; 17606 } 17607 17608 private boolean isPermittedShellBroadcast(Intent intent) { 17609 // remote bugreport should always be allowed to be taken 17610 return INTENT_REMOTE_BUGREPORT_FINISHED.equals(intent.getAction()); 17611 } 17612 17613 private void checkBroadcastFromSystem(Intent intent, ProcessRecord callerApp, 17614 String callerPackage, int callingUid, boolean isProtectedBroadcast, List receivers) { 17615 final String action = intent.getAction(); 17616 if (isProtectedBroadcast 17617 || Intent.ACTION_CLOSE_SYSTEM_DIALOGS.equals(action) 17618 || Intent.ACTION_DISMISS_KEYBOARD_SHORTCUTS.equals(action) 17619 || Intent.ACTION_MEDIA_BUTTON.equals(action) 17620 || Intent.ACTION_MEDIA_SCANNER_SCAN_FILE.equals(action) 17621 || Intent.ACTION_SHOW_KEYBOARD_SHORTCUTS.equals(action) 17622 || Intent.ACTION_MASTER_CLEAR.equals(action) 17623 || AppWidgetManager.ACTION_APPWIDGET_CONFIGURE.equals(action) 17624 || AppWidgetManager.ACTION_APPWIDGET_UPDATE.equals(action) 17625 || LocationManager.HIGH_POWER_REQUEST_CHANGE_ACTION.equals(action) 17626 || TelephonyIntents.ACTION_REQUEST_OMADM_CONFIGURATION_UPDATE.equals(action) 17627 || SuggestionSpan.ACTION_SUGGESTION_PICKED.equals(action)) { 17628 // Broadcast is either protected, or it's a public action that 17629 // we've relaxed, so it's fine for system internals to send. 17630 return; 17631 } 17632 17633 // This broadcast may be a problem... but there are often system components that 17634 // want to send an internal broadcast to themselves, which is annoying to have to 17635 // explicitly list each action as a protected broadcast, so we will check for that 17636 // one safe case and allow it: an explicit broadcast, only being received by something 17637 // that has protected itself. 17638 if (receivers != null && receivers.size() > 0 17639 && (intent.getPackage() != null || intent.getComponent() != null)) { 17640 boolean allProtected = true; 17641 for (int i = receivers.size()-1; i >= 0; i--) { 17642 Object target = receivers.get(i); 17643 if (target instanceof ResolveInfo) { 17644 ResolveInfo ri = (ResolveInfo)target; 17645 if (ri.activityInfo.exported && ri.activityInfo.permission == null) { 17646 allProtected = false; 17647 break; 17648 } 17649 } else { 17650 BroadcastFilter bf = (BroadcastFilter)target; 17651 if (bf.requiredPermission == null) { 17652 allProtected = false; 17653 break; 17654 } 17655 } 17656 } 17657 if (allProtected) { 17658 // All safe! 17659 return; 17660 } 17661 } 17662 17663 // The vast majority of broadcasts sent from system internals 17664 // should be protected to avoid security holes, so yell loudly 17665 // to ensure we examine these cases. 17666 if (callerApp != null) { 17667 Log.wtf(TAG, "Sending non-protected broadcast " + action 17668 + " from system " + callerApp.toShortString() + " pkg " + callerPackage, 17669 new Throwable()); 17670 } else { 17671 Log.wtf(TAG, "Sending non-protected broadcast " + action 17672 + " from system uid " + UserHandle.formatUid(callingUid) 17673 + " pkg " + callerPackage, 17674 new Throwable()); 17675 } 17676 } 17677 17678 final int broadcastIntentLocked(ProcessRecord callerApp, 17679 String callerPackage, Intent intent, String resolvedType, 17680 IIntentReceiver resultTo, int resultCode, String resultData, 17681 Bundle resultExtras, String[] requiredPermissions, int appOp, Bundle bOptions, 17682 boolean ordered, boolean sticky, int callingPid, int callingUid, int userId) { 17683 intent = new Intent(intent); 17684 17685 // By default broadcasts do not go to stopped apps. 17686 intent.addFlags(Intent.FLAG_EXCLUDE_STOPPED_PACKAGES); 17687 17688 // If we have not finished booting, don't allow this to launch new processes. 17689 if (!mProcessesReady && (intent.getFlags()&Intent.FLAG_RECEIVER_BOOT_UPGRADE) == 0) { 17690 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 17691 } 17692 17693 if (DEBUG_BROADCAST_LIGHT) Slog.v(TAG_BROADCAST, 17694 (sticky ? "Broadcast sticky: ": "Broadcast: ") + intent 17695 + " ordered=" + ordered + " userid=" + userId); 17696 if ((resultTo != null) && !ordered) { 17697 Slog.w(TAG, "Broadcast " + intent + " not ordered but result callback requested!"); 17698 } 17699 17700 userId = mUserController.handleIncomingUser(callingPid, callingUid, userId, true, 17701 ALLOW_NON_FULL, "broadcast", callerPackage); 17702 17703 // Make sure that the user who is receiving this broadcast is running. 17704 // If not, we will just skip it. Make an exception for shutdown broadcasts 17705 // and upgrade steps. 17706 17707 if (userId != UserHandle.USER_ALL && !mUserController.isUserRunningLocked(userId, 0)) { 17708 if ((callingUid != Process.SYSTEM_UID 17709 || (intent.getFlags() & Intent.FLAG_RECEIVER_BOOT_UPGRADE) == 0) 17710 && !Intent.ACTION_SHUTDOWN.equals(intent.getAction())) { 17711 Slog.w(TAG, "Skipping broadcast of " + intent 17712 + ": user " + userId + " is stopped"); 17713 return ActivityManager.BROADCAST_FAILED_USER_STOPPED; 17714 } 17715 } 17716 17717 BroadcastOptions brOptions = null; 17718 if (bOptions != null) { 17719 brOptions = new BroadcastOptions(bOptions); 17720 if (brOptions.getTemporaryAppWhitelistDuration() > 0) { 17721 // See if the caller is allowed to do this. Note we are checking against 17722 // the actual real caller (not whoever provided the operation as say a 17723 // PendingIntent), because that who is actually supplied the arguments. 17724 if (checkComponentPermission( 17725 android.Manifest.permission.CHANGE_DEVICE_IDLE_TEMP_WHITELIST, 17726 Binder.getCallingPid(), Binder.getCallingUid(), -1, true) 17727 != PackageManager.PERMISSION_GRANTED) { 17728 String msg = "Permission Denial: " + intent.getAction() 17729 + " broadcast from " + callerPackage + " (pid=" + callingPid 17730 + ", uid=" + callingUid + ")" 17731 + " requires " 17732 + android.Manifest.permission.CHANGE_DEVICE_IDLE_TEMP_WHITELIST; 17733 Slog.w(TAG, msg); 17734 throw new SecurityException(msg); 17735 } 17736 } 17737 } 17738 17739 // Verify that protected broadcasts are only being sent by system code, 17740 // and that system code is only sending protected broadcasts. 17741 final String action = intent.getAction(); 17742 final boolean isProtectedBroadcast; 17743 try { 17744 isProtectedBroadcast = AppGlobals.getPackageManager().isProtectedBroadcast(action); 17745 } catch (RemoteException e) { 17746 Slog.w(TAG, "Remote exception", e); 17747 return ActivityManager.BROADCAST_SUCCESS; 17748 } 17749 17750 final boolean isCallerSystem; 17751 switch (UserHandle.getAppId(callingUid)) { 17752 case Process.ROOT_UID: 17753 case Process.SYSTEM_UID: 17754 case Process.PHONE_UID: 17755 case Process.BLUETOOTH_UID: 17756 case Process.NFC_UID: 17757 isCallerSystem = true; 17758 break; 17759 default: 17760 isCallerSystem = (callerApp != null) && callerApp.persistent; 17761 break; 17762 } 17763 17764 // First line security check before anything else: stop non-system apps from 17765 // sending protected broadcasts. 17766 if (!isCallerSystem) { 17767 if (isProtectedBroadcast) { 17768 String msg = "Permission Denial: not allowed to send broadcast " 17769 + action + " from pid=" 17770 + callingPid + ", uid=" + callingUid; 17771 Slog.w(TAG, msg); 17772 throw new SecurityException(msg); 17773 17774 } else if (AppWidgetManager.ACTION_APPWIDGET_CONFIGURE.equals(action) 17775 || AppWidgetManager.ACTION_APPWIDGET_UPDATE.equals(action)) { 17776 // Special case for compatibility: we don't want apps to send this, 17777 // but historically it has not been protected and apps may be using it 17778 // to poke their own app widget. So, instead of making it protected, 17779 // just limit it to the caller. 17780 if (callerPackage == null) { 17781 String msg = "Permission Denial: not allowed to send broadcast " 17782 + action + " from unknown caller."; 17783 Slog.w(TAG, msg); 17784 throw new SecurityException(msg); 17785 } else if (intent.getComponent() != null) { 17786 // They are good enough to send to an explicit component... verify 17787 // it is being sent to the calling app. 17788 if (!intent.getComponent().getPackageName().equals( 17789 callerPackage)) { 17790 String msg = "Permission Denial: not allowed to send broadcast " 17791 + action + " to " 17792 + intent.getComponent().getPackageName() + " from " 17793 + callerPackage; 17794 Slog.w(TAG, msg); 17795 throw new SecurityException(msg); 17796 } 17797 } else { 17798 // Limit broadcast to their own package. 17799 intent.setPackage(callerPackage); 17800 } 17801 } 17802 } 17803 17804 if (action != null) { 17805 switch (action) { 17806 case Intent.ACTION_UID_REMOVED: 17807 case Intent.ACTION_PACKAGE_REMOVED: 17808 case Intent.ACTION_PACKAGE_CHANGED: 17809 case Intent.ACTION_EXTERNAL_APPLICATIONS_UNAVAILABLE: 17810 case Intent.ACTION_EXTERNAL_APPLICATIONS_AVAILABLE: 17811 case Intent.ACTION_PACKAGES_SUSPENDED: 17812 case Intent.ACTION_PACKAGES_UNSUSPENDED: 17813 // Handle special intents: if this broadcast is from the package 17814 // manager about a package being removed, we need to remove all of 17815 // its activities from the history stack. 17816 if (checkComponentPermission( 17817 android.Manifest.permission.BROADCAST_PACKAGE_REMOVED, 17818 callingPid, callingUid, -1, true) 17819 != PackageManager.PERMISSION_GRANTED) { 17820 String msg = "Permission Denial: " + intent.getAction() 17821 + " broadcast from " + callerPackage + " (pid=" + callingPid 17822 + ", uid=" + callingUid + ")" 17823 + " requires " 17824 + android.Manifest.permission.BROADCAST_PACKAGE_REMOVED; 17825 Slog.w(TAG, msg); 17826 throw new SecurityException(msg); 17827 } 17828 switch (action) { 17829 case Intent.ACTION_UID_REMOVED: 17830 final Bundle intentExtras = intent.getExtras(); 17831 final int uid = intentExtras != null 17832 ? intentExtras.getInt(Intent.EXTRA_UID) : -1; 17833 if (uid >= 0) { 17834 mBatteryStatsService.removeUid(uid); 17835 mAppOpsService.uidRemoved(uid); 17836 } 17837 break; 17838 case Intent.ACTION_EXTERNAL_APPLICATIONS_UNAVAILABLE: 17839 // If resources are unavailable just force stop all those packages 17840 // and flush the attribute cache as well. 17841 String list[] = 17842 intent.getStringArrayExtra(Intent.EXTRA_CHANGED_PACKAGE_LIST); 17843 if (list != null && list.length > 0) { 17844 for (int i = 0; i < list.length; i++) { 17845 forceStopPackageLocked(list[i], -1, false, true, true, 17846 false, false, userId, "storage unmount"); 17847 } 17848 mRecentTasks.cleanupLocked(UserHandle.USER_ALL); 17849 sendPackageBroadcastLocked( 17850 ApplicationThreadConstants.EXTERNAL_STORAGE_UNAVAILABLE, 17851 list, userId); 17852 } 17853 break; 17854 case Intent.ACTION_EXTERNAL_APPLICATIONS_AVAILABLE: 17855 mRecentTasks.cleanupLocked(UserHandle.USER_ALL); 17856 break; 17857 case Intent.ACTION_PACKAGE_REMOVED: 17858 case Intent.ACTION_PACKAGE_CHANGED: 17859 Uri data = intent.getData(); 17860 String ssp; 17861 if (data != null && (ssp=data.getSchemeSpecificPart()) != null) { 17862 boolean removed = Intent.ACTION_PACKAGE_REMOVED.equals(action); 17863 final boolean replacing = 17864 intent.getBooleanExtra(Intent.EXTRA_REPLACING, false); 17865 final boolean killProcess = 17866 !intent.getBooleanExtra(Intent.EXTRA_DONT_KILL_APP, false); 17867 final boolean fullUninstall = removed && !replacing; 17868 if (removed) { 17869 if (killProcess) { 17870 forceStopPackageLocked(ssp, UserHandle.getAppId( 17871 intent.getIntExtra(Intent.EXTRA_UID, -1)), 17872 false, true, true, false, fullUninstall, userId, 17873 removed ? "pkg removed" : "pkg changed"); 17874 } 17875 final int cmd = killProcess 17876 ? ApplicationThreadConstants.PACKAGE_REMOVED 17877 : ApplicationThreadConstants.PACKAGE_REMOVED_DONT_KILL; 17878 sendPackageBroadcastLocked(cmd, 17879 new String[] {ssp}, userId); 17880 if (fullUninstall) { 17881 mAppOpsService.packageRemoved( 17882 intent.getIntExtra(Intent.EXTRA_UID, -1), ssp); 17883 17884 // Remove all permissions granted from/to this package 17885 removeUriPermissionsForPackageLocked(ssp, userId, true); 17886 17887 removeTasksByPackageNameLocked(ssp, userId); 17888 17889 // Hide the "unsupported display" dialog if necessary. 17890 if (mUnsupportedDisplaySizeDialog != null && ssp.equals( 17891 mUnsupportedDisplaySizeDialog.getPackageName())) { 17892 mUnsupportedDisplaySizeDialog.dismiss(); 17893 mUnsupportedDisplaySizeDialog = null; 17894 } 17895 mCompatModePackages.handlePackageUninstalledLocked(ssp); 17896 mBatteryStatsService.notePackageUninstalled(ssp); 17897 } 17898 } else { 17899 if (killProcess) { 17900 killPackageProcessesLocked(ssp, UserHandle.getAppId( 17901 intent.getIntExtra(Intent.EXTRA_UID, -1)), 17902 userId, ProcessList.INVALID_ADJ, 17903 false, true, true, false, "change " + ssp); 17904 } 17905 cleanupDisabledPackageComponentsLocked(ssp, userId, killProcess, 17906 intent.getStringArrayExtra( 17907 Intent.EXTRA_CHANGED_COMPONENT_NAME_LIST)); 17908 } 17909 } 17910 break; 17911 case Intent.ACTION_PACKAGES_SUSPENDED: 17912 case Intent.ACTION_PACKAGES_UNSUSPENDED: 17913 final boolean suspended = Intent.ACTION_PACKAGES_SUSPENDED.equals( 17914 intent.getAction()); 17915 final String[] packageNames = intent.getStringArrayExtra( 17916 Intent.EXTRA_CHANGED_PACKAGE_LIST); 17917 final int userHandle = intent.getIntExtra( 17918 Intent.EXTRA_USER_HANDLE, UserHandle.USER_NULL); 17919 17920 synchronized(ActivityManagerService.this) { 17921 mRecentTasks.onPackagesSuspendedChanged( 17922 packageNames, suspended, userHandle); 17923 } 17924 break; 17925 } 17926 break; 17927 case Intent.ACTION_PACKAGE_REPLACED: 17928 { 17929 final Uri data = intent.getData(); 17930 final String ssp; 17931 if (data != null && (ssp = data.getSchemeSpecificPart()) != null) { 17932 final ApplicationInfo aInfo = 17933 getPackageManagerInternalLocked().getApplicationInfo( 17934 ssp, 17935 userId); 17936 if (aInfo == null) { 17937 Slog.w(TAG, "Dropping ACTION_PACKAGE_REPLACED for non-existent pkg:" 17938 + " ssp=" + ssp + " data=" + data); 17939 return ActivityManager.BROADCAST_SUCCESS; 17940 } 17941 mStackSupervisor.updateActivityApplicationInfoLocked(aInfo); 17942 sendPackageBroadcastLocked(ApplicationThreadConstants.PACKAGE_REPLACED, 17943 new String[] {ssp}, userId); 17944 } 17945 break; 17946 } 17947 case Intent.ACTION_PACKAGE_ADDED: 17948 { 17949 // Special case for adding a package: by default turn on compatibility mode. 17950 Uri data = intent.getData(); 17951 String ssp; 17952 if (data != null && (ssp = data.getSchemeSpecificPart()) != null) { 17953 final boolean replacing = 17954 intent.getBooleanExtra(Intent.EXTRA_REPLACING, false); 17955 mCompatModePackages.handlePackageAddedLocked(ssp, replacing); 17956 17957 try { 17958 ApplicationInfo ai = AppGlobals.getPackageManager(). 17959 getApplicationInfo(ssp, 0, 0); 17960 mBatteryStatsService.notePackageInstalled(ssp, 17961 ai != null ? ai.versionCode : 0); 17962 } catch (RemoteException e) { 17963 } 17964 } 17965 break; 17966 } 17967 case Intent.ACTION_PACKAGE_DATA_CLEARED: 17968 { 17969 Uri data = intent.getData(); 17970 String ssp; 17971 if (data != null && (ssp = data.getSchemeSpecificPart()) != null) { 17972 // Hide the "unsupported display" dialog if necessary. 17973 if (mUnsupportedDisplaySizeDialog != null && ssp.equals( 17974 mUnsupportedDisplaySizeDialog.getPackageName())) { 17975 mUnsupportedDisplaySizeDialog.dismiss(); 17976 mUnsupportedDisplaySizeDialog = null; 17977 } 17978 mCompatModePackages.handlePackageDataClearedLocked(ssp); 17979 } 17980 break; 17981 } 17982 case Intent.ACTION_TIMEZONE_CHANGED: 17983 // If this is the time zone changed action, queue up a message that will reset 17984 // the timezone of all currently running processes. This message will get 17985 // queued up before the broadcast happens. 17986 mHandler.sendEmptyMessage(UPDATE_TIME_ZONE); 17987 break; 17988 case Intent.ACTION_TIME_CHANGED: 17989 // If the user set the time, let all running processes know. 17990 final int is24Hour = 17991 intent.getBooleanExtra(Intent.EXTRA_TIME_PREF_24_HOUR_FORMAT, false) ? 1 17992 : 0; 17993 mHandler.sendMessage(mHandler.obtainMessage(UPDATE_TIME, is24Hour, 0)); 17994 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 17995 synchronized (stats) { 17996 stats.noteCurrentTimeChangedLocked(); 17997 } 17998 break; 17999 case Intent.ACTION_CLEAR_DNS_CACHE: 18000 mHandler.sendEmptyMessage(CLEAR_DNS_CACHE_MSG); 18001 break; 18002 case Proxy.PROXY_CHANGE_ACTION: 18003 ProxyInfo proxy = intent.getParcelableExtra(Proxy.EXTRA_PROXY_INFO); 18004 mHandler.sendMessage(mHandler.obtainMessage(UPDATE_HTTP_PROXY_MSG, proxy)); 18005 break; 18006 case android.hardware.Camera.ACTION_NEW_PICTURE: 18007 case android.hardware.Camera.ACTION_NEW_VIDEO: 18008 // These broadcasts are no longer allowed by the system, since they can 18009 // cause significant thrashing at a crictical point (using the camera). 18010 // Apps should use JobScehduler to monitor for media provider changes. 18011 Slog.w(TAG, action + " no longer allowed; dropping from " 18012 + UserHandle.formatUid(callingUid)); 18013 if (resultTo != null) { 18014 final BroadcastQueue queue = broadcastQueueForIntent(intent); 18015 try { 18016 queue.performReceiveLocked(callerApp, resultTo, intent, 18017 Activity.RESULT_CANCELED, null, null, 18018 false, false, userId); 18019 } catch (RemoteException e) { 18020 Slog.w(TAG, "Failure [" 18021 + queue.mQueueName + "] sending broadcast result of " 18022 + intent, e); 18023 18024 } 18025 } 18026 // Lie; we don't want to crash the app. 18027 return ActivityManager.BROADCAST_SUCCESS; 18028 case android.security.KeyChain.ACTION_TRUST_STORE_CHANGED: 18029 mHandler.sendEmptyMessage(HANDLE_TRUST_STORAGE_UPDATE_MSG); 18030 break; 18031 } 18032 } 18033 18034 // Add to the sticky list if requested. 18035 if (sticky) { 18036 if (checkPermission(android.Manifest.permission.BROADCAST_STICKY, 18037 callingPid, callingUid) 18038 != PackageManager.PERMISSION_GRANTED) { 18039 String msg = "Permission Denial: broadcastIntent() requesting a sticky broadcast from pid=" 18040 + callingPid + ", uid=" + callingUid 18041 + " requires " + android.Manifest.permission.BROADCAST_STICKY; 18042 Slog.w(TAG, msg); 18043 throw new SecurityException(msg); 18044 } 18045 if (requiredPermissions != null && requiredPermissions.length > 0) { 18046 Slog.w(TAG, "Can't broadcast sticky intent " + intent 18047 + " and enforce permissions " + Arrays.toString(requiredPermissions)); 18048 return ActivityManager.BROADCAST_STICKY_CANT_HAVE_PERMISSION; 18049 } 18050 if (intent.getComponent() != null) { 18051 throw new SecurityException( 18052 "Sticky broadcasts can't target a specific component"); 18053 } 18054 // We use userId directly here, since the "all" target is maintained 18055 // as a separate set of sticky broadcasts. 18056 if (userId != UserHandle.USER_ALL) { 18057 // But first, if this is not a broadcast to all users, then 18058 // make sure it doesn't conflict with an existing broadcast to 18059 // all users. 18060 ArrayMap<String, ArrayList<Intent>> stickies = mStickyBroadcasts.get( 18061 UserHandle.USER_ALL); 18062 if (stickies != null) { 18063 ArrayList<Intent> list = stickies.get(intent.getAction()); 18064 if (list != null) { 18065 int N = list.size(); 18066 int i; 18067 for (i=0; i<N; i++) { 18068 if (intent.filterEquals(list.get(i))) { 18069 throw new IllegalArgumentException( 18070 "Sticky broadcast " + intent + " for user " 18071 + userId + " conflicts with existing global broadcast"); 18072 } 18073 } 18074 } 18075 } 18076 } 18077 ArrayMap<String, ArrayList<Intent>> stickies = mStickyBroadcasts.get(userId); 18078 if (stickies == null) { 18079 stickies = new ArrayMap<>(); 18080 mStickyBroadcasts.put(userId, stickies); 18081 } 18082 ArrayList<Intent> list = stickies.get(intent.getAction()); 18083 if (list == null) { 18084 list = new ArrayList<>(); 18085 stickies.put(intent.getAction(), list); 18086 } 18087 final int stickiesCount = list.size(); 18088 int i; 18089 for (i = 0; i < stickiesCount; i++) { 18090 if (intent.filterEquals(list.get(i))) { 18091 // This sticky already exists, replace it. 18092 list.set(i, new Intent(intent)); 18093 break; 18094 } 18095 } 18096 if (i >= stickiesCount) { 18097 list.add(new Intent(intent)); 18098 } 18099 } 18100 18101 int[] users; 18102 if (userId == UserHandle.USER_ALL) { 18103 // Caller wants broadcast to go to all started users. 18104 users = mUserController.getStartedUserArrayLocked(); 18105 } else { 18106 // Caller wants broadcast to go to one specific user. 18107 users = new int[] {userId}; 18108 } 18109 18110 // Figure out who all will receive this broadcast. 18111 List receivers = null; 18112 List<BroadcastFilter> registeredReceivers = null; 18113 // Need to resolve the intent to interested receivers... 18114 if ((intent.getFlags()&Intent.FLAG_RECEIVER_REGISTERED_ONLY) 18115 == 0) { 18116 receivers = collectReceiverComponents(intent, resolvedType, callingUid, users); 18117 } 18118 if (intent.getComponent() == null) { 18119 if (userId == UserHandle.USER_ALL && callingUid == Process.SHELL_UID) { 18120 // Query one target user at a time, excluding shell-restricted users 18121 for (int i = 0; i < users.length; i++) { 18122 if (mUserController.hasUserRestriction( 18123 UserManager.DISALLOW_DEBUGGING_FEATURES, users[i])) { 18124 continue; 18125 } 18126 List<BroadcastFilter> registeredReceiversForUser = 18127 mReceiverResolver.queryIntent(intent, 18128 resolvedType, false, users[i]); 18129 if (registeredReceivers == null) { 18130 registeredReceivers = registeredReceiversForUser; 18131 } else if (registeredReceiversForUser != null) { 18132 registeredReceivers.addAll(registeredReceiversForUser); 18133 } 18134 } 18135 } else { 18136 registeredReceivers = mReceiverResolver.queryIntent(intent, 18137 resolvedType, false, userId); 18138 } 18139 } 18140 18141 final boolean replacePending = 18142 (intent.getFlags()&Intent.FLAG_RECEIVER_REPLACE_PENDING) != 0; 18143 18144 if (DEBUG_BROADCAST) Slog.v(TAG_BROADCAST, "Enqueing broadcast: " + intent.getAction() 18145 + " replacePending=" + replacePending); 18146 18147 int NR = registeredReceivers != null ? registeredReceivers.size() : 0; 18148 if (!ordered && NR > 0) { 18149 // If we are not serializing this broadcast, then send the 18150 // registered receivers separately so they don't wait for the 18151 // components to be launched. 18152 if (isCallerSystem) { 18153 checkBroadcastFromSystem(intent, callerApp, callerPackage, callingUid, 18154 isProtectedBroadcast, registeredReceivers); 18155 } 18156 final BroadcastQueue queue = broadcastQueueForIntent(intent); 18157 BroadcastRecord r = new BroadcastRecord(queue, intent, callerApp, 18158 callerPackage, callingPid, callingUid, resolvedType, requiredPermissions, 18159 appOp, brOptions, registeredReceivers, resultTo, resultCode, resultData, 18160 resultExtras, ordered, sticky, false, userId); 18161 if (DEBUG_BROADCAST) Slog.v(TAG_BROADCAST, "Enqueueing parallel broadcast " + r); 18162 final boolean replaced = replacePending && queue.replaceParallelBroadcastLocked(r); 18163 if (!replaced) { 18164 queue.enqueueParallelBroadcastLocked(r); 18165 queue.scheduleBroadcastsLocked(); 18166 } 18167 registeredReceivers = null; 18168 NR = 0; 18169 } 18170 18171 // Merge into one list. 18172 int ir = 0; 18173 if (receivers != null) { 18174 // A special case for PACKAGE_ADDED: do not allow the package 18175 // being added to see this broadcast. This prevents them from 18176 // using this as a back door to get run as soon as they are 18177 // installed. Maybe in the future we want to have a special install 18178 // broadcast or such for apps, but we'd like to deliberately make 18179 // this decision. 18180 String skipPackages[] = null; 18181 if (Intent.ACTION_PACKAGE_ADDED.equals(intent.getAction()) 18182 || Intent.ACTION_PACKAGE_RESTARTED.equals(intent.getAction()) 18183 || Intent.ACTION_PACKAGE_DATA_CLEARED.equals(intent.getAction())) { 18184 Uri data = intent.getData(); 18185 if (data != null) { 18186 String pkgName = data.getSchemeSpecificPart(); 18187 if (pkgName != null) { 18188 skipPackages = new String[] { pkgName }; 18189 } 18190 } 18191 } else if (Intent.ACTION_EXTERNAL_APPLICATIONS_AVAILABLE.equals(intent.getAction())) { 18192 skipPackages = intent.getStringArrayExtra(Intent.EXTRA_CHANGED_PACKAGE_LIST); 18193 } 18194 if (skipPackages != null && (skipPackages.length > 0)) { 18195 for (String skipPackage : skipPackages) { 18196 if (skipPackage != null) { 18197 int NT = receivers.size(); 18198 for (int it=0; it<NT; it++) { 18199 ResolveInfo curt = (ResolveInfo)receivers.get(it); 18200 if (curt.activityInfo.packageName.equals(skipPackage)) { 18201 receivers.remove(it); 18202 it--; 18203 NT--; 18204 } 18205 } 18206 } 18207 } 18208 } 18209 18210 int NT = receivers != null ? receivers.size() : 0; 18211 int it = 0; 18212 ResolveInfo curt = null; 18213 BroadcastFilter curr = null; 18214 while (it < NT && ir < NR) { 18215 if (curt == null) { 18216 curt = (ResolveInfo)receivers.get(it); 18217 } 18218 if (curr == null) { 18219 curr = registeredReceivers.get(ir); 18220 } 18221 if (curr.getPriority() >= curt.priority) { 18222 // Insert this broadcast record into the final list. 18223 receivers.add(it, curr); 18224 ir++; 18225 curr = null; 18226 it++; 18227 NT++; 18228 } else { 18229 // Skip to the next ResolveInfo in the final list. 18230 it++; 18231 curt = null; 18232 } 18233 } 18234 } 18235 while (ir < NR) { 18236 if (receivers == null) { 18237 receivers = new ArrayList(); 18238 } 18239 receivers.add(registeredReceivers.get(ir)); 18240 ir++; 18241 } 18242 18243 if (isCallerSystem) { 18244 checkBroadcastFromSystem(intent, callerApp, callerPackage, callingUid, 18245 isProtectedBroadcast, receivers); 18246 } 18247 18248 if ((receivers != null && receivers.size() > 0) 18249 || resultTo != null) { 18250 BroadcastQueue queue = broadcastQueueForIntent(intent); 18251 BroadcastRecord r = new BroadcastRecord(queue, intent, callerApp, 18252 callerPackage, callingPid, callingUid, resolvedType, 18253 requiredPermissions, appOp, brOptions, receivers, resultTo, resultCode, 18254 resultData, resultExtras, ordered, sticky, false, userId); 18255 18256 if (DEBUG_BROADCAST) Slog.v(TAG_BROADCAST, "Enqueueing ordered broadcast " + r 18257 + ": prev had " + queue.mOrderedBroadcasts.size()); 18258 if (DEBUG_BROADCAST) Slog.i(TAG_BROADCAST, 18259 "Enqueueing broadcast " + r.intent.getAction()); 18260 18261 boolean replaced = replacePending && queue.replaceOrderedBroadcastLocked(r); 18262 if (!replaced) { 18263 queue.enqueueOrderedBroadcastLocked(r); 18264 queue.scheduleBroadcastsLocked(); 18265 } 18266 } else { 18267 // There was nobody interested in the broadcast, but we still want to record 18268 // that it happened. 18269 if (intent.getComponent() == null && intent.getPackage() == null 18270 && (intent.getFlags()&Intent.FLAG_RECEIVER_REGISTERED_ONLY) == 0) { 18271 // This was an implicit broadcast... let's record it for posterity. 18272 addBroadcastStatLocked(intent.getAction(), callerPackage, 0, 0, 0); 18273 } 18274 } 18275 18276 return ActivityManager.BROADCAST_SUCCESS; 18277 } 18278 18279 final void addBroadcastStatLocked(String action, String srcPackage, int receiveCount, 18280 int skipCount, long dispatchTime) { 18281 final long now = SystemClock.elapsedRealtime(); 18282 if (mCurBroadcastStats == null || 18283 (mCurBroadcastStats.mStartRealtime +(24*60*60*1000) < now)) { 18284 mLastBroadcastStats = mCurBroadcastStats; 18285 if (mLastBroadcastStats != null) { 18286 mLastBroadcastStats.mEndRealtime = SystemClock.elapsedRealtime(); 18287 mLastBroadcastStats.mEndUptime = SystemClock.uptimeMillis(); 18288 } 18289 mCurBroadcastStats = new BroadcastStats(); 18290 } 18291 mCurBroadcastStats.addBroadcast(action, srcPackage, receiveCount, skipCount, dispatchTime); 18292 } 18293 18294 final Intent verifyBroadcastLocked(Intent intent) { 18295 // Refuse possible leaked file descriptors 18296 if (intent != null && intent.hasFileDescriptors() == true) { 18297 throw new IllegalArgumentException("File descriptors passed in Intent"); 18298 } 18299 18300 int flags = intent.getFlags(); 18301 18302 if (!mProcessesReady) { 18303 // if the caller really truly claims to know what they're doing, go 18304 // ahead and allow the broadcast without launching any receivers 18305 if ((flags&Intent.FLAG_RECEIVER_REGISTERED_ONLY_BEFORE_BOOT) != 0) { 18306 // This will be turned into a FLAG_RECEIVER_REGISTERED_ONLY later on if needed. 18307 } else if ((flags&Intent.FLAG_RECEIVER_REGISTERED_ONLY) == 0) { 18308 Slog.e(TAG, "Attempt to launch receivers of broadcast intent " + intent 18309 + " before boot completion"); 18310 throw new IllegalStateException("Cannot broadcast before boot completed"); 18311 } 18312 } 18313 18314 if ((flags&Intent.FLAG_RECEIVER_BOOT_UPGRADE) != 0) { 18315 throw new IllegalArgumentException( 18316 "Can't use FLAG_RECEIVER_BOOT_UPGRADE here"); 18317 } 18318 18319 return intent; 18320 } 18321 18322 public final int broadcastIntent(IApplicationThread caller, 18323 Intent intent, String resolvedType, IIntentReceiver resultTo, 18324 int resultCode, String resultData, Bundle resultExtras, 18325 String[] requiredPermissions, int appOp, Bundle bOptions, 18326 boolean serialized, boolean sticky, int userId) { 18327 enforceNotIsolatedCaller("broadcastIntent"); 18328 synchronized(this) { 18329 intent = verifyBroadcastLocked(intent); 18330 18331 final ProcessRecord callerApp = getRecordForAppLocked(caller); 18332 final int callingPid = Binder.getCallingPid(); 18333 final int callingUid = Binder.getCallingUid(); 18334 final long origId = Binder.clearCallingIdentity(); 18335 int res = broadcastIntentLocked(callerApp, 18336 callerApp != null ? callerApp.info.packageName : null, 18337 intent, resolvedType, resultTo, resultCode, resultData, resultExtras, 18338 requiredPermissions, appOp, bOptions, serialized, sticky, 18339 callingPid, callingUid, userId); 18340 Binder.restoreCallingIdentity(origId); 18341 return res; 18342 } 18343 } 18344 18345 18346 int broadcastIntentInPackage(String packageName, int uid, 18347 Intent intent, String resolvedType, IIntentReceiver resultTo, 18348 int resultCode, String resultData, Bundle resultExtras, 18349 String requiredPermission, Bundle bOptions, boolean serialized, boolean sticky, 18350 int userId) { 18351 synchronized(this) { 18352 intent = verifyBroadcastLocked(intent); 18353 18354 final long origId = Binder.clearCallingIdentity(); 18355 String[] requiredPermissions = requiredPermission == null ? null 18356 : new String[] {requiredPermission}; 18357 int res = broadcastIntentLocked(null, packageName, intent, resolvedType, 18358 resultTo, resultCode, resultData, resultExtras, 18359 requiredPermissions, AppOpsManager.OP_NONE, bOptions, serialized, 18360 sticky, -1, uid, userId); 18361 Binder.restoreCallingIdentity(origId); 18362 return res; 18363 } 18364 } 18365 18366 public final void unbroadcastIntent(IApplicationThread caller, Intent intent, int userId) { 18367 // Refuse possible leaked file descriptors 18368 if (intent != null && intent.hasFileDescriptors() == true) { 18369 throw new IllegalArgumentException("File descriptors passed in Intent"); 18370 } 18371 18372 userId = mUserController.handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 18373 userId, true, ALLOW_NON_FULL, "removeStickyBroadcast", null); 18374 18375 synchronized(this) { 18376 if (checkCallingPermission(android.Manifest.permission.BROADCAST_STICKY) 18377 != PackageManager.PERMISSION_GRANTED) { 18378 String msg = "Permission Denial: unbroadcastIntent() from pid=" 18379 + Binder.getCallingPid() 18380 + ", uid=" + Binder.getCallingUid() 18381 + " requires " + android.Manifest.permission.BROADCAST_STICKY; 18382 Slog.w(TAG, msg); 18383 throw new SecurityException(msg); 18384 } 18385 ArrayMap<String, ArrayList<Intent>> stickies = mStickyBroadcasts.get(userId); 18386 if (stickies != null) { 18387 ArrayList<Intent> list = stickies.get(intent.getAction()); 18388 if (list != null) { 18389 int N = list.size(); 18390 int i; 18391 for (i=0; i<N; i++) { 18392 if (intent.filterEquals(list.get(i))) { 18393 list.remove(i); 18394 break; 18395 } 18396 } 18397 if (list.size() <= 0) { 18398 stickies.remove(intent.getAction()); 18399 } 18400 } 18401 if (stickies.size() <= 0) { 18402 mStickyBroadcasts.remove(userId); 18403 } 18404 } 18405 } 18406 } 18407 18408 void backgroundServicesFinishedLocked(int userId) { 18409 for (BroadcastQueue queue : mBroadcastQueues) { 18410 queue.backgroundServicesFinishedLocked(userId); 18411 } 18412 } 18413 18414 public void finishReceiver(IBinder who, int resultCode, String resultData, 18415 Bundle resultExtras, boolean resultAbort, int flags) { 18416 if (DEBUG_BROADCAST) Slog.v(TAG_BROADCAST, "Finish receiver: " + who); 18417 18418 // Refuse possible leaked file descriptors 18419 if (resultExtras != null && resultExtras.hasFileDescriptors()) { 18420 throw new IllegalArgumentException("File descriptors passed in Bundle"); 18421 } 18422 18423 final long origId = Binder.clearCallingIdentity(); 18424 try { 18425 boolean doNext = false; 18426 BroadcastRecord r; 18427 18428 synchronized(this) { 18429 BroadcastQueue queue = (flags & Intent.FLAG_RECEIVER_FOREGROUND) != 0 18430 ? mFgBroadcastQueue : mBgBroadcastQueue; 18431 r = queue.getMatchingOrderedReceiver(who); 18432 if (r != null) { 18433 doNext = r.queue.finishReceiverLocked(r, resultCode, 18434 resultData, resultExtras, resultAbort, true); 18435 } 18436 } 18437 18438 if (doNext) { 18439 r.queue.processNextBroadcast(false); 18440 } 18441 trimApplications(); 18442 } finally { 18443 Binder.restoreCallingIdentity(origId); 18444 } 18445 } 18446 18447 // ========================================================= 18448 // INSTRUMENTATION 18449 // ========================================================= 18450 18451 public boolean startInstrumentation(ComponentName className, 18452 String profileFile, int flags, Bundle arguments, 18453 IInstrumentationWatcher watcher, IUiAutomationConnection uiAutomationConnection, 18454 int userId, String abiOverride) { 18455 enforceNotIsolatedCaller("startInstrumentation"); 18456 userId = mUserController.handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 18457 userId, false, ALLOW_FULL_ONLY, "startInstrumentation", null); 18458 // Refuse possible leaked file descriptors 18459 if (arguments != null && arguments.hasFileDescriptors()) { 18460 throw new IllegalArgumentException("File descriptors passed in Bundle"); 18461 } 18462 18463 synchronized(this) { 18464 InstrumentationInfo ii = null; 18465 ApplicationInfo ai = null; 18466 try { 18467 ii = mContext.getPackageManager().getInstrumentationInfo( 18468 className, STOCK_PM_FLAGS); 18469 ai = AppGlobals.getPackageManager().getApplicationInfo( 18470 ii.targetPackage, STOCK_PM_FLAGS, userId); 18471 } catch (PackageManager.NameNotFoundException e) { 18472 } catch (RemoteException e) { 18473 } 18474 if (ii == null) { 18475 reportStartInstrumentationFailureLocked(watcher, className, 18476 "Unable to find instrumentation info for: " + className); 18477 return false; 18478 } 18479 if (ai == null) { 18480 reportStartInstrumentationFailureLocked(watcher, className, 18481 "Unable to find instrumentation target package: " + ii.targetPackage); 18482 return false; 18483 } 18484 if (!ai.hasCode()) { 18485 reportStartInstrumentationFailureLocked(watcher, className, 18486 "Instrumentation target has no code: " + ii.targetPackage); 18487 return false; 18488 } 18489 18490 int match = mContext.getPackageManager().checkSignatures( 18491 ii.targetPackage, ii.packageName); 18492 if (match < 0 && match != PackageManager.SIGNATURE_FIRST_NOT_SIGNED) { 18493 String msg = "Permission Denial: starting instrumentation " 18494 + className + " from pid=" 18495 + Binder.getCallingPid() 18496 + ", uid=" + Binder.getCallingPid() 18497 + " not allowed because package " + ii.packageName 18498 + " does not have a signature matching the target " 18499 + ii.targetPackage; 18500 reportStartInstrumentationFailureLocked(watcher, className, msg); 18501 throw new SecurityException(msg); 18502 } 18503 18504 final long origId = Binder.clearCallingIdentity(); 18505 // Instrumentation can kill and relaunch even persistent processes 18506 forceStopPackageLocked(ii.targetPackage, -1, true, false, true, true, false, userId, 18507 "start instr"); 18508 ProcessRecord app = addAppLocked(ai, false, abiOverride); 18509 app.instrumentationClass = className; 18510 app.instrumentationInfo = ai; 18511 app.instrumentationProfileFile = profileFile; 18512 app.instrumentationArguments = arguments; 18513 app.instrumentationWatcher = watcher; 18514 app.instrumentationUiAutomationConnection = uiAutomationConnection; 18515 app.instrumentationResultClass = className; 18516 Binder.restoreCallingIdentity(origId); 18517 } 18518 18519 return true; 18520 } 18521 18522 /** 18523 * Report errors that occur while attempting to start Instrumentation. Always writes the 18524 * error to the logs, but if somebody is watching, send the report there too. This enables 18525 * the "am" command to report errors with more information. 18526 * 18527 * @param watcher The IInstrumentationWatcher. Null if there isn't one. 18528 * @param cn The component name of the instrumentation. 18529 * @param report The error report. 18530 */ 18531 private void reportStartInstrumentationFailureLocked(IInstrumentationWatcher watcher, 18532 ComponentName cn, String report) { 18533 Slog.w(TAG, report); 18534 if (watcher != null) { 18535 Bundle results = new Bundle(); 18536 results.putString(Instrumentation.REPORT_KEY_IDENTIFIER, "ActivityManagerService"); 18537 results.putString("Error", report); 18538 mInstrumentationReporter.reportStatus(watcher, cn, -1, results); 18539 } 18540 } 18541 18542 void finishInstrumentationLocked(ProcessRecord app, int resultCode, Bundle results) { 18543 if (app.instrumentationWatcher != null) { 18544 mInstrumentationReporter.reportFinished(app.instrumentationWatcher, 18545 app.instrumentationClass, resultCode, results); 18546 } 18547 18548 // Can't call out of the system process with a lock held, so post a message. 18549 if (app.instrumentationUiAutomationConnection != null) { 18550 mHandler.obtainMessage(SHUTDOWN_UI_AUTOMATION_CONNECTION_MSG, 18551 app.instrumentationUiAutomationConnection).sendToTarget(); 18552 } 18553 18554 app.instrumentationWatcher = null; 18555 app.instrumentationUiAutomationConnection = null; 18556 app.instrumentationClass = null; 18557 app.instrumentationInfo = null; 18558 app.instrumentationProfileFile = null; 18559 app.instrumentationArguments = null; 18560 18561 forceStopPackageLocked(app.info.packageName, -1, false, false, true, true, false, app.userId, 18562 "finished inst"); 18563 } 18564 18565 public void finishInstrumentation(IApplicationThread target, 18566 int resultCode, Bundle results) { 18567 int userId = UserHandle.getCallingUserId(); 18568 // Refuse possible leaked file descriptors 18569 if (results != null && results.hasFileDescriptors()) { 18570 throw new IllegalArgumentException("File descriptors passed in Intent"); 18571 } 18572 18573 synchronized(this) { 18574 ProcessRecord app = getRecordForAppLocked(target); 18575 if (app == null) { 18576 Slog.w(TAG, "finishInstrumentation: no app for " + target); 18577 return; 18578 } 18579 final long origId = Binder.clearCallingIdentity(); 18580 finishInstrumentationLocked(app, resultCode, results); 18581 Binder.restoreCallingIdentity(origId); 18582 } 18583 } 18584 18585 // ========================================================= 18586 // CONFIGURATION 18587 // ========================================================= 18588 18589 public ConfigurationInfo getDeviceConfigurationInfo() { 18590 ConfigurationInfo config = new ConfigurationInfo(); 18591 synchronized (this) { 18592 final Configuration globalConfig = getGlobalConfiguration(); 18593 config.reqTouchScreen = globalConfig.touchscreen; 18594 config.reqKeyboardType = globalConfig.keyboard; 18595 config.reqNavigation = globalConfig.navigation; 18596 if (globalConfig.navigation == Configuration.NAVIGATION_DPAD 18597 || globalConfig.navigation == Configuration.NAVIGATION_TRACKBALL) { 18598 config.reqInputFeatures |= ConfigurationInfo.INPUT_FEATURE_FIVE_WAY_NAV; 18599 } 18600 if (globalConfig.keyboard != Configuration.KEYBOARD_UNDEFINED 18601 && globalConfig.keyboard != Configuration.KEYBOARD_NOKEYS) { 18602 config.reqInputFeatures |= ConfigurationInfo.INPUT_FEATURE_HARD_KEYBOARD; 18603 } 18604 config.reqGlEsVersion = GL_ES_VERSION; 18605 } 18606 return config; 18607 } 18608 18609 ActivityStack getFocusedStack() { 18610 return mStackSupervisor.getFocusedStack(); 18611 } 18612 18613 @Override 18614 public int getFocusedStackId() throws RemoteException { 18615 ActivityStack focusedStack = getFocusedStack(); 18616 if (focusedStack != null) { 18617 return focusedStack.getStackId(); 18618 } 18619 return -1; 18620 } 18621 18622 public Configuration getConfiguration() { 18623 Configuration ci; 18624 synchronized(this) { 18625 ci = new Configuration(getGlobalConfiguration()); 18626 ci.userSetLocale = false; 18627 } 18628 return ci; 18629 } 18630 18631 @Override 18632 public void suppressResizeConfigChanges(boolean suppress) throws RemoteException { 18633 enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "suppressResizeConfigChanges()"); 18634 synchronized (this) { 18635 mSuppressResizeConfigChanges = suppress; 18636 } 18637 } 18638 18639 @Override 18640 public void moveTasksToFullscreenStack(int fromStackId, boolean onTop) { 18641 enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "moveTasksToFullscreenStack()"); 18642 if (fromStackId == HOME_STACK_ID) { 18643 throw new IllegalArgumentException("You can't move tasks from the home stack."); 18644 } 18645 synchronized (this) { 18646 final long origId = Binder.clearCallingIdentity(); 18647 try { 18648 mStackSupervisor.moveTasksToFullscreenStackLocked(fromStackId, onTop); 18649 } finally { 18650 Binder.restoreCallingIdentity(origId); 18651 } 18652 } 18653 } 18654 18655 @Override 18656 public void updatePersistentConfiguration(Configuration values) { 18657 enforceCallingPermission(CHANGE_CONFIGURATION, "updatePersistentConfiguration()"); 18658 enforceWriteSettingsPermission("updatePersistentConfiguration()"); 18659 if (values == null) { 18660 throw new NullPointerException("Configuration must not be null"); 18661 } 18662 18663 int userId = UserHandle.getCallingUserId(); 18664 18665 synchronized(this) { 18666 updatePersistentConfigurationLocked(values, userId); 18667 } 18668 } 18669 18670 private void updatePersistentConfigurationLocked(Configuration values, @UserIdInt int userId) { 18671 final long origId = Binder.clearCallingIdentity(); 18672 try { 18673 updateConfigurationLocked(values, null, false, true, userId, false /* deferResume */); 18674 } finally { 18675 Binder.restoreCallingIdentity(origId); 18676 } 18677 } 18678 18679 private void updateFontScaleIfNeeded(@UserIdInt int userId) { 18680 final float scaleFactor = Settings.System.getFloatForUser(mContext.getContentResolver(), 18681 FONT_SCALE, 1.0f, userId); 18682 18683 synchronized (this) { 18684 if (getGlobalConfiguration().fontScale == scaleFactor) { 18685 return; 18686 } 18687 18688 final Configuration configuration 18689 = mWindowManager.computeNewConfiguration(DEFAULT_DISPLAY); 18690 configuration.fontScale = scaleFactor; 18691 updatePersistentConfigurationLocked(configuration, userId); 18692 } 18693 } 18694 18695 private void enforceWriteSettingsPermission(String func) { 18696 int uid = Binder.getCallingUid(); 18697 if (uid == Process.ROOT_UID) { 18698 return; 18699 } 18700 18701 if (Settings.checkAndNoteWriteSettingsOperation(mContext, uid, 18702 Settings.getPackageNameForUid(mContext, uid), false)) { 18703 return; 18704 } 18705 18706 String msg = "Permission Denial: " + func + " from pid=" 18707 + Binder.getCallingPid() 18708 + ", uid=" + uid 18709 + " requires " + android.Manifest.permission.WRITE_SETTINGS; 18710 Slog.w(TAG, msg); 18711 throw new SecurityException(msg); 18712 } 18713 18714 @Override 18715 public boolean updateConfiguration(Configuration values) { 18716 enforceCallingPermission(CHANGE_CONFIGURATION, "updateConfiguration()"); 18717 18718 synchronized(this) { 18719 if (values == null && mWindowManager != null) { 18720 // sentinel: fetch the current configuration from the window manager 18721 values = mWindowManager.computeNewConfiguration(DEFAULT_DISPLAY); 18722 } 18723 18724 if (mWindowManager != null) { 18725 // Update OOM levels based on display size. 18726 mProcessList.applyDisplaySize(mWindowManager); 18727 } 18728 18729 final long origId = Binder.clearCallingIdentity(); 18730 try { 18731 if (values != null) { 18732 Settings.System.clearConfiguration(values); 18733 } 18734 updateConfigurationLocked(values, null, false, false /* persistent */, 18735 UserHandle.USER_NULL, false /* deferResume */, 18736 mTmpUpdateConfigurationResult); 18737 return mTmpUpdateConfigurationResult.changes != 0; 18738 } finally { 18739 Binder.restoreCallingIdentity(origId); 18740 } 18741 } 18742 } 18743 18744 void updateUserConfigurationLocked() { 18745 final Configuration configuration = new Configuration(getGlobalConfiguration()); 18746 final int currentUserId = mUserController.getCurrentUserIdLocked(); 18747 Settings.System.adjustConfigurationForUser(mContext.getContentResolver(), configuration, 18748 currentUserId, Settings.System.canWrite(mContext)); 18749 updateConfigurationLocked(configuration, null /* starting */, false /* initLocale */, 18750 false /* persistent */, currentUserId, false /* deferResume */); 18751 } 18752 18753 boolean updateConfigurationLocked(Configuration values, ActivityRecord starting, 18754 boolean initLocale) { 18755 return updateConfigurationLocked(values, starting, initLocale, false /* deferResume */); 18756 } 18757 18758 boolean updateConfigurationLocked(Configuration values, ActivityRecord starting, 18759 boolean initLocale, boolean deferResume) { 18760 // pass UserHandle.USER_NULL as userId because we don't persist configuration for any user 18761 return updateConfigurationLocked(values, starting, initLocale, false /* persistent */, 18762 UserHandle.USER_NULL, deferResume); 18763 } 18764 18765 // To cache the list of supported system locales 18766 private String[] mSupportedSystemLocales = null; 18767 18768 private boolean updateConfigurationLocked(Configuration values, ActivityRecord starting, 18769 boolean initLocale, boolean persistent, int userId, boolean deferResume) { 18770 return updateConfigurationLocked(values, starting, initLocale, persistent, userId, 18771 deferResume, null /* result */); 18772 } 18773 18774 /** 18775 * Do either or both things: (1) change the current configuration, and (2) 18776 * make sure the given activity is running with the (now) current 18777 * configuration. Returns true if the activity has been left running, or 18778 * false if <var>starting</var> is being destroyed to match the new 18779 * configuration. 18780 * 18781 * @param userId is only used when persistent parameter is set to true to persist configuration 18782 * for that particular user 18783 */ 18784 private boolean updateConfigurationLocked(Configuration values, ActivityRecord starting, 18785 boolean initLocale, boolean persistent, int userId, boolean deferResume, 18786 UpdateConfigurationResult result) { 18787 int changes = 0; 18788 boolean kept = true; 18789 18790 if (mWindowManager != null) { 18791 mWindowManager.deferSurfaceLayout(); 18792 } 18793 try { 18794 if (values != null) { 18795 changes = updateGlobalConfiguration(values, initLocale, persistent, userId, 18796 deferResume); 18797 } 18798 18799 kept = ensureConfigAndVisibilityAfterUpdate(starting, changes); 18800 } finally { 18801 if (mWindowManager != null) { 18802 mWindowManager.continueSurfaceLayout(); 18803 } 18804 } 18805 18806 if (result != null) { 18807 result.changes = changes; 18808 result.activityRelaunched = !kept; 18809 } 18810 return kept; 18811 } 18812 18813 /** Update default (global) configuration and notify listeners about changes. */ 18814 private int updateGlobalConfiguration(@NonNull Configuration values, boolean initLocale, 18815 boolean persistent, int userId, boolean deferResume) { 18816 mTempConfig.setTo(getGlobalConfiguration()); 18817 final int changes = mTempConfig.updateFrom(values); 18818 if (changes == 0) { 18819 return 0; 18820 } 18821 18822 if (DEBUG_SWITCH || DEBUG_CONFIGURATION) Slog.i(TAG_CONFIGURATION, 18823 "Updating global configuration to: " + values); 18824 18825 EventLog.writeEvent(EventLogTags.CONFIGURATION_CHANGED, changes); 18826 18827 if (!initLocale && !values.getLocales().isEmpty() && values.userSetLocale) { 18828 final LocaleList locales = values.getLocales(); 18829 int bestLocaleIndex = 0; 18830 if (locales.size() > 1) { 18831 if (mSupportedSystemLocales == null) { 18832 mSupportedSystemLocales = Resources.getSystem().getAssets().getLocales(); 18833 } 18834 bestLocaleIndex = Math.max(0, locales.getFirstMatchIndex(mSupportedSystemLocales)); 18835 } 18836 SystemProperties.set("persist.sys.locale", 18837 locales.get(bestLocaleIndex).toLanguageTag()); 18838 LocaleList.setDefault(locales, bestLocaleIndex); 18839 mHandler.sendMessage(mHandler.obtainMessage(SEND_LOCALE_TO_MOUNT_DAEMON_MSG, 18840 locales.get(bestLocaleIndex))); 18841 } 18842 18843 mConfigurationSeq = Math.max(++mConfigurationSeq, 1); 18844 mTempConfig.seq = mConfigurationSeq; 18845 18846 // Update stored global config and notify everyone about the change. 18847 mStackSupervisor.onConfigurationChanged(mTempConfig); 18848 18849 Slog.i(TAG, "Config changes=" + Integer.toHexString(changes) + " " + mTempConfig); 18850 // TODO(multi-display): Update UsageEvents#Event to include displayId. 18851 mUsageStatsService.reportConfigurationChange(mTempConfig, 18852 mUserController.getCurrentUserIdLocked()); 18853 18854 // TODO: If our config changes, should we auto dismiss any currently showing dialogs? 18855 mShowDialogs = shouldShowDialogs(mTempConfig, mInVrMode); 18856 18857 AttributeCache ac = AttributeCache.instance(); 18858 if (ac != null) { 18859 ac.updateConfiguration(mTempConfig); 18860 } 18861 18862 // Make sure all resources in our process are updated right now, so that anyone who is going 18863 // to retrieve resource values after we return will be sure to get the new ones. This is 18864 // especially important during boot, where the first config change needs to guarantee all 18865 // resources have that config before following boot code is executed. 18866 mSystemThread.applyConfigurationToResources(mTempConfig); 18867 18868 // We need another copy of global config because we're scheduling some calls instead of 18869 // running them in place. We need to be sure that object we send will be handled unchanged. 18870 final Configuration configCopy = new Configuration(mTempConfig); 18871 if (persistent && Settings.System.hasInterestingConfigurationChanges(changes)) { 18872 Message msg = mHandler.obtainMessage(UPDATE_CONFIGURATION_MSG); 18873 msg.obj = configCopy; 18874 msg.arg1 = userId; 18875 mHandler.sendMessage(msg); 18876 } 18877 18878 for (int i = mLruProcesses.size() - 1; i >= 0; i--) { 18879 ProcessRecord app = mLruProcesses.get(i); 18880 try { 18881 if (app.thread != null) { 18882 if (DEBUG_CONFIGURATION) Slog.v(TAG_CONFIGURATION, "Sending to proc " 18883 + app.processName + " new config " + configCopy); 18884 app.thread.scheduleConfigurationChanged(configCopy); 18885 } 18886 } catch (Exception e) { 18887 } 18888 } 18889 18890 Intent intent = new Intent(Intent.ACTION_CONFIGURATION_CHANGED); 18891 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY | Intent.FLAG_RECEIVER_REPLACE_PENDING 18892 | Intent.FLAG_RECEIVER_FOREGROUND); 18893 broadcastIntentLocked(null, null, intent, null, null, 0, null, null, null, 18894 AppOpsManager.OP_NONE, null, false, false, MY_PID, Process.SYSTEM_UID, 18895 UserHandle.USER_ALL); 18896 if ((changes & ActivityInfo.CONFIG_LOCALE) != 0) { 18897 intent = new Intent(Intent.ACTION_LOCALE_CHANGED); 18898 intent.addFlags(Intent.FLAG_RECEIVER_FOREGROUND); 18899 if (initLocale || !mProcessesReady) { 18900 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 18901 } 18902 broadcastIntentLocked(null, null, intent, null, null, 0, null, null, null, 18903 AppOpsManager.OP_NONE, null, false, false, MY_PID, Process.SYSTEM_UID, 18904 UserHandle.USER_ALL); 18905 } 18906 18907 // Override configuration of the default display duplicates global config, so we need to 18908 // update it also. This will also notify WindowManager about changes. 18909 performDisplayOverrideConfigUpdate(mStackSupervisor.getConfiguration(), deferResume, 18910 DEFAULT_DISPLAY); 18911 18912 return changes; 18913 } 18914 18915 @Override 18916 public boolean updateDisplayOverrideConfiguration(Configuration values, int displayId) { 18917 enforceCallingPermission(CHANGE_CONFIGURATION, "updateDisplayOverrideConfiguration()"); 18918 18919 synchronized (this) { 18920 if (values == null && mWindowManager != null) { 18921 // sentinel: fetch the current configuration from the window manager 18922 values = mWindowManager.computeNewConfiguration(displayId); 18923 } 18924 18925 if (mWindowManager != null) { 18926 // Update OOM levels based on display size. 18927 mProcessList.applyDisplaySize(mWindowManager); 18928 } 18929 18930 final long origId = Binder.clearCallingIdentity(); 18931 try { 18932 if (values != null) { 18933 Settings.System.clearConfiguration(values); 18934 } 18935 updateDisplayOverrideConfigurationLocked(values, null /* starting */, 18936 false /* deferResume */, displayId, mTmpUpdateConfigurationResult); 18937 return mTmpUpdateConfigurationResult.changes != 0; 18938 } finally { 18939 Binder.restoreCallingIdentity(origId); 18940 } 18941 } 18942 } 18943 18944 boolean updateDisplayOverrideConfigurationLocked(Configuration values, ActivityRecord starting, 18945 boolean deferResume, int displayId) { 18946 return updateDisplayOverrideConfigurationLocked(values, starting, deferResume /* deferResume */, 18947 displayId, null /* result */); 18948 } 18949 18950 /** 18951 * Updates override configuration specific for the selected display. If no config is provided, 18952 * new one will be computed in WM based on current display info. 18953 */ 18954 private boolean updateDisplayOverrideConfigurationLocked(Configuration values, 18955 ActivityRecord starting, boolean deferResume, int displayId, 18956 UpdateConfigurationResult result) { 18957 int changes = 0; 18958 boolean kept = true; 18959 18960 if (mWindowManager != null) { 18961 mWindowManager.deferSurfaceLayout(); 18962 } 18963 try { 18964 if (values != null) { 18965 if (displayId == DEFAULT_DISPLAY) { 18966 // Override configuration of the default display duplicates global config, so 18967 // we're calling global config update instead for default display. It will also 18968 // apply the correct override config. 18969 changes = updateGlobalConfiguration(values, false /* initLocale */, 18970 false /* persistent */, UserHandle.USER_NULL /* userId */, deferResume); 18971 } else { 18972 changes = performDisplayOverrideConfigUpdate(values, deferResume, displayId); 18973 } 18974 } 18975 18976 kept = ensureConfigAndVisibilityAfterUpdate(starting, changes); 18977 } finally { 18978 if (mWindowManager != null) { 18979 mWindowManager.continueSurfaceLayout(); 18980 } 18981 } 18982 18983 if (result != null) { 18984 result.changes = changes; 18985 result.activityRelaunched = !kept; 18986 } 18987 return kept; 18988 } 18989 18990 private int performDisplayOverrideConfigUpdate(Configuration values, boolean deferResume, 18991 int displayId) { 18992 mTempConfig.setTo(mStackSupervisor.getDisplayOverrideConfiguration(displayId)); 18993 final int changes = mTempConfig.updateFrom(values); 18994 if (changes == 0) { 18995 return 0; 18996 } 18997 18998 Slog.i(TAG, "Override config changes=" + Integer.toHexString(changes) + " " + mTempConfig 18999 + " for displayId=" + displayId); 19000 mStackSupervisor.setDisplayOverrideConfiguration(mTempConfig, displayId); 19001 19002 final boolean isDensityChange = (changes & ActivityInfo.CONFIG_DENSITY) != 0; 19003 if (isDensityChange) { 19004 // Reset the unsupported display size dialog. 19005 mUiHandler.sendEmptyMessage(SHOW_UNSUPPORTED_DISPLAY_SIZE_DIALOG_MSG); 19006 19007 killAllBackgroundProcessesExcept(N, ActivityManager.PROCESS_STATE_FOREGROUND_SERVICE); 19008 } 19009 19010 // Update the configuration with WM first and check if any of the stacks need to be resized 19011 // due to the configuration change. If so, resize the stacks now and do any relaunches if 19012 // necessary. This way we don't need to relaunch again afterwards in 19013 // ensureActivityConfigurationLocked(). 19014 if (mWindowManager != null) { 19015 final int[] resizedStacks = 19016 mWindowManager.setNewDisplayOverrideConfiguration(mTempConfig, displayId); 19017 if (resizedStacks != null) { 19018 for (int stackId : resizedStacks) { 19019 resizeStackWithBoundsFromWindowManager(stackId, deferResume); 19020 } 19021 } 19022 } 19023 19024 return changes; 19025 } 19026 19027 /** Applies latest configuration and/or visibility updates if needed. */ 19028 private boolean ensureConfigAndVisibilityAfterUpdate(ActivityRecord starting, int changes) { 19029 boolean kept = true; 19030 final ActivityStack mainStack = mStackSupervisor.getFocusedStack(); 19031 // mainStack is null during startup. 19032 if (mainStack != null) { 19033 if (changes != 0 && starting == null) { 19034 // If the configuration changed, and the caller is not already 19035 // in the process of starting an activity, then find the top 19036 // activity to check if its configuration needs to change. 19037 starting = mainStack.topRunningActivityLocked(); 19038 } 19039 19040 if (starting != null) { 19041 kept = starting.ensureActivityConfigurationLocked(changes, 19042 false /* preserveWindow */); 19043 // And we need to make sure at this point that all other activities 19044 // are made visible with the correct configuration. 19045 mStackSupervisor.ensureActivitiesVisibleLocked(starting, changes, 19046 !PRESERVE_WINDOWS); 19047 } 19048 } 19049 19050 return kept; 19051 } 19052 19053 /** Helper method that requests bounds from WM and applies them to stack. */ 19054 private void resizeStackWithBoundsFromWindowManager(int stackId, boolean deferResume) { 19055 final Rect newBounds = mWindowManager.getBoundsForNewConfiguration(stackId); 19056 mStackSupervisor.resizeStackLocked( 19057 stackId, newBounds, null /* tempTaskBounds */, null /* tempTaskInsetBounds */, 19058 false /* preserveWindows */, false /* allowResizeInDockedMode */, deferResume); 19059 } 19060 19061 /** 19062 * Decide based on the configuration whether we should show the ANR, 19063 * crash, etc dialogs. The idea is that if there is no affordance to 19064 * press the on-screen buttons, or the user experience would be more 19065 * greatly impacted than the crash itself, we shouldn't show the dialog. 19066 * 19067 * A thought: SystemUI might also want to get told about this, the Power 19068 * dialog / global actions also might want different behaviors. 19069 */ 19070 private static boolean shouldShowDialogs(Configuration config, boolean inVrMode) { 19071 final boolean inputMethodExists = !(config.keyboard == Configuration.KEYBOARD_NOKEYS 19072 && config.touchscreen == Configuration.TOUCHSCREEN_NOTOUCH 19073 && config.navigation == Configuration.NAVIGATION_NONAV); 19074 int modeType = config.uiMode & Configuration.UI_MODE_TYPE_MASK; 19075 final boolean uiModeSupportsDialogs = (modeType != Configuration.UI_MODE_TYPE_CAR 19076 && !(modeType == Configuration.UI_MODE_TYPE_WATCH && "user".equals(Build.TYPE))); 19077 return inputMethodExists && uiModeSupportsDialogs && !inVrMode; 19078 } 19079 19080 @Override 19081 public boolean shouldUpRecreateTask(IBinder token, String destAffinity) { 19082 synchronized (this) { 19083 ActivityRecord srec = ActivityRecord.forTokenLocked(token); 19084 if (srec != null) { 19085 return srec.getStack().shouldUpRecreateTaskLocked(srec, destAffinity); 19086 } 19087 } 19088 return false; 19089 } 19090 19091 public boolean navigateUpTo(IBinder token, Intent destIntent, int resultCode, 19092 Intent resultData) { 19093 19094 synchronized (this) { 19095 final ActivityRecord r = ActivityRecord.forTokenLocked(token); 19096 if (r != null) { 19097 return r.getStack().navigateUpToLocked(r, destIntent, resultCode, resultData); 19098 } 19099 return false; 19100 } 19101 } 19102 19103 public int getLaunchedFromUid(IBinder activityToken) { 19104 ActivityRecord srec; 19105 synchronized (this) { 19106 srec = ActivityRecord.forTokenLocked(activityToken); 19107 } 19108 if (srec == null) { 19109 return -1; 19110 } 19111 return srec.launchedFromUid; 19112 } 19113 19114 public String getLaunchedFromPackage(IBinder activityToken) { 19115 ActivityRecord srec; 19116 synchronized (this) { 19117 srec = ActivityRecord.forTokenLocked(activityToken); 19118 } 19119 if (srec == null) { 19120 return null; 19121 } 19122 return srec.launchedFromPackage; 19123 } 19124 19125 // ========================================================= 19126 // LIFETIME MANAGEMENT 19127 // ========================================================= 19128 19129 // Returns whether the app is receiving broadcast. 19130 // If receiving, fetch all broadcast queues which the app is 19131 // the current [or imminent] receiver on. 19132 private boolean isReceivingBroadcastLocked(ProcessRecord app, 19133 ArraySet<BroadcastQueue> receivingQueues) { 19134 if (!app.curReceivers.isEmpty()) { 19135 for (BroadcastRecord r : app.curReceivers) { 19136 receivingQueues.add(r.queue); 19137 } 19138 return true; 19139 } 19140 19141 // It's not the current receiver, but it might be starting up to become one 19142 for (BroadcastQueue queue : mBroadcastQueues) { 19143 final BroadcastRecord r = queue.mPendingBroadcast; 19144 if (r != null && r.curApp == app) { 19145 // found it; report which queue it's in 19146 receivingQueues.add(queue); 19147 } 19148 } 19149 19150 return !receivingQueues.isEmpty(); 19151 } 19152 19153 Association startAssociationLocked(int sourceUid, String sourceProcess, int sourceState, 19154 int targetUid, ComponentName targetComponent, String targetProcess) { 19155 if (!mTrackingAssociations) { 19156 return null; 19157 } 19158 ArrayMap<ComponentName, SparseArray<ArrayMap<String, Association>>> components 19159 = mAssociations.get(targetUid); 19160 if (components == null) { 19161 components = new ArrayMap<>(); 19162 mAssociations.put(targetUid, components); 19163 } 19164 SparseArray<ArrayMap<String, Association>> sourceUids = components.get(targetComponent); 19165 if (sourceUids == null) { 19166 sourceUids = new SparseArray<>(); 19167 components.put(targetComponent, sourceUids); 19168 } 19169 ArrayMap<String, Association> sourceProcesses = sourceUids.get(sourceUid); 19170 if (sourceProcesses == null) { 19171 sourceProcesses = new ArrayMap<>(); 19172 sourceUids.put(sourceUid, sourceProcesses); 19173 } 19174 Association ass = sourceProcesses.get(sourceProcess); 19175 if (ass == null) { 19176 ass = new Association(sourceUid, sourceProcess, targetUid, targetComponent, 19177 targetProcess); 19178 sourceProcesses.put(sourceProcess, ass); 19179 } 19180 ass.mCount++; 19181 ass.mNesting++; 19182 if (ass.mNesting == 1) { 19183 ass.mStartTime = ass.mLastStateUptime = SystemClock.uptimeMillis(); 19184 ass.mLastState = sourceState; 19185 } 19186 return ass; 19187 } 19188 19189 void stopAssociationLocked(int sourceUid, String sourceProcess, int targetUid, 19190 ComponentName targetComponent) { 19191 if (!mTrackingAssociations) { 19192 return; 19193 } 19194 ArrayMap<ComponentName, SparseArray<ArrayMap<String, Association>>> components 19195 = mAssociations.get(targetUid); 19196 if (components == null) { 19197 return; 19198 } 19199 SparseArray<ArrayMap<String, Association>> sourceUids = components.get(targetComponent); 19200 if (sourceUids == null) { 19201 return; 19202 } 19203 ArrayMap<String, Association> sourceProcesses = sourceUids.get(sourceUid); 19204 if (sourceProcesses == null) { 19205 return; 19206 } 19207 Association ass = sourceProcesses.get(sourceProcess); 19208 if (ass == null || ass.mNesting <= 0) { 19209 return; 19210 } 19211 ass.mNesting--; 19212 if (ass.mNesting == 0) { 19213 long uptime = SystemClock.uptimeMillis(); 19214 ass.mTime += uptime - ass.mStartTime; 19215 ass.mStateTimes[ass.mLastState-ActivityManager.MIN_PROCESS_STATE] 19216 += uptime - ass.mLastStateUptime; 19217 ass.mLastState = ActivityManager.MAX_PROCESS_STATE + 2; 19218 } 19219 } 19220 19221 private void noteUidProcessState(final int uid, final int state) { 19222 mBatteryStatsService.noteUidProcessState(uid, state); 19223 if (mTrackingAssociations) { 19224 for (int i1=0, N1=mAssociations.size(); i1<N1; i1++) { 19225 ArrayMap<ComponentName, SparseArray<ArrayMap<String, Association>>> targetComponents 19226 = mAssociations.valueAt(i1); 19227 for (int i2=0, N2=targetComponents.size(); i2<N2; i2++) { 19228 SparseArray<ArrayMap<String, Association>> sourceUids 19229 = targetComponents.valueAt(i2); 19230 ArrayMap<String, Association> sourceProcesses = sourceUids.get(uid); 19231 if (sourceProcesses != null) { 19232 for (int i4=0, N4=sourceProcesses.size(); i4<N4; i4++) { 19233 Association ass = sourceProcesses.valueAt(i4); 19234 if (ass.mNesting >= 1) { 19235 // currently associated 19236 long uptime = SystemClock.uptimeMillis(); 19237 ass.mStateTimes[ass.mLastState-ActivityManager.MIN_PROCESS_STATE] 19238 += uptime - ass.mLastStateUptime; 19239 ass.mLastState = state; 19240 ass.mLastStateUptime = uptime; 19241 } 19242 } 19243 } 19244 } 19245 } 19246 } 19247 } 19248 19249 private final int computeOomAdjLocked(ProcessRecord app, int cachedAdj, ProcessRecord TOP_APP, 19250 boolean doingAll, long now) { 19251 if (mAdjSeq == app.adjSeq) { 19252 // This adjustment has already been computed. 19253 return app.curRawAdj; 19254 } 19255 19256 if (app.thread == null) { 19257 app.adjSeq = mAdjSeq; 19258 app.curSchedGroup = ProcessList.SCHED_GROUP_BACKGROUND; 19259 app.curProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 19260 return (app.curAdj=app.curRawAdj=ProcessList.CACHED_APP_MAX_ADJ); 19261 } 19262 19263 app.adjTypeCode = ActivityManager.RunningAppProcessInfo.REASON_UNKNOWN; 19264 app.adjSource = null; 19265 app.adjTarget = null; 19266 app.empty = false; 19267 app.cached = false; 19268 19269 final int activitiesSize = app.activities.size(); 19270 19271 if (app.maxAdj <= ProcessList.FOREGROUND_APP_ADJ) { 19272 // The max adjustment doesn't allow this app to be anything 19273 // below foreground, so it is not worth doing work for it. 19274 app.adjType = "fixed"; 19275 app.adjSeq = mAdjSeq; 19276 app.curRawAdj = app.maxAdj; 19277 app.foregroundActivities = false; 19278 app.curSchedGroup = ProcessList.SCHED_GROUP_DEFAULT; 19279 app.curProcState = ActivityManager.PROCESS_STATE_PERSISTENT; 19280 // System processes can do UI, and when they do we want to have 19281 // them trim their memory after the user leaves the UI. To 19282 // facilitate this, here we need to determine whether or not it 19283 // is currently showing UI. 19284 app.systemNoUi = true; 19285 if (app == TOP_APP) { 19286 app.systemNoUi = false; 19287 app.curSchedGroup = ProcessList.SCHED_GROUP_TOP_APP; 19288 app.adjType = "pers-top-activity"; 19289 } else if (app.hasTopUi) { 19290 app.systemNoUi = false; 19291 app.curSchedGroup = ProcessList.SCHED_GROUP_TOP_APP; 19292 app.adjType = "pers-top-ui"; 19293 } else if (activitiesSize > 0) { 19294 for (int j = 0; j < activitiesSize; j++) { 19295 final ActivityRecord r = app.activities.get(j); 19296 if (r.visible) { 19297 app.systemNoUi = false; 19298 } 19299 } 19300 } 19301 if (!app.systemNoUi) { 19302 app.curProcState = ActivityManager.PROCESS_STATE_PERSISTENT_UI; 19303 } 19304 return (app.curAdj=app.maxAdj); 19305 } 19306 19307 app.systemNoUi = false; 19308 19309 final int PROCESS_STATE_CUR_TOP = mTopProcessState; 19310 19311 // Determine the importance of the process, starting with most 19312 // important to least, and assign an appropriate OOM adjustment. 19313 int adj; 19314 int schedGroup; 19315 int procState; 19316 boolean foregroundActivities = false; 19317 final ArraySet<BroadcastQueue> queues = new ArraySet<BroadcastQueue>(); 19318 if (app == TOP_APP) { 19319 // The last app on the list is the foreground app. 19320 adj = ProcessList.FOREGROUND_APP_ADJ; 19321 schedGroup = ProcessList.SCHED_GROUP_TOP_APP; 19322 app.adjType = "top-activity"; 19323 foregroundActivities = true; 19324 procState = PROCESS_STATE_CUR_TOP; 19325 } else if (app.instrumentationClass != null) { 19326 // Don't want to kill running instrumentation. 19327 adj = ProcessList.FOREGROUND_APP_ADJ; 19328 schedGroup = ProcessList.SCHED_GROUP_DEFAULT; 19329 app.adjType = "instrumentation"; 19330 procState = ActivityManager.PROCESS_STATE_FOREGROUND_SERVICE; 19331 } else if (isReceivingBroadcastLocked(app, queues)) { 19332 // An app that is currently receiving a broadcast also 19333 // counts as being in the foreground for OOM killer purposes. 19334 // It's placed in a sched group based on the nature of the 19335 // broadcast as reflected by which queue it's active in. 19336 adj = ProcessList.FOREGROUND_APP_ADJ; 19337 schedGroup = (queues.contains(mFgBroadcastQueue)) 19338 ? ProcessList.SCHED_GROUP_DEFAULT : ProcessList.SCHED_GROUP_BACKGROUND; 19339 app.adjType = "broadcast"; 19340 procState = ActivityManager.PROCESS_STATE_RECEIVER; 19341 } else if (app.executingServices.size() > 0) { 19342 // An app that is currently executing a service callback also 19343 // counts as being in the foreground. 19344 adj = ProcessList.FOREGROUND_APP_ADJ; 19345 schedGroup = app.execServicesFg ? 19346 ProcessList.SCHED_GROUP_DEFAULT : ProcessList.SCHED_GROUP_BACKGROUND; 19347 app.adjType = "exec-service"; 19348 procState = ActivityManager.PROCESS_STATE_SERVICE; 19349 //Slog.i(TAG, "EXEC " + (app.execServicesFg ? "FG" : "BG") + ": " + app); 19350 } else { 19351 // As far as we know the process is empty. We may change our mind later. 19352 schedGroup = ProcessList.SCHED_GROUP_BACKGROUND; 19353 // At this point we don't actually know the adjustment. Use the cached adj 19354 // value that the caller wants us to. 19355 adj = cachedAdj; 19356 procState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 19357 app.cached = true; 19358 app.empty = true; 19359 app.adjType = "cch-empty"; 19360 } 19361 19362 // Examine all activities if not already foreground. 19363 if (!foregroundActivities && activitiesSize > 0) { 19364 int minLayer = ProcessList.VISIBLE_APP_LAYER_MAX; 19365 for (int j = 0; j < activitiesSize; j++) { 19366 final ActivityRecord r = app.activities.get(j); 19367 if (r.app != app) { 19368 Log.e(TAG, "Found activity " + r + " in proc activity list using " + r.app 19369 + " instead of expected " + app); 19370 if (r.app == null || (r.app.uid == app.uid)) { 19371 // Only fix things up when they look sane 19372 r.app = app; 19373 } else { 19374 continue; 19375 } 19376 } 19377 if (r.visible) { 19378 // App has a visible activity; only upgrade adjustment. 19379 if (adj > ProcessList.VISIBLE_APP_ADJ) { 19380 adj = ProcessList.VISIBLE_APP_ADJ; 19381 app.adjType = "visible"; 19382 } 19383 if (procState > PROCESS_STATE_CUR_TOP) { 19384 procState = PROCESS_STATE_CUR_TOP; 19385 } 19386 schedGroup = ProcessList.SCHED_GROUP_DEFAULT; 19387 app.cached = false; 19388 app.empty = false; 19389 foregroundActivities = true; 19390 if (r.task != null && minLayer > 0) { 19391 final int layer = r.task.mLayerRank; 19392 if (layer >= 0 && minLayer > layer) { 19393 minLayer = layer; 19394 } 19395 } 19396 break; 19397 } else if (r.state == ActivityState.PAUSING || r.state == ActivityState.PAUSED) { 19398 if (adj > ProcessList.PERCEPTIBLE_APP_ADJ) { 19399 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 19400 app.adjType = "pausing"; 19401 } 19402 if (procState > PROCESS_STATE_CUR_TOP) { 19403 procState = PROCESS_STATE_CUR_TOP; 19404 } 19405 schedGroup = ProcessList.SCHED_GROUP_DEFAULT; 19406 app.cached = false; 19407 app.empty = false; 19408 foregroundActivities = true; 19409 } else if (r.state == ActivityState.STOPPING) { 19410 if (adj > ProcessList.PERCEPTIBLE_APP_ADJ) { 19411 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 19412 app.adjType = "stopping"; 19413 } 19414 // For the process state, we will at this point consider the 19415 // process to be cached. It will be cached either as an activity 19416 // or empty depending on whether the activity is finishing. We do 19417 // this so that we can treat the process as cached for purposes of 19418 // memory trimming (determing current memory level, trim command to 19419 // send to process) since there can be an arbitrary number of stopping 19420 // processes and they should soon all go into the cached state. 19421 if (!r.finishing) { 19422 if (procState > ActivityManager.PROCESS_STATE_LAST_ACTIVITY) { 19423 procState = ActivityManager.PROCESS_STATE_LAST_ACTIVITY; 19424 } 19425 } 19426 app.cached = false; 19427 app.empty = false; 19428 foregroundActivities = true; 19429 } else { 19430 if (procState > ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 19431 procState = ActivityManager.PROCESS_STATE_CACHED_ACTIVITY; 19432 app.adjType = "cch-act"; 19433 } 19434 } 19435 } 19436 if (adj == ProcessList.VISIBLE_APP_ADJ) { 19437 adj += minLayer; 19438 } 19439 } 19440 19441 if (adj > ProcessList.PERCEPTIBLE_APP_ADJ 19442 || procState > ActivityManager.PROCESS_STATE_FOREGROUND_SERVICE) { 19443 if (app.foregroundServices) { 19444 // The user is aware of this app, so make it visible. 19445 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 19446 procState = ActivityManager.PROCESS_STATE_FOREGROUND_SERVICE; 19447 app.cached = false; 19448 app.adjType = "fg-service"; 19449 schedGroup = ProcessList.SCHED_GROUP_DEFAULT; 19450 } else if (app.forcingToForeground != null) { 19451 // The user is aware of this app, so make it visible. 19452 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 19453 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 19454 app.cached = false; 19455 app.adjType = "force-fg"; 19456 app.adjSource = app.forcingToForeground; 19457 schedGroup = ProcessList.SCHED_GROUP_DEFAULT; 19458 } 19459 } 19460 19461 if (app == mHeavyWeightProcess) { 19462 if (adj > ProcessList.HEAVY_WEIGHT_APP_ADJ) { 19463 // We don't want to kill the current heavy-weight process. 19464 adj = ProcessList.HEAVY_WEIGHT_APP_ADJ; 19465 schedGroup = ProcessList.SCHED_GROUP_BACKGROUND; 19466 app.cached = false; 19467 app.adjType = "heavy"; 19468 } 19469 if (procState > ActivityManager.PROCESS_STATE_HEAVY_WEIGHT) { 19470 procState = ActivityManager.PROCESS_STATE_HEAVY_WEIGHT; 19471 } 19472 } 19473 19474 if (app == mHomeProcess) { 19475 if (adj > ProcessList.HOME_APP_ADJ) { 19476 // This process is hosting what we currently consider to be the 19477 // home app, so we don't want to let it go into the background. 19478 adj = ProcessList.HOME_APP_ADJ; 19479 schedGroup = ProcessList.SCHED_GROUP_BACKGROUND; 19480 app.cached = false; 19481 app.adjType = "home"; 19482 } 19483 if (procState > ActivityManager.PROCESS_STATE_HOME) { 19484 procState = ActivityManager.PROCESS_STATE_HOME; 19485 } 19486 } 19487 19488 if (app == mPreviousProcess && app.activities.size() > 0) { 19489 if (adj > ProcessList.PREVIOUS_APP_ADJ) { 19490 // This was the previous process that showed UI to the user. 19491 // We want to try to keep it around more aggressively, to give 19492 // a good experience around switching between two apps. 19493 adj = ProcessList.PREVIOUS_APP_ADJ; 19494 schedGroup = ProcessList.SCHED_GROUP_BACKGROUND; 19495 app.cached = false; 19496 app.adjType = "previous"; 19497 } 19498 if (procState > ActivityManager.PROCESS_STATE_LAST_ACTIVITY) { 19499 procState = ActivityManager.PROCESS_STATE_LAST_ACTIVITY; 19500 } 19501 } 19502 19503 if (false) Slog.i(TAG, "OOM " + app + ": initial adj=" + adj 19504 + " reason=" + app.adjType); 19505 19506 // By default, we use the computed adjustment. It may be changed if 19507 // there are applications dependent on our services or providers, but 19508 // this gives us a baseline and makes sure we don't get into an 19509 // infinite recursion. 19510 app.adjSeq = mAdjSeq; 19511 app.curRawAdj = adj; 19512 app.hasStartedServices = false; 19513 19514 if (mBackupTarget != null && app == mBackupTarget.app) { 19515 // If possible we want to avoid killing apps while they're being backed up 19516 if (adj > ProcessList.BACKUP_APP_ADJ) { 19517 if (DEBUG_BACKUP) Slog.v(TAG_BACKUP, "oom BACKUP_APP_ADJ for " + app); 19518 adj = ProcessList.BACKUP_APP_ADJ; 19519 if (procState > ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND) { 19520 procState = ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND; 19521 } 19522 app.adjType = "backup"; 19523 app.cached = false; 19524 } 19525 if (procState > ActivityManager.PROCESS_STATE_BACKUP) { 19526 procState = ActivityManager.PROCESS_STATE_BACKUP; 19527 } 19528 } 19529 19530 boolean mayBeTop = false; 19531 19532 for (int is = app.services.size()-1; 19533 is >= 0 && (adj > ProcessList.FOREGROUND_APP_ADJ 19534 || schedGroup == ProcessList.SCHED_GROUP_BACKGROUND 19535 || procState > ActivityManager.PROCESS_STATE_TOP); 19536 is--) { 19537 ServiceRecord s = app.services.valueAt(is); 19538 if (s.startRequested) { 19539 app.hasStartedServices = true; 19540 if (procState > ActivityManager.PROCESS_STATE_SERVICE) { 19541 procState = ActivityManager.PROCESS_STATE_SERVICE; 19542 } 19543 if (app.hasShownUi && app != mHomeProcess) { 19544 // If this process has shown some UI, let it immediately 19545 // go to the LRU list because it may be pretty heavy with 19546 // UI stuff. We'll tag it with a label just to help 19547 // debug and understand what is going on. 19548 if (adj > ProcessList.SERVICE_ADJ) { 19549 app.adjType = "cch-started-ui-services"; 19550 } 19551 } else { 19552 if (now < (s.lastActivity + ActiveServices.MAX_SERVICE_INACTIVITY)) { 19553 // This service has seen some activity within 19554 // recent memory, so we will keep its process ahead 19555 // of the background processes. 19556 if (adj > ProcessList.SERVICE_ADJ) { 19557 adj = ProcessList.SERVICE_ADJ; 19558 app.adjType = "started-services"; 19559 app.cached = false; 19560 } 19561 } 19562 // If we have let the service slide into the background 19563 // state, still have some text describing what it is doing 19564 // even though the service no longer has an impact. 19565 if (adj > ProcessList.SERVICE_ADJ) { 19566 app.adjType = "cch-started-services"; 19567 } 19568 } 19569 } 19570 19571 for (int conni = s.connections.size()-1; 19572 conni >= 0 && (adj > ProcessList.FOREGROUND_APP_ADJ 19573 || schedGroup == ProcessList.SCHED_GROUP_BACKGROUND 19574 || procState > ActivityManager.PROCESS_STATE_TOP); 19575 conni--) { 19576 ArrayList<ConnectionRecord> clist = s.connections.valueAt(conni); 19577 for (int i = 0; 19578 i < clist.size() && (adj > ProcessList.FOREGROUND_APP_ADJ 19579 || schedGroup == ProcessList.SCHED_GROUP_BACKGROUND 19580 || procState > ActivityManager.PROCESS_STATE_TOP); 19581 i++) { 19582 // XXX should compute this based on the max of 19583 // all connected clients. 19584 ConnectionRecord cr = clist.get(i); 19585 if (cr.binding.client == app) { 19586 // Binding to ourself is not interesting. 19587 continue; 19588 } 19589 19590 if ((cr.flags&Context.BIND_WAIVE_PRIORITY) == 0) { 19591 ProcessRecord client = cr.binding.client; 19592 int clientAdj = computeOomAdjLocked(client, cachedAdj, 19593 TOP_APP, doingAll, now); 19594 int clientProcState = client.curProcState; 19595 if (clientProcState >= ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 19596 // If the other app is cached for any reason, for purposes here 19597 // we are going to consider it empty. The specific cached state 19598 // doesn't propagate except under certain conditions. 19599 clientProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 19600 } 19601 String adjType = null; 19602 if ((cr.flags&Context.BIND_ALLOW_OOM_MANAGEMENT) != 0) { 19603 // Not doing bind OOM management, so treat 19604 // this guy more like a started service. 19605 if (app.hasShownUi && app != mHomeProcess) { 19606 // If this process has shown some UI, let it immediately 19607 // go to the LRU list because it may be pretty heavy with 19608 // UI stuff. We'll tag it with a label just to help 19609 // debug and understand what is going on. 19610 if (adj > clientAdj) { 19611 adjType = "cch-bound-ui-services"; 19612 } 19613 app.cached = false; 19614 clientAdj = adj; 19615 clientProcState = procState; 19616 } else { 19617 if (now >= (s.lastActivity 19618 + ActiveServices.MAX_SERVICE_INACTIVITY)) { 19619 // This service has not seen activity within 19620 // recent memory, so allow it to drop to the 19621 // LRU list if there is no other reason to keep 19622 // it around. We'll also tag it with a label just 19623 // to help debug and undertand what is going on. 19624 if (adj > clientAdj) { 19625 adjType = "cch-bound-services"; 19626 } 19627 clientAdj = adj; 19628 } 19629 } 19630 } 19631 if (adj > clientAdj) { 19632 // If this process has recently shown UI, and 19633 // the process that is binding to it is less 19634 // important than being visible, then we don't 19635 // care about the binding as much as we care 19636 // about letting this process get into the LRU 19637 // list to be killed and restarted if needed for 19638 // memory. 19639 if (app.hasShownUi && app != mHomeProcess 19640 && clientAdj > ProcessList.PERCEPTIBLE_APP_ADJ) { 19641 adjType = "cch-bound-ui-services"; 19642 } else { 19643 if ((cr.flags&(Context.BIND_ABOVE_CLIENT 19644 |Context.BIND_IMPORTANT)) != 0) { 19645 adj = clientAdj >= ProcessList.PERSISTENT_SERVICE_ADJ 19646 ? clientAdj : ProcessList.PERSISTENT_SERVICE_ADJ; 19647 } else if ((cr.flags&Context.BIND_NOT_VISIBLE) != 0 19648 && clientAdj < ProcessList.PERCEPTIBLE_APP_ADJ 19649 && adj > ProcessList.PERCEPTIBLE_APP_ADJ) { 19650 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 19651 } else if (clientAdj >= ProcessList.PERCEPTIBLE_APP_ADJ) { 19652 adj = clientAdj; 19653 } else { 19654 if (adj > ProcessList.VISIBLE_APP_ADJ) { 19655 adj = Math.max(clientAdj, ProcessList.VISIBLE_APP_ADJ); 19656 } 19657 } 19658 if (!client.cached) { 19659 app.cached = false; 19660 } 19661 adjType = "service"; 19662 } 19663 } 19664 if ((cr.flags&Context.BIND_NOT_FOREGROUND) == 0) { 19665 // This will treat important bound services identically to 19666 // the top app, which may behave differently than generic 19667 // foreground work. 19668 if (client.curSchedGroup > schedGroup) { 19669 if ((cr.flags&Context.BIND_IMPORTANT) != 0) { 19670 schedGroup = client.curSchedGroup; 19671 } else { 19672 schedGroup = ProcessList.SCHED_GROUP_DEFAULT; 19673 } 19674 } 19675 if (clientProcState <= ActivityManager.PROCESS_STATE_TOP) { 19676 if (clientProcState == ActivityManager.PROCESS_STATE_TOP) { 19677 // Special handling of clients who are in the top state. 19678 // We *may* want to consider this process to be in the 19679 // top state as well, but only if there is not another 19680 // reason for it to be running. Being on the top is a 19681 // special state, meaning you are specifically running 19682 // for the current top app. If the process is already 19683 // running in the background for some other reason, it 19684 // is more important to continue considering it to be 19685 // in the background state. 19686 mayBeTop = true; 19687 clientProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 19688 } else { 19689 // Special handling for above-top states (persistent 19690 // processes). These should not bring the current process 19691 // into the top state, since they are not on top. Instead 19692 // give them the best state after that. 19693 if ((cr.flags&Context.BIND_FOREGROUND_SERVICE) != 0) { 19694 clientProcState = 19695 ActivityManager.PROCESS_STATE_BOUND_FOREGROUND_SERVICE; 19696 } else if (mWakefulness 19697 == PowerManagerInternal.WAKEFULNESS_AWAKE && 19698 (cr.flags&Context.BIND_FOREGROUND_SERVICE_WHILE_AWAKE) 19699 != 0) { 19700 clientProcState = 19701 ActivityManager.PROCESS_STATE_BOUND_FOREGROUND_SERVICE; 19702 } else { 19703 clientProcState = 19704 ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 19705 } 19706 } 19707 } 19708 } else { 19709 if (clientProcState < 19710 ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND) { 19711 clientProcState = 19712 ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND; 19713 } 19714 } 19715 if (procState > clientProcState) { 19716 procState = clientProcState; 19717 } 19718 if (procState < ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND 19719 && (cr.flags&Context.BIND_SHOWING_UI) != 0) { 19720 app.pendingUiClean = true; 19721 } 19722 if (adjType != null) { 19723 app.adjType = adjType; 19724 app.adjTypeCode = ActivityManager.RunningAppProcessInfo 19725 .REASON_SERVICE_IN_USE; 19726 app.adjSource = cr.binding.client; 19727 app.adjSourceProcState = clientProcState; 19728 app.adjTarget = s.name; 19729 } 19730 } 19731 if ((cr.flags&Context.BIND_TREAT_LIKE_ACTIVITY) != 0) { 19732 app.treatLikeActivity = true; 19733 } 19734 final ActivityRecord a = cr.activity; 19735 if ((cr.flags&Context.BIND_ADJUST_WITH_ACTIVITY) != 0) { 19736 if (a != null && adj > ProcessList.FOREGROUND_APP_ADJ && 19737 (a.visible || a.state == ActivityState.RESUMED || 19738 a.state == ActivityState.PAUSING)) { 19739 adj = ProcessList.FOREGROUND_APP_ADJ; 19740 if ((cr.flags&Context.BIND_NOT_FOREGROUND) == 0) { 19741 if ((cr.flags&Context.BIND_IMPORTANT) != 0) { 19742 schedGroup = ProcessList.SCHED_GROUP_TOP_APP_BOUND; 19743 } else { 19744 schedGroup = ProcessList.SCHED_GROUP_DEFAULT; 19745 } 19746 } 19747 app.cached = false; 19748 app.adjType = "service"; 19749 app.adjTypeCode = ActivityManager.RunningAppProcessInfo 19750 .REASON_SERVICE_IN_USE; 19751 app.adjSource = a; 19752 app.adjSourceProcState = procState; 19753 app.adjTarget = s.name; 19754 } 19755 } 19756 } 19757 } 19758 } 19759 19760 for (int provi = app.pubProviders.size()-1; 19761 provi >= 0 && (adj > ProcessList.FOREGROUND_APP_ADJ 19762 || schedGroup == ProcessList.SCHED_GROUP_BACKGROUND 19763 || procState > ActivityManager.PROCESS_STATE_TOP); 19764 provi--) { 19765 ContentProviderRecord cpr = app.pubProviders.valueAt(provi); 19766 for (int i = cpr.connections.size()-1; 19767 i >= 0 && (adj > ProcessList.FOREGROUND_APP_ADJ 19768 || schedGroup == ProcessList.SCHED_GROUP_BACKGROUND 19769 || procState > ActivityManager.PROCESS_STATE_TOP); 19770 i--) { 19771 ContentProviderConnection conn = cpr.connections.get(i); 19772 ProcessRecord client = conn.client; 19773 if (client == app) { 19774 // Being our own client is not interesting. 19775 continue; 19776 } 19777 int clientAdj = computeOomAdjLocked(client, cachedAdj, TOP_APP, doingAll, now); 19778 int clientProcState = client.curProcState; 19779 if (clientProcState >= ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 19780 // If the other app is cached for any reason, for purposes here 19781 // we are going to consider it empty. 19782 clientProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 19783 } 19784 if (adj > clientAdj) { 19785 if (app.hasShownUi && app != mHomeProcess 19786 && clientAdj > ProcessList.PERCEPTIBLE_APP_ADJ) { 19787 app.adjType = "cch-ui-provider"; 19788 } else { 19789 adj = clientAdj > ProcessList.FOREGROUND_APP_ADJ 19790 ? clientAdj : ProcessList.FOREGROUND_APP_ADJ; 19791 app.adjType = "provider"; 19792 } 19793 app.cached &= client.cached; 19794 app.adjTypeCode = ActivityManager.RunningAppProcessInfo 19795 .REASON_PROVIDER_IN_USE; 19796 app.adjSource = client; 19797 app.adjSourceProcState = clientProcState; 19798 app.adjTarget = cpr.name; 19799 } 19800 if (clientProcState <= ActivityManager.PROCESS_STATE_TOP) { 19801 if (clientProcState == ActivityManager.PROCESS_STATE_TOP) { 19802 // Special handling of clients who are in the top state. 19803 // We *may* want to consider this process to be in the 19804 // top state as well, but only if there is not another 19805 // reason for it to be running. Being on the top is a 19806 // special state, meaning you are specifically running 19807 // for the current top app. If the process is already 19808 // running in the background for some other reason, it 19809 // is more important to continue considering it to be 19810 // in the background state. 19811 mayBeTop = true; 19812 clientProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 19813 } else { 19814 // Special handling for above-top states (persistent 19815 // processes). These should not bring the current process 19816 // into the top state, since they are not on top. Instead 19817 // give them the best state after that. 19818 clientProcState = 19819 ActivityManager.PROCESS_STATE_BOUND_FOREGROUND_SERVICE; 19820 } 19821 } 19822 if (procState > clientProcState) { 19823 procState = clientProcState; 19824 } 19825 if (client.curSchedGroup > schedGroup) { 19826 schedGroup = ProcessList.SCHED_GROUP_DEFAULT; 19827 } 19828 } 19829 // If the provider has external (non-framework) process 19830 // dependencies, ensure that its adjustment is at least 19831 // FOREGROUND_APP_ADJ. 19832 if (cpr.hasExternalProcessHandles()) { 19833 if (adj > ProcessList.FOREGROUND_APP_ADJ) { 19834 adj = ProcessList.FOREGROUND_APP_ADJ; 19835 schedGroup = ProcessList.SCHED_GROUP_DEFAULT; 19836 app.cached = false; 19837 app.adjType = "provider"; 19838 app.adjTarget = cpr.name; 19839 } 19840 if (procState > ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND) { 19841 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 19842 } 19843 } 19844 } 19845 19846 if (app.lastProviderTime > 0 && (app.lastProviderTime+CONTENT_PROVIDER_RETAIN_TIME) > now) { 19847 if (adj > ProcessList.PREVIOUS_APP_ADJ) { 19848 adj = ProcessList.PREVIOUS_APP_ADJ; 19849 schedGroup = ProcessList.SCHED_GROUP_BACKGROUND; 19850 app.cached = false; 19851 app.adjType = "provider"; 19852 } 19853 if (procState > ActivityManager.PROCESS_STATE_LAST_ACTIVITY) { 19854 procState = ActivityManager.PROCESS_STATE_LAST_ACTIVITY; 19855 } 19856 } 19857 19858 if (mayBeTop && procState > ActivityManager.PROCESS_STATE_TOP) { 19859 // A client of one of our services or providers is in the top state. We 19860 // *may* want to be in the top state, but not if we are already running in 19861 // the background for some other reason. For the decision here, we are going 19862 // to pick out a few specific states that we want to remain in when a client 19863 // is top (states that tend to be longer-term) and otherwise allow it to go 19864 // to the top state. 19865 switch (procState) { 19866 case ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND: 19867 case ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND: 19868 case ActivityManager.PROCESS_STATE_SERVICE: 19869 // These all are longer-term states, so pull them up to the top 19870 // of the background states, but not all the way to the top state. 19871 procState = ActivityManager.PROCESS_STATE_BOUND_FOREGROUND_SERVICE; 19872 break; 19873 default: 19874 // Otherwise, top is a better choice, so take it. 19875 procState = ActivityManager.PROCESS_STATE_TOP; 19876 break; 19877 } 19878 } 19879 19880 if (procState >= ActivityManager.PROCESS_STATE_CACHED_EMPTY) { 19881 if (app.hasClientActivities) { 19882 // This is a cached process, but with client activities. Mark it so. 19883 procState = ActivityManager.PROCESS_STATE_CACHED_ACTIVITY_CLIENT; 19884 app.adjType = "cch-client-act"; 19885 } else if (app.treatLikeActivity) { 19886 // This is a cached process, but somebody wants us to treat it like it has 19887 // an activity, okay! 19888 procState = ActivityManager.PROCESS_STATE_CACHED_ACTIVITY; 19889 app.adjType = "cch-as-act"; 19890 } 19891 } 19892 19893 if (adj == ProcessList.SERVICE_ADJ) { 19894 if (doingAll) { 19895 app.serviceb = mNewNumAServiceProcs > (mNumServiceProcs/3); 19896 mNewNumServiceProcs++; 19897 //Slog.i(TAG, "ADJ " + app + " serviceb=" + app.serviceb); 19898 if (!app.serviceb) { 19899 // This service isn't far enough down on the LRU list to 19900 // normally be a B service, but if we are low on RAM and it 19901 // is large we want to force it down since we would prefer to 19902 // keep launcher over it. 19903 if (mLastMemoryLevel > ProcessStats.ADJ_MEM_FACTOR_NORMAL 19904 && app.lastPss >= mProcessList.getCachedRestoreThresholdKb()) { 19905 app.serviceHighRam = true; 19906 app.serviceb = true; 19907 //Slog.i(TAG, "ADJ " + app + " high ram!"); 19908 } else { 19909 mNewNumAServiceProcs++; 19910 //Slog.i(TAG, "ADJ " + app + " not high ram!"); 19911 } 19912 } else { 19913 app.serviceHighRam = false; 19914 } 19915 } 19916 if (app.serviceb) { 19917 adj = ProcessList.SERVICE_B_ADJ; 19918 } 19919 } 19920 19921 app.curRawAdj = adj; 19922 19923 //Slog.i(TAG, "OOM ADJ " + app + ": pid=" + app.pid + 19924 // " adj=" + adj + " curAdj=" + app.curAdj + " maxAdj=" + app.maxAdj); 19925 if (adj > app.maxAdj) { 19926 adj = app.maxAdj; 19927 if (app.maxAdj <= ProcessList.PERCEPTIBLE_APP_ADJ) { 19928 schedGroup = ProcessList.SCHED_GROUP_DEFAULT; 19929 } 19930 } 19931 19932 // Do final modification to adj. Everything we do between here and applying 19933 // the final setAdj must be done in this function, because we will also use 19934 // it when computing the final cached adj later. Note that we don't need to 19935 // worry about this for max adj above, since max adj will always be used to 19936 // keep it out of the cached vaues. 19937 app.curAdj = app.modifyRawOomAdj(adj); 19938 app.curSchedGroup = schedGroup; 19939 app.curProcState = procState; 19940 app.foregroundActivities = foregroundActivities; 19941 19942 return app.curRawAdj; 19943 } 19944 19945 /** 19946 * Record new PSS sample for a process. 19947 */ 19948 void recordPssSampleLocked(ProcessRecord proc, int procState, long pss, long uss, long swapPss, 19949 long now) { 19950 EventLogTags.writeAmPss(proc.pid, proc.uid, proc.processName, pss * 1024, uss * 1024, 19951 swapPss * 1024); 19952 proc.lastPssTime = now; 19953 proc.baseProcessTracker.addPss(pss, uss, true, proc.pkgList); 19954 if (DEBUG_PSS) Slog.d(TAG_PSS, 19955 "PSS of " + proc.toShortString() + ": " + pss + " lastPss=" + proc.lastPss 19956 + " state=" + ProcessList.makeProcStateString(procState)); 19957 if (proc.initialIdlePss == 0) { 19958 proc.initialIdlePss = pss; 19959 } 19960 proc.lastPss = pss; 19961 proc.lastSwapPss = swapPss; 19962 if (procState >= ActivityManager.PROCESS_STATE_HOME) { 19963 proc.lastCachedPss = pss; 19964 proc.lastCachedSwapPss = swapPss; 19965 } 19966 19967 final SparseArray<Pair<Long, String>> watchUids 19968 = mMemWatchProcesses.getMap().get(proc.processName); 19969 Long check = null; 19970 if (watchUids != null) { 19971 Pair<Long, String> val = watchUids.get(proc.uid); 19972 if (val == null) { 19973 val = watchUids.get(0); 19974 } 19975 if (val != null) { 19976 check = val.first; 19977 } 19978 } 19979 if (check != null) { 19980 if ((pss * 1024) >= check && proc.thread != null && mMemWatchDumpProcName == null) { 19981 boolean isDebuggable = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 19982 if (!isDebuggable) { 19983 if ((proc.info.flags&ApplicationInfo.FLAG_DEBUGGABLE) != 0) { 19984 isDebuggable = true; 19985 } 19986 } 19987 if (isDebuggable) { 19988 Slog.w(TAG, "Process " + proc + " exceeded pss limit " + check + "; reporting"); 19989 final ProcessRecord myProc = proc; 19990 final File heapdumpFile = DumpHeapProvider.getJavaFile(); 19991 mMemWatchDumpProcName = proc.processName; 19992 mMemWatchDumpFile = heapdumpFile.toString(); 19993 mMemWatchDumpPid = proc.pid; 19994 mMemWatchDumpUid = proc.uid; 19995 BackgroundThread.getHandler().post(new Runnable() { 19996 @Override 19997 public void run() { 19998 revokeUriPermission(ActivityThread.currentActivityThread() 19999 .getApplicationThread(), 20000 DumpHeapActivity.JAVA_URI, 20001 Intent.FLAG_GRANT_READ_URI_PERMISSION 20002 | Intent.FLAG_GRANT_WRITE_URI_PERMISSION, 20003 UserHandle.myUserId()); 20004 ParcelFileDescriptor fd = null; 20005 try { 20006 heapdumpFile.delete(); 20007 fd = ParcelFileDescriptor.open(heapdumpFile, 20008 ParcelFileDescriptor.MODE_CREATE | 20009 ParcelFileDescriptor.MODE_TRUNCATE | 20010 ParcelFileDescriptor.MODE_WRITE_ONLY | 20011 ParcelFileDescriptor.MODE_APPEND); 20012 IApplicationThread thread = myProc.thread; 20013 if (thread != null) { 20014 try { 20015 if (DEBUG_PSS) Slog.d(TAG_PSS, 20016 "Requesting dump heap from " 20017 + myProc + " to " + heapdumpFile); 20018 thread.dumpHeap(true, heapdumpFile.toString(), fd); 20019 } catch (RemoteException e) { 20020 } 20021 } 20022 } catch (FileNotFoundException e) { 20023 e.printStackTrace(); 20024 } finally { 20025 if (fd != null) { 20026 try { 20027 fd.close(); 20028 } catch (IOException e) { 20029 } 20030 } 20031 } 20032 } 20033 }); 20034 } else { 20035 Slog.w(TAG, "Process " + proc + " exceeded pss limit " + check 20036 + ", but debugging not enabled"); 20037 } 20038 } 20039 } 20040 } 20041 20042 /** 20043 * Schedule PSS collection of a process. 20044 */ 20045 void requestPssLocked(ProcessRecord proc, int procState) { 20046 if (mPendingPssProcesses.contains(proc)) { 20047 return; 20048 } 20049 if (mPendingPssProcesses.size() == 0) { 20050 mBgHandler.sendEmptyMessage(COLLECT_PSS_BG_MSG); 20051 } 20052 if (DEBUG_PSS) Slog.d(TAG_PSS, "Requesting PSS of: " + proc); 20053 proc.pssProcState = procState; 20054 mPendingPssProcesses.add(proc); 20055 } 20056 20057 /** 20058 * Schedule PSS collection of all processes. 20059 */ 20060 void requestPssAllProcsLocked(long now, boolean always, boolean memLowered) { 20061 if (!always) { 20062 if (now < (mLastFullPssTime + 20063 (memLowered ? FULL_PSS_LOWERED_INTERVAL : FULL_PSS_MIN_INTERVAL))) { 20064 return; 20065 } 20066 } 20067 if (DEBUG_PSS) Slog.d(TAG_PSS, "Requesting PSS of all procs! memLowered=" + memLowered); 20068 mLastFullPssTime = now; 20069 mFullPssPending = true; 20070 mPendingPssProcesses.ensureCapacity(mLruProcesses.size()); 20071 mPendingPssProcesses.clear(); 20072 for (int i = mLruProcesses.size() - 1; i >= 0; i--) { 20073 ProcessRecord app = mLruProcesses.get(i); 20074 if (app.thread == null 20075 || app.curProcState == ActivityManager.PROCESS_STATE_NONEXISTENT) { 20076 continue; 20077 } 20078 if (memLowered || now > (app.lastStateTime+ProcessList.PSS_ALL_INTERVAL)) { 20079 app.pssProcState = app.setProcState; 20080 app.nextPssTime = ProcessList.computeNextPssTime(app.curProcState, true, 20081 mTestPssMode, isSleepingLocked(), now); 20082 mPendingPssProcesses.add(app); 20083 } 20084 } 20085 mBgHandler.sendEmptyMessage(COLLECT_PSS_BG_MSG); 20086 } 20087 20088 public void setTestPssMode(boolean enabled) { 20089 synchronized (this) { 20090 mTestPssMode = enabled; 20091 if (enabled) { 20092 // Whenever we enable the mode, we want to take a snapshot all of current 20093 // process mem use. 20094 requestPssAllProcsLocked(SystemClock.uptimeMillis(), true, true); 20095 } 20096 } 20097 } 20098 20099 /** 20100 * Ask a given process to GC right now. 20101 */ 20102 final void performAppGcLocked(ProcessRecord app) { 20103 try { 20104 app.lastRequestedGc = SystemClock.uptimeMillis(); 20105 if (app.thread != null) { 20106 if (app.reportLowMemory) { 20107 app.reportLowMemory = false; 20108 app.thread.scheduleLowMemory(); 20109 } else { 20110 app.thread.processInBackground(); 20111 } 20112 } 20113 } catch (Exception e) { 20114 // whatever. 20115 } 20116 } 20117 20118 /** 20119 * Returns true if things are idle enough to perform GCs. 20120 */ 20121 private final boolean canGcNowLocked() { 20122 boolean processingBroadcasts = false; 20123 for (BroadcastQueue q : mBroadcastQueues) { 20124 if (q.mParallelBroadcasts.size() != 0 || q.mOrderedBroadcasts.size() != 0) { 20125 processingBroadcasts = true; 20126 } 20127 } 20128 return !processingBroadcasts 20129 && (isSleepingLocked() || mStackSupervisor.allResumedActivitiesIdle()); 20130 } 20131 20132 /** 20133 * Perform GCs on all processes that are waiting for it, but only 20134 * if things are idle. 20135 */ 20136 final void performAppGcsLocked() { 20137 final int N = mProcessesToGc.size(); 20138 if (N <= 0) { 20139 return; 20140 } 20141 if (canGcNowLocked()) { 20142 while (mProcessesToGc.size() > 0) { 20143 ProcessRecord proc = mProcessesToGc.remove(0); 20144 if (proc.curRawAdj > ProcessList.PERCEPTIBLE_APP_ADJ || proc.reportLowMemory) { 20145 if ((proc.lastRequestedGc+GC_MIN_INTERVAL) 20146 <= SystemClock.uptimeMillis()) { 20147 // To avoid spamming the system, we will GC processes one 20148 // at a time, waiting a few seconds between each. 20149 performAppGcLocked(proc); 20150 scheduleAppGcsLocked(); 20151 return; 20152 } else { 20153 // It hasn't been long enough since we last GCed this 20154 // process... put it in the list to wait for its time. 20155 addProcessToGcListLocked(proc); 20156 break; 20157 } 20158 } 20159 } 20160 20161 scheduleAppGcsLocked(); 20162 } 20163 } 20164 20165 /** 20166 * If all looks good, perform GCs on all processes waiting for them. 20167 */ 20168 final void performAppGcsIfAppropriateLocked() { 20169 if (canGcNowLocked()) { 20170 performAppGcsLocked(); 20171 return; 20172 } 20173 // Still not idle, wait some more. 20174 scheduleAppGcsLocked(); 20175 } 20176 20177 /** 20178 * Schedule the execution of all pending app GCs. 20179 */ 20180 final void scheduleAppGcsLocked() { 20181 mHandler.removeMessages(GC_BACKGROUND_PROCESSES_MSG); 20182 20183 if (mProcessesToGc.size() > 0) { 20184 // Schedule a GC for the time to the next process. 20185 ProcessRecord proc = mProcessesToGc.get(0); 20186 Message msg = mHandler.obtainMessage(GC_BACKGROUND_PROCESSES_MSG); 20187 20188 long when = proc.lastRequestedGc + GC_MIN_INTERVAL; 20189 long now = SystemClock.uptimeMillis(); 20190 if (when < (now+GC_TIMEOUT)) { 20191 when = now + GC_TIMEOUT; 20192 } 20193 mHandler.sendMessageAtTime(msg, when); 20194 } 20195 } 20196 20197 /** 20198 * Add a process to the array of processes waiting to be GCed. Keeps the 20199 * list in sorted order by the last GC time. The process can't already be 20200 * on the list. 20201 */ 20202 final void addProcessToGcListLocked(ProcessRecord proc) { 20203 boolean added = false; 20204 for (int i=mProcessesToGc.size()-1; i>=0; i--) { 20205 if (mProcessesToGc.get(i).lastRequestedGc < 20206 proc.lastRequestedGc) { 20207 added = true; 20208 mProcessesToGc.add(i+1, proc); 20209 break; 20210 } 20211 } 20212 if (!added) { 20213 mProcessesToGc.add(0, proc); 20214 } 20215 } 20216 20217 /** 20218 * Set up to ask a process to GC itself. This will either do it 20219 * immediately, or put it on the list of processes to gc the next 20220 * time things are idle. 20221 */ 20222 final void scheduleAppGcLocked(ProcessRecord app) { 20223 long now = SystemClock.uptimeMillis(); 20224 if ((app.lastRequestedGc+GC_MIN_INTERVAL) > now) { 20225 return; 20226 } 20227 if (!mProcessesToGc.contains(app)) { 20228 addProcessToGcListLocked(app); 20229 scheduleAppGcsLocked(); 20230 } 20231 } 20232 20233 final void checkExcessivePowerUsageLocked(boolean doKills) { 20234 updateCpuStatsNow(); 20235 20236 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 20237 boolean doWakeKills = doKills; 20238 boolean doCpuKills = doKills; 20239 if (mLastPowerCheckRealtime == 0) { 20240 doWakeKills = false; 20241 } 20242 if (mLastPowerCheckUptime == 0) { 20243 doCpuKills = false; 20244 } 20245 if (stats.isScreenOn()) { 20246 doWakeKills = false; 20247 } 20248 final long curRealtime = SystemClock.elapsedRealtime(); 20249 final long realtimeSince = curRealtime - mLastPowerCheckRealtime; 20250 final long curUptime = SystemClock.uptimeMillis(); 20251 final long uptimeSince = curUptime - mLastPowerCheckUptime; 20252 mLastPowerCheckRealtime = curRealtime; 20253 mLastPowerCheckUptime = curUptime; 20254 if (realtimeSince < WAKE_LOCK_MIN_CHECK_DURATION) { 20255 doWakeKills = false; 20256 } 20257 if (uptimeSince < CPU_MIN_CHECK_DURATION) { 20258 doCpuKills = false; 20259 } 20260 int i = mLruProcesses.size(); 20261 while (i > 0) { 20262 i--; 20263 ProcessRecord app = mLruProcesses.get(i); 20264 if (app.setProcState >= ActivityManager.PROCESS_STATE_HOME) { 20265 long wtime; 20266 synchronized (stats) { 20267 wtime = stats.getProcessWakeTime(app.info.uid, 20268 app.pid, curRealtime); 20269 } 20270 long wtimeUsed = wtime - app.lastWakeTime; 20271 long cputimeUsed = app.curCpuTime - app.lastCpuTime; 20272 if (DEBUG_POWER) { 20273 StringBuilder sb = new StringBuilder(128); 20274 sb.append("Wake for "); 20275 app.toShortString(sb); 20276 sb.append(": over "); 20277 TimeUtils.formatDuration(realtimeSince, sb); 20278 sb.append(" used "); 20279 TimeUtils.formatDuration(wtimeUsed, sb); 20280 sb.append(" ("); 20281 sb.append((wtimeUsed*100)/realtimeSince); 20282 sb.append("%)"); 20283 Slog.i(TAG_POWER, sb.toString()); 20284 sb.setLength(0); 20285 sb.append("CPU for "); 20286 app.toShortString(sb); 20287 sb.append(": over "); 20288 TimeUtils.formatDuration(uptimeSince, sb); 20289 sb.append(" used "); 20290 TimeUtils.formatDuration(cputimeUsed, sb); 20291 sb.append(" ("); 20292 sb.append((cputimeUsed*100)/uptimeSince); 20293 sb.append("%)"); 20294 Slog.i(TAG_POWER, sb.toString()); 20295 } 20296 // If a process has held a wake lock for more 20297 // than 50% of the time during this period, 20298 // that sounds bad. Kill! 20299 if (doWakeKills && realtimeSince > 0 20300 && ((wtimeUsed*100)/realtimeSince) >= 50) { 20301 synchronized (stats) { 20302 stats.reportExcessiveWakeLocked(app.info.uid, app.processName, 20303 realtimeSince, wtimeUsed); 20304 } 20305 app.kill("excessive wake held " + wtimeUsed + " during " + realtimeSince, true); 20306 app.baseProcessTracker.reportExcessiveWake(app.pkgList); 20307 } else if (doCpuKills && uptimeSince > 0 20308 && ((cputimeUsed*100)/uptimeSince) >= 25) { 20309 synchronized (stats) { 20310 stats.reportExcessiveCpuLocked(app.info.uid, app.processName, 20311 uptimeSince, cputimeUsed); 20312 } 20313 app.kill("excessive cpu " + cputimeUsed + " during " + uptimeSince, true); 20314 app.baseProcessTracker.reportExcessiveCpu(app.pkgList); 20315 } else { 20316 app.lastWakeTime = wtime; 20317 app.lastCpuTime = app.curCpuTime; 20318 } 20319 } 20320 } 20321 } 20322 20323 private final boolean applyOomAdjLocked(ProcessRecord app, boolean doingAll, long now, 20324 long nowElapsed) { 20325 boolean success = true; 20326 20327 if (app.curRawAdj != app.setRawAdj) { 20328 app.setRawAdj = app.curRawAdj; 20329 } 20330 20331 int changes = 0; 20332 20333 if (app.curAdj != app.setAdj) { 20334 ProcessList.setOomAdj(app.pid, app.info.uid, app.curAdj); 20335 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG_OOM_ADJ, 20336 "Set " + app.pid + " " + app.processName + " adj " + app.curAdj + ": " 20337 + app.adjType); 20338 app.setAdj = app.curAdj; 20339 app.verifiedAdj = ProcessList.INVALID_ADJ; 20340 } 20341 20342 if (app.setSchedGroup != app.curSchedGroup) { 20343 int oldSchedGroup = app.setSchedGroup; 20344 app.setSchedGroup = app.curSchedGroup; 20345 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG_OOM_ADJ, 20346 "Setting sched group of " + app.processName 20347 + " to " + app.curSchedGroup); 20348 if (app.waitingToKill != null && app.curReceivers.isEmpty() 20349 && app.setSchedGroup == ProcessList.SCHED_GROUP_BACKGROUND) { 20350 app.kill(app.waitingToKill, true); 20351 success = false; 20352 } else { 20353 int processGroup; 20354 switch (app.curSchedGroup) { 20355 case ProcessList.SCHED_GROUP_BACKGROUND: 20356 processGroup = Process.THREAD_GROUP_BG_NONINTERACTIVE; 20357 break; 20358 case ProcessList.SCHED_GROUP_TOP_APP: 20359 case ProcessList.SCHED_GROUP_TOP_APP_BOUND: 20360 processGroup = Process.THREAD_GROUP_TOP_APP; 20361 break; 20362 default: 20363 processGroup = Process.THREAD_GROUP_DEFAULT; 20364 break; 20365 } 20366 long oldId = Binder.clearCallingIdentity(); 20367 try { 20368 Process.setProcessGroup(app.pid, processGroup); 20369 if (app.curSchedGroup == ProcessList.SCHED_GROUP_TOP_APP) { 20370 // do nothing if we already switched to RT 20371 if (oldSchedGroup != ProcessList.SCHED_GROUP_TOP_APP) { 20372 // Switch VR thread for app to SCHED_FIFO 20373 if (mInVrMode && app.vrThreadTid != 0) { 20374 try { 20375 Process.setThreadScheduler(app.vrThreadTid, 20376 Process.SCHED_FIFO | Process.SCHED_RESET_ON_FORK, 1); 20377 } catch (IllegalArgumentException e) { 20378 // thread died, ignore 20379 } 20380 } 20381 if (mUseFifoUiScheduling) { 20382 // Switch UI pipeline for app to SCHED_FIFO 20383 app.savedPriority = Process.getThreadPriority(app.pid); 20384 try { 20385 Process.setThreadScheduler(app.pid, 20386 Process.SCHED_FIFO | Process.SCHED_RESET_ON_FORK, 1); 20387 } catch (IllegalArgumentException e) { 20388 // thread died, ignore 20389 } 20390 if (app.renderThreadTid != 0) { 20391 try { 20392 Process.setThreadScheduler(app.renderThreadTid, 20393 Process.SCHED_FIFO | Process.SCHED_RESET_ON_FORK, 1); 20394 } catch (IllegalArgumentException e) { 20395 // thread died, ignore 20396 } 20397 if (DEBUG_OOM_ADJ) { 20398 Slog.d("UI_FIFO", "Set RenderThread (TID " + 20399 app.renderThreadTid + ") to FIFO"); 20400 } 20401 } else { 20402 if (DEBUG_OOM_ADJ) { 20403 Slog.d("UI_FIFO", "Not setting RenderThread TID"); 20404 } 20405 } 20406 } else { 20407 // Boost priority for top app UI and render threads 20408 Process.setThreadPriority(app.pid, -10); 20409 if (app.renderThreadTid != 0) { 20410 try { 20411 Process.setThreadPriority(app.renderThreadTid, -10); 20412 } catch (IllegalArgumentException e) { 20413 // thread died, ignore 20414 } 20415 } 20416 } 20417 } 20418 } else if (oldSchedGroup == ProcessList.SCHED_GROUP_TOP_APP && 20419 app.curSchedGroup != ProcessList.SCHED_GROUP_TOP_APP) { 20420 // Reset VR thread to SCHED_OTHER 20421 // Safe to do even if we're not in VR mode 20422 if (app.vrThreadTid != 0) { 20423 Process.setThreadScheduler(app.vrThreadTid, Process.SCHED_OTHER, 0); 20424 } 20425 if (mUseFifoUiScheduling) { 20426 // Reset UI pipeline to SCHED_OTHER 20427 Process.setThreadScheduler(app.pid, Process.SCHED_OTHER, 0); 20428 Process.setThreadPriority(app.pid, app.savedPriority); 20429 if (app.renderThreadTid != 0) { 20430 Process.setThreadScheduler(app.renderThreadTid, 20431 Process.SCHED_OTHER, 0); 20432 Process.setThreadPriority(app.renderThreadTid, -4); 20433 } 20434 } else { 20435 // Reset priority for top app UI and render threads 20436 Process.setThreadPriority(app.pid, 0); 20437 if (app.renderThreadTid != 0) { 20438 Process.setThreadPriority(app.renderThreadTid, 0); 20439 } 20440 } 20441 } 20442 } catch (Exception e) { 20443 Slog.w(TAG, "Failed setting process group of " + app.pid 20444 + " to " + app.curSchedGroup); 20445 e.printStackTrace(); 20446 } finally { 20447 Binder.restoreCallingIdentity(oldId); 20448 } 20449 } 20450 } 20451 if (app.repForegroundActivities != app.foregroundActivities) { 20452 app.repForegroundActivities = app.foregroundActivities; 20453 changes |= ProcessChangeItem.CHANGE_ACTIVITIES; 20454 } 20455 if (app.repProcState != app.curProcState) { 20456 app.repProcState = app.curProcState; 20457 changes |= ProcessChangeItem.CHANGE_PROCESS_STATE; 20458 if (app.thread != null) { 20459 try { 20460 if (false) { 20461 //RuntimeException h = new RuntimeException("here"); 20462 Slog.i(TAG, "Sending new process state " + app.repProcState 20463 + " to " + app /*, h*/); 20464 } 20465 app.thread.setProcessState(app.repProcState); 20466 } catch (RemoteException e) { 20467 } 20468 } 20469 } 20470 if (app.setProcState == ActivityManager.PROCESS_STATE_NONEXISTENT 20471 || ProcessList.procStatesDifferForMem(app.curProcState, app.setProcState)) { 20472 if (false && mTestPssMode && app.setProcState >= 0 && app.lastStateTime <= (now-200)) { 20473 // Experimental code to more aggressively collect pss while 20474 // running test... the problem is that this tends to collect 20475 // the data right when a process is transitioning between process 20476 // states, which well tend to give noisy data. 20477 long start = SystemClock.uptimeMillis(); 20478 long pss = Debug.getPss(app.pid, mTmpLong, null); 20479 recordPssSampleLocked(app, app.curProcState, pss, mTmpLong[0], mTmpLong[1], now); 20480 mPendingPssProcesses.remove(app); 20481 Slog.i(TAG, "Recorded pss for " + app + " state " + app.setProcState 20482 + " to " + app.curProcState + ": " 20483 + (SystemClock.uptimeMillis()-start) + "ms"); 20484 } 20485 app.lastStateTime = now; 20486 app.nextPssTime = ProcessList.computeNextPssTime(app.curProcState, true, 20487 mTestPssMode, isSleepingLocked(), now); 20488 if (DEBUG_PSS) Slog.d(TAG_PSS, "Process state change from " 20489 + ProcessList.makeProcStateString(app.setProcState) + " to " 20490 + ProcessList.makeProcStateString(app.curProcState) + " next pss in " 20491 + (app.nextPssTime-now) + ": " + app); 20492 } else { 20493 if (now > app.nextPssTime || (now > (app.lastPssTime+ProcessList.PSS_MAX_INTERVAL) 20494 && now > (app.lastStateTime+ProcessList.minTimeFromStateChange( 20495 mTestPssMode)))) { 20496 requestPssLocked(app, app.setProcState); 20497 app.nextPssTime = ProcessList.computeNextPssTime(app.curProcState, false, 20498 mTestPssMode, isSleepingLocked(), now); 20499 } else if (false && DEBUG_PSS) Slog.d(TAG_PSS, 20500 "Not requesting PSS of " + app + ": next=" + (app.nextPssTime-now)); 20501 } 20502 if (app.setProcState != app.curProcState) { 20503 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG_OOM_ADJ, 20504 "Proc state change of " + app.processName 20505 + " to " + app.curProcState); 20506 boolean setImportant = app.setProcState < ActivityManager.PROCESS_STATE_SERVICE; 20507 boolean curImportant = app.curProcState < ActivityManager.PROCESS_STATE_SERVICE; 20508 if (setImportant && !curImportant) { 20509 // This app is no longer something we consider important enough to allow to 20510 // use arbitrary amounts of battery power. Note 20511 // its current wake lock time to later know to kill it if 20512 // it is not behaving well. 20513 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 20514 synchronized (stats) { 20515 app.lastWakeTime = stats.getProcessWakeTime(app.info.uid, 20516 app.pid, nowElapsed); 20517 } 20518 app.lastCpuTime = app.curCpuTime; 20519 20520 } 20521 // Inform UsageStats of important process state change 20522 // Must be called before updating setProcState 20523 maybeUpdateUsageStatsLocked(app, nowElapsed); 20524 20525 app.setProcState = app.curProcState; 20526 if (app.setProcState >= ActivityManager.PROCESS_STATE_HOME) { 20527 app.notCachedSinceIdle = false; 20528 } 20529 if (!doingAll) { 20530 setProcessTrackerStateLocked(app, mProcessStats.getMemFactorLocked(), now); 20531 } else { 20532 app.procStateChanged = true; 20533 } 20534 } else if (app.reportedInteraction && (nowElapsed-app.interactionEventTime) 20535 > USAGE_STATS_INTERACTION_INTERVAL) { 20536 // For apps that sit around for a long time in the interactive state, we need 20537 // to report this at least once a day so they don't go idle. 20538 maybeUpdateUsageStatsLocked(app, nowElapsed); 20539 } 20540 20541 if (changes != 0) { 20542 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG_PROCESS_OBSERVERS, 20543 "Changes in " + app + ": " + changes); 20544 int i = mPendingProcessChanges.size()-1; 20545 ProcessChangeItem item = null; 20546 while (i >= 0) { 20547 item = mPendingProcessChanges.get(i); 20548 if (item.pid == app.pid) { 20549 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG_PROCESS_OBSERVERS, 20550 "Re-using existing item: " + item); 20551 break; 20552 } 20553 i--; 20554 } 20555 if (i < 0) { 20556 // No existing item in pending changes; need a new one. 20557 final int NA = mAvailProcessChanges.size(); 20558 if (NA > 0) { 20559 item = mAvailProcessChanges.remove(NA-1); 20560 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG_PROCESS_OBSERVERS, 20561 "Retrieving available item: " + item); 20562 } else { 20563 item = new ProcessChangeItem(); 20564 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG_PROCESS_OBSERVERS, 20565 "Allocating new item: " + item); 20566 } 20567 item.changes = 0; 20568 item.pid = app.pid; 20569 item.uid = app.info.uid; 20570 if (mPendingProcessChanges.size() == 0) { 20571 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG_PROCESS_OBSERVERS, 20572 "*** Enqueueing dispatch processes changed!"); 20573 mUiHandler.obtainMessage(DISPATCH_PROCESSES_CHANGED_UI_MSG).sendToTarget(); 20574 } 20575 mPendingProcessChanges.add(item); 20576 } 20577 item.changes |= changes; 20578 item.processState = app.repProcState; 20579 item.foregroundActivities = app.repForegroundActivities; 20580 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG_PROCESS_OBSERVERS, 20581 "Item " + Integer.toHexString(System.identityHashCode(item)) 20582 + " " + app.toShortString() + ": changes=" + item.changes 20583 + " procState=" + item.processState 20584 + " foreground=" + item.foregroundActivities 20585 + " type=" + app.adjType + " source=" + app.adjSource 20586 + " target=" + app.adjTarget); 20587 } 20588 20589 return success; 20590 } 20591 20592 private final void enqueueUidChangeLocked(UidRecord uidRec, int uid, int change) { 20593 final UidRecord.ChangeItem pendingChange; 20594 if (uidRec == null || uidRec.pendingChange == null) { 20595 if (mPendingUidChanges.size() == 0) { 20596 if (DEBUG_UID_OBSERVERS) Slog.i(TAG_UID_OBSERVERS, 20597 "*** Enqueueing dispatch uid changed!"); 20598 mUiHandler.obtainMessage(DISPATCH_UIDS_CHANGED_UI_MSG).sendToTarget(); 20599 } 20600 final int NA = mAvailUidChanges.size(); 20601 if (NA > 0) { 20602 pendingChange = mAvailUidChanges.remove(NA-1); 20603 if (DEBUG_UID_OBSERVERS) Slog.i(TAG_UID_OBSERVERS, 20604 "Retrieving available item: " + pendingChange); 20605 } else { 20606 pendingChange = new UidRecord.ChangeItem(); 20607 if (DEBUG_UID_OBSERVERS) Slog.i(TAG_UID_OBSERVERS, 20608 "Allocating new item: " + pendingChange); 20609 } 20610 if (uidRec != null) { 20611 uidRec.pendingChange = pendingChange; 20612 if (change == UidRecord.CHANGE_GONE && !uidRec.idle) { 20613 // If this uid is going away, and we haven't yet reported it is gone, 20614 // then do so now. 20615 change = UidRecord.CHANGE_GONE_IDLE; 20616 } 20617 } else if (uid < 0) { 20618 throw new IllegalArgumentException("No UidRecord or uid"); 20619 } 20620 pendingChange.uidRecord = uidRec; 20621 pendingChange.uid = uidRec != null ? uidRec.uid : uid; 20622 mPendingUidChanges.add(pendingChange); 20623 } else { 20624 pendingChange = uidRec.pendingChange; 20625 if (change == UidRecord.CHANGE_GONE && pendingChange.change == UidRecord.CHANGE_IDLE) { 20626 change = UidRecord.CHANGE_GONE_IDLE; 20627 } 20628 } 20629 pendingChange.change = change; 20630 pendingChange.processState = uidRec != null 20631 ? uidRec.setProcState : ActivityManager.PROCESS_STATE_NONEXISTENT; 20632 20633 // Directly update the power manager, since we sit on top of it and it is critical 20634 // it be kept in sync (so wake locks will be held as soon as appropriate). 20635 if (mLocalPowerManager != null) { 20636 switch (change) { 20637 case UidRecord.CHANGE_GONE: 20638 case UidRecord.CHANGE_GONE_IDLE: 20639 mLocalPowerManager.uidGone(pendingChange.uid); 20640 break; 20641 case UidRecord.CHANGE_IDLE: 20642 mLocalPowerManager.uidIdle(pendingChange.uid); 20643 break; 20644 case UidRecord.CHANGE_ACTIVE: 20645 mLocalPowerManager.uidActive(pendingChange.uid); 20646 break; 20647 default: 20648 mLocalPowerManager.updateUidProcState(pendingChange.uid, 20649 pendingChange.processState); 20650 break; 20651 } 20652 } 20653 } 20654 20655 private void maybeUpdateProviderUsageStatsLocked(ProcessRecord app, String providerPkgName, 20656 String authority) { 20657 if (app == null) return; 20658 if (app.curProcState <= ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND) { 20659 UserState userState = mUserController.getStartedUserStateLocked(app.userId); 20660 if (userState == null) return; 20661 final long now = SystemClock.elapsedRealtime(); 20662 Long lastReported = userState.mProviderLastReportedFg.get(authority); 20663 if (lastReported == null || lastReported < now - 60 * 1000L) { 20664 if (mSystemReady) { 20665 // Cannot touch the user stats if not system ready 20666 mUsageStatsService.reportContentProviderUsage( 20667 authority, providerPkgName, app.userId); 20668 } 20669 userState.mProviderLastReportedFg.put(authority, now); 20670 } 20671 } 20672 } 20673 20674 private void maybeUpdateUsageStatsLocked(ProcessRecord app, long nowElapsed) { 20675 if (DEBUG_USAGE_STATS) { 20676 Slog.d(TAG, "Checking proc [" + Arrays.toString(app.getPackageList()) 20677 + "] state changes: old = " + app.setProcState + ", new = " 20678 + app.curProcState); 20679 } 20680 if (mUsageStatsService == null) { 20681 return; 20682 } 20683 boolean isInteraction; 20684 // To avoid some abuse patterns, we are going to be careful about what we consider 20685 // to be an app interaction. Being the top activity doesn't count while the display 20686 // is sleeping, nor do short foreground services. 20687 if (app.curProcState <= ActivityManager.PROCESS_STATE_BOUND_FOREGROUND_SERVICE) { 20688 isInteraction = true; 20689 app.fgInteractionTime = 0; 20690 } else if (app.curProcState <= ActivityManager.PROCESS_STATE_TOP_SLEEPING) { 20691 if (app.fgInteractionTime == 0) { 20692 app.fgInteractionTime = nowElapsed; 20693 isInteraction = false; 20694 } else { 20695 isInteraction = nowElapsed > app.fgInteractionTime + SERVICE_USAGE_INTERACTION_TIME; 20696 } 20697 } else { 20698 // If the app was being forced to the foreground, by say a Toast, then 20699 // no need to treat it as an interaction 20700 isInteraction = app.forcingToForeground == null 20701 && app.curProcState <= ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 20702 app.fgInteractionTime = 0; 20703 } 20704 if (isInteraction && (!app.reportedInteraction 20705 || (nowElapsed-app.interactionEventTime) > USAGE_STATS_INTERACTION_INTERVAL)) { 20706 app.interactionEventTime = nowElapsed; 20707 String[] packages = app.getPackageList(); 20708 if (packages != null) { 20709 for (int i = 0; i < packages.length; i++) { 20710 mUsageStatsService.reportEvent(packages[i], app.userId, 20711 UsageEvents.Event.SYSTEM_INTERACTION); 20712 } 20713 } 20714 } 20715 app.reportedInteraction = isInteraction; 20716 if (!isInteraction) { 20717 app.interactionEventTime = 0; 20718 } 20719 } 20720 20721 private final void setProcessTrackerStateLocked(ProcessRecord proc, int memFactor, long now) { 20722 if (proc.thread != null) { 20723 if (proc.baseProcessTracker != null) { 20724 proc.baseProcessTracker.setState(proc.repProcState, memFactor, now, proc.pkgList); 20725 } 20726 } 20727 } 20728 20729 private final boolean updateOomAdjLocked(ProcessRecord app, int cachedAdj, 20730 ProcessRecord TOP_APP, boolean doingAll, long now) { 20731 if (app.thread == null) { 20732 return false; 20733 } 20734 20735 computeOomAdjLocked(app, cachedAdj, TOP_APP, doingAll, now); 20736 20737 return applyOomAdjLocked(app, doingAll, now, SystemClock.elapsedRealtime()); 20738 } 20739 20740 final void updateProcessForegroundLocked(ProcessRecord proc, boolean isForeground, 20741 boolean oomAdj) { 20742 if (isForeground != proc.foregroundServices) { 20743 proc.foregroundServices = isForeground; 20744 ArrayList<ProcessRecord> curProcs = mForegroundPackages.get(proc.info.packageName, 20745 proc.info.uid); 20746 if (isForeground) { 20747 if (curProcs == null) { 20748 curProcs = new ArrayList<ProcessRecord>(); 20749 mForegroundPackages.put(proc.info.packageName, proc.info.uid, curProcs); 20750 } 20751 if (!curProcs.contains(proc)) { 20752 curProcs.add(proc); 20753 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_FOREGROUND_START, 20754 proc.info.packageName, proc.info.uid); 20755 } 20756 } else { 20757 if (curProcs != null) { 20758 if (curProcs.remove(proc)) { 20759 mBatteryStatsService.noteEvent( 20760 BatteryStats.HistoryItem.EVENT_FOREGROUND_FINISH, 20761 proc.info.packageName, proc.info.uid); 20762 if (curProcs.size() <= 0) { 20763 mForegroundPackages.remove(proc.info.packageName, proc.info.uid); 20764 } 20765 } 20766 } 20767 } 20768 if (oomAdj) { 20769 updateOomAdjLocked(); 20770 } 20771 } 20772 } 20773 20774 private final ActivityRecord resumedAppLocked() { 20775 ActivityRecord act = mStackSupervisor.getResumedActivityLocked(); 20776 String pkg; 20777 int uid; 20778 if (act != null) { 20779 pkg = act.packageName; 20780 uid = act.info.applicationInfo.uid; 20781 } else { 20782 pkg = null; 20783 uid = -1; 20784 } 20785 // Has the UID or resumed package name changed? 20786 if (uid != mCurResumedUid || (pkg != mCurResumedPackage 20787 && (pkg == null || !pkg.equals(mCurResumedPackage)))) { 20788 if (mCurResumedPackage != null) { 20789 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_TOP_FINISH, 20790 mCurResumedPackage, mCurResumedUid); 20791 } 20792 mCurResumedPackage = pkg; 20793 mCurResumedUid = uid; 20794 if (mCurResumedPackage != null) { 20795 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_TOP_START, 20796 mCurResumedPackage, mCurResumedUid); 20797 } 20798 } 20799 return act; 20800 } 20801 20802 final boolean updateOomAdjLocked(ProcessRecord app) { 20803 final ActivityRecord TOP_ACT = resumedAppLocked(); 20804 final ProcessRecord TOP_APP = TOP_ACT != null ? TOP_ACT.app : null; 20805 final boolean wasCached = app.cached; 20806 20807 mAdjSeq++; 20808 20809 // This is the desired cached adjusment we want to tell it to use. 20810 // If our app is currently cached, we know it, and that is it. Otherwise, 20811 // we don't know it yet, and it needs to now be cached we will then 20812 // need to do a complete oom adj. 20813 final int cachedAdj = app.curRawAdj >= ProcessList.CACHED_APP_MIN_ADJ 20814 ? app.curRawAdj : ProcessList.UNKNOWN_ADJ; 20815 boolean success = updateOomAdjLocked(app, cachedAdj, TOP_APP, false, 20816 SystemClock.uptimeMillis()); 20817 if (wasCached != app.cached || app.curRawAdj == ProcessList.UNKNOWN_ADJ) { 20818 // Changed to/from cached state, so apps after it in the LRU 20819 // list may also be changed. 20820 updateOomAdjLocked(); 20821 } 20822 return success; 20823 } 20824 20825 final void updateOomAdjLocked() { 20826 final ActivityRecord TOP_ACT = resumedAppLocked(); 20827 final ProcessRecord TOP_APP = TOP_ACT != null ? TOP_ACT.app : null; 20828 final long now = SystemClock.uptimeMillis(); 20829 final long nowElapsed = SystemClock.elapsedRealtime(); 20830 final long oldTime = now - ProcessList.MAX_EMPTY_TIME; 20831 final int N = mLruProcesses.size(); 20832 20833 if (false) { 20834 RuntimeException e = new RuntimeException(); 20835 e.fillInStackTrace(); 20836 Slog.i(TAG, "updateOomAdj: top=" + TOP_ACT, e); 20837 } 20838 20839 // Reset state in all uid records. 20840 for (int i=mActiveUids.size()-1; i>=0; i--) { 20841 final UidRecord uidRec = mActiveUids.valueAt(i); 20842 if (false && DEBUG_UID_OBSERVERS) Slog.i(TAG_UID_OBSERVERS, 20843 "Starting update of " + uidRec); 20844 uidRec.reset(); 20845 } 20846 20847 mStackSupervisor.rankTaskLayersIfNeeded(); 20848 20849 mAdjSeq++; 20850 mNewNumServiceProcs = 0; 20851 mNewNumAServiceProcs = 0; 20852 20853 final int emptyProcessLimit; 20854 final int cachedProcessLimit; 20855 if (mProcessLimit <= 0) { 20856 emptyProcessLimit = cachedProcessLimit = 0; 20857 } else if (mProcessLimit == 1) { 20858 emptyProcessLimit = 1; 20859 cachedProcessLimit = 0; 20860 } else { 20861 emptyProcessLimit = ProcessList.computeEmptyProcessLimit(mProcessLimit); 20862 cachedProcessLimit = mProcessLimit - emptyProcessLimit; 20863 } 20864 20865 // Let's determine how many processes we have running vs. 20866 // how many slots we have for background processes; we may want 20867 // to put multiple processes in a slot of there are enough of 20868 // them. 20869 int numSlots = (ProcessList.CACHED_APP_MAX_ADJ 20870 - ProcessList.CACHED_APP_MIN_ADJ + 1) / 2; 20871 int numEmptyProcs = N - mNumNonCachedProcs - mNumCachedHiddenProcs; 20872 if (numEmptyProcs > cachedProcessLimit) { 20873 // If there are more empty processes than our limit on cached 20874 // processes, then use the cached process limit for the factor. 20875 // This ensures that the really old empty processes get pushed 20876 // down to the bottom, so if we are running low on memory we will 20877 // have a better chance at keeping around more cached processes 20878 // instead of a gazillion empty processes. 20879 numEmptyProcs = cachedProcessLimit; 20880 } 20881 int emptyFactor = numEmptyProcs/numSlots; 20882 if (emptyFactor < 1) emptyFactor = 1; 20883 int cachedFactor = (mNumCachedHiddenProcs > 0 ? mNumCachedHiddenProcs : 1)/numSlots; 20884 if (cachedFactor < 1) cachedFactor = 1; 20885 int stepCached = 0; 20886 int stepEmpty = 0; 20887 int numCached = 0; 20888 int numEmpty = 0; 20889 int numTrimming = 0; 20890 20891 mNumNonCachedProcs = 0; 20892 mNumCachedHiddenProcs = 0; 20893 20894 // First update the OOM adjustment for each of the 20895 // application processes based on their current state. 20896 int curCachedAdj = ProcessList.CACHED_APP_MIN_ADJ; 20897 int nextCachedAdj = curCachedAdj+1; 20898 int curEmptyAdj = ProcessList.CACHED_APP_MIN_ADJ; 20899 int nextEmptyAdj = curEmptyAdj+2; 20900 for (int i=N-1; i>=0; i--) { 20901 ProcessRecord app = mLruProcesses.get(i); 20902 if (!app.killedByAm && app.thread != null) { 20903 app.procStateChanged = false; 20904 computeOomAdjLocked(app, ProcessList.UNKNOWN_ADJ, TOP_APP, true, now); 20905 20906 // If we haven't yet assigned the final cached adj 20907 // to the process, do that now. 20908 if (app.curAdj >= ProcessList.UNKNOWN_ADJ) { 20909 switch (app.curProcState) { 20910 case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY: 20911 case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY_CLIENT: 20912 // This process is a cached process holding activities... 20913 // assign it the next cached value for that type, and then 20914 // step that cached level. 20915 app.curRawAdj = curCachedAdj; 20916 app.curAdj = app.modifyRawOomAdj(curCachedAdj); 20917 if (DEBUG_LRU && false) Slog.d(TAG_LRU, "Assigning activity LRU #" + i 20918 + " adj: " + app.curAdj + " (curCachedAdj=" + curCachedAdj 20919 + ")"); 20920 if (curCachedAdj != nextCachedAdj) { 20921 stepCached++; 20922 if (stepCached >= cachedFactor) { 20923 stepCached = 0; 20924 curCachedAdj = nextCachedAdj; 20925 nextCachedAdj += 2; 20926 if (nextCachedAdj > ProcessList.CACHED_APP_MAX_ADJ) { 20927 nextCachedAdj = ProcessList.CACHED_APP_MAX_ADJ; 20928 } 20929 } 20930 } 20931 break; 20932 default: 20933 // For everything else, assign next empty cached process 20934 // level and bump that up. Note that this means that 20935 // long-running services that have dropped down to the 20936 // cached level will be treated as empty (since their process 20937 // state is still as a service), which is what we want. 20938 app.curRawAdj = curEmptyAdj; 20939 app.curAdj = app.modifyRawOomAdj(curEmptyAdj); 20940 if (DEBUG_LRU && false) Slog.d(TAG_LRU, "Assigning empty LRU #" + i 20941 + " adj: " + app.curAdj + " (curEmptyAdj=" + curEmptyAdj 20942 + ")"); 20943 if (curEmptyAdj != nextEmptyAdj) { 20944 stepEmpty++; 20945 if (stepEmpty >= emptyFactor) { 20946 stepEmpty = 0; 20947 curEmptyAdj = nextEmptyAdj; 20948 nextEmptyAdj += 2; 20949 if (nextEmptyAdj > ProcessList.CACHED_APP_MAX_ADJ) { 20950 nextEmptyAdj = ProcessList.CACHED_APP_MAX_ADJ; 20951 } 20952 } 20953 } 20954 break; 20955 } 20956 } 20957 20958 applyOomAdjLocked(app, true, now, nowElapsed); 20959 20960 // Count the number of process types. 20961 switch (app.curProcState) { 20962 case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY: 20963 case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY_CLIENT: 20964 mNumCachedHiddenProcs++; 20965 numCached++; 20966 if (numCached > cachedProcessLimit) { 20967 app.kill("cached #" + numCached, true); 20968 } 20969 break; 20970 case ActivityManager.PROCESS_STATE_CACHED_EMPTY: 20971 if (numEmpty > ProcessList.TRIM_EMPTY_APPS 20972 && app.lastActivityTime < oldTime) { 20973 app.kill("empty for " 20974 + ((oldTime + ProcessList.MAX_EMPTY_TIME - app.lastActivityTime) 20975 / 1000) + "s", true); 20976 } else { 20977 numEmpty++; 20978 if (numEmpty > emptyProcessLimit) { 20979 app.kill("empty #" + numEmpty, true); 20980 } 20981 } 20982 break; 20983 default: 20984 mNumNonCachedProcs++; 20985 break; 20986 } 20987 20988 if (app.isolated && app.services.size() <= 0) { 20989 // If this is an isolated process, and there are no 20990 // services running in it, then the process is no longer 20991 // needed. We agressively kill these because we can by 20992 // definition not re-use the same process again, and it is 20993 // good to avoid having whatever code was running in them 20994 // left sitting around after no longer needed. 20995 app.kill("isolated not needed", true); 20996 } else { 20997 // Keeping this process, update its uid. 20998 final UidRecord uidRec = app.uidRecord; 20999 if (uidRec != null && uidRec.curProcState > app.curProcState) { 21000 uidRec.curProcState = app.curProcState; 21001 } 21002 } 21003 21004 if (app.curProcState >= ActivityManager.PROCESS_STATE_HOME 21005 && !app.killedByAm) { 21006 numTrimming++; 21007 } 21008 } 21009 } 21010 21011 mNumServiceProcs = mNewNumServiceProcs; 21012 21013 // Now determine the memory trimming level of background processes. 21014 // Unfortunately we need to start at the back of the list to do this 21015 // properly. We only do this if the number of background apps we 21016 // are managing to keep around is less than half the maximum we desire; 21017 // if we are keeping a good number around, we'll let them use whatever 21018 // memory they want. 21019 final int numCachedAndEmpty = numCached + numEmpty; 21020 int memFactor; 21021 if (numCached <= ProcessList.TRIM_CACHED_APPS 21022 && numEmpty <= ProcessList.TRIM_EMPTY_APPS) { 21023 if (numCachedAndEmpty <= ProcessList.TRIM_CRITICAL_THRESHOLD) { 21024 memFactor = ProcessStats.ADJ_MEM_FACTOR_CRITICAL; 21025 } else if (numCachedAndEmpty <= ProcessList.TRIM_LOW_THRESHOLD) { 21026 memFactor = ProcessStats.ADJ_MEM_FACTOR_LOW; 21027 } else { 21028 memFactor = ProcessStats.ADJ_MEM_FACTOR_MODERATE; 21029 } 21030 } else { 21031 memFactor = ProcessStats.ADJ_MEM_FACTOR_NORMAL; 21032 } 21033 // We always allow the memory level to go up (better). We only allow it to go 21034 // down if we are in a state where that is allowed, *and* the total number of processes 21035 // has gone down since last time. 21036 if (DEBUG_OOM_ADJ) Slog.d(TAG_OOM_ADJ, "oom: memFactor=" + memFactor 21037 + " last=" + mLastMemoryLevel + " allowLow=" + mAllowLowerMemLevel 21038 + " numProcs=" + mLruProcesses.size() + " last=" + mLastNumProcesses); 21039 if (memFactor > mLastMemoryLevel) { 21040 if (!mAllowLowerMemLevel || mLruProcesses.size() >= mLastNumProcesses) { 21041 memFactor = mLastMemoryLevel; 21042 if (DEBUG_OOM_ADJ) Slog.d(TAG_OOM_ADJ, "Keeping last mem factor!"); 21043 } 21044 } 21045 if (memFactor != mLastMemoryLevel) { 21046 EventLogTags.writeAmMemFactor(memFactor, mLastMemoryLevel); 21047 } 21048 mLastMemoryLevel = memFactor; 21049 mLastNumProcesses = mLruProcesses.size(); 21050 boolean allChanged = mProcessStats.setMemFactorLocked(memFactor, !isSleepingLocked(), now); 21051 final int trackerMemFactor = mProcessStats.getMemFactorLocked(); 21052 if (memFactor != ProcessStats.ADJ_MEM_FACTOR_NORMAL) { 21053 if (mLowRamStartTime == 0) { 21054 mLowRamStartTime = now; 21055 } 21056 int step = 0; 21057 int fgTrimLevel; 21058 switch (memFactor) { 21059 case ProcessStats.ADJ_MEM_FACTOR_CRITICAL: 21060 fgTrimLevel = ComponentCallbacks2.TRIM_MEMORY_RUNNING_CRITICAL; 21061 break; 21062 case ProcessStats.ADJ_MEM_FACTOR_LOW: 21063 fgTrimLevel = ComponentCallbacks2.TRIM_MEMORY_RUNNING_LOW; 21064 break; 21065 default: 21066 fgTrimLevel = ComponentCallbacks2.TRIM_MEMORY_RUNNING_MODERATE; 21067 break; 21068 } 21069 int factor = numTrimming/3; 21070 int minFactor = 2; 21071 if (mHomeProcess != null) minFactor++; 21072 if (mPreviousProcess != null) minFactor++; 21073 if (factor < minFactor) factor = minFactor; 21074 int curLevel = ComponentCallbacks2.TRIM_MEMORY_COMPLETE; 21075 for (int i=N-1; i>=0; i--) { 21076 ProcessRecord app = mLruProcesses.get(i); 21077 if (allChanged || app.procStateChanged) { 21078 setProcessTrackerStateLocked(app, trackerMemFactor, now); 21079 app.procStateChanged = false; 21080 } 21081 if (app.curProcState >= ActivityManager.PROCESS_STATE_HOME 21082 && !app.killedByAm) { 21083 if (app.trimMemoryLevel < curLevel && app.thread != null) { 21084 try { 21085 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG_OOM_ADJ, 21086 "Trimming memory of " + app.processName + " to " + curLevel); 21087 app.thread.scheduleTrimMemory(curLevel); 21088 } catch (RemoteException e) { 21089 } 21090 if (false) { 21091 // For now we won't do this; our memory trimming seems 21092 // to be good enough at this point that destroying 21093 // activities causes more harm than good. 21094 if (curLevel >= ComponentCallbacks2.TRIM_MEMORY_COMPLETE 21095 && app != mHomeProcess && app != mPreviousProcess) { 21096 // Need to do this on its own message because the stack may not 21097 // be in a consistent state at this point. 21098 // For these apps we will also finish their activities 21099 // to help them free memory. 21100 mStackSupervisor.scheduleDestroyAllActivities(app, "trim"); 21101 } 21102 } 21103 } 21104 app.trimMemoryLevel = curLevel; 21105 step++; 21106 if (step >= factor) { 21107 step = 0; 21108 switch (curLevel) { 21109 case ComponentCallbacks2.TRIM_MEMORY_COMPLETE: 21110 curLevel = ComponentCallbacks2.TRIM_MEMORY_MODERATE; 21111 break; 21112 case ComponentCallbacks2.TRIM_MEMORY_MODERATE: 21113 curLevel = ComponentCallbacks2.TRIM_MEMORY_BACKGROUND; 21114 break; 21115 } 21116 } 21117 } else if (app.curProcState == ActivityManager.PROCESS_STATE_HEAVY_WEIGHT) { 21118 if (app.trimMemoryLevel < ComponentCallbacks2.TRIM_MEMORY_BACKGROUND 21119 && app.thread != null) { 21120 try { 21121 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG_OOM_ADJ, 21122 "Trimming memory of heavy-weight " + app.processName 21123 + " to " + ComponentCallbacks2.TRIM_MEMORY_BACKGROUND); 21124 app.thread.scheduleTrimMemory( 21125 ComponentCallbacks2.TRIM_MEMORY_BACKGROUND); 21126 } catch (RemoteException e) { 21127 } 21128 } 21129 app.trimMemoryLevel = ComponentCallbacks2.TRIM_MEMORY_BACKGROUND; 21130 } else { 21131 if ((app.curProcState >= ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND 21132 || app.systemNoUi) && app.pendingUiClean) { 21133 // If this application is now in the background and it 21134 // had done UI, then give it the special trim level to 21135 // have it free UI resources. 21136 final int level = ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN; 21137 if (app.trimMemoryLevel < level && app.thread != null) { 21138 try { 21139 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG_OOM_ADJ, 21140 "Trimming memory of bg-ui " + app.processName 21141 + " to " + level); 21142 app.thread.scheduleTrimMemory(level); 21143 } catch (RemoteException e) { 21144 } 21145 } 21146 app.pendingUiClean = false; 21147 } 21148 if (app.trimMemoryLevel < fgTrimLevel && app.thread != null) { 21149 try { 21150 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG_OOM_ADJ, 21151 "Trimming memory of fg " + app.processName 21152 + " to " + fgTrimLevel); 21153 app.thread.scheduleTrimMemory(fgTrimLevel); 21154 } catch (RemoteException e) { 21155 } 21156 } 21157 app.trimMemoryLevel = fgTrimLevel; 21158 } 21159 } 21160 } else { 21161 if (mLowRamStartTime != 0) { 21162 mLowRamTimeSinceLastIdle += now - mLowRamStartTime; 21163 mLowRamStartTime = 0; 21164 } 21165 for (int i=N-1; i>=0; i--) { 21166 ProcessRecord app = mLruProcesses.get(i); 21167 if (allChanged || app.procStateChanged) { 21168 setProcessTrackerStateLocked(app, trackerMemFactor, now); 21169 app.procStateChanged = false; 21170 } 21171 if ((app.curProcState >= ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND 21172 || app.systemNoUi) && app.pendingUiClean) { 21173 if (app.trimMemoryLevel < ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN 21174 && app.thread != null) { 21175 try { 21176 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG_OOM_ADJ, 21177 "Trimming memory of ui hidden " + app.processName 21178 + " to " + ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN); 21179 app.thread.scheduleTrimMemory( 21180 ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN); 21181 } catch (RemoteException e) { 21182 } 21183 } 21184 app.pendingUiClean = false; 21185 } 21186 app.trimMemoryLevel = 0; 21187 } 21188 } 21189 21190 if (mAlwaysFinishActivities) { 21191 // Need to do this on its own message because the stack may not 21192 // be in a consistent state at this point. 21193 mStackSupervisor.scheduleDestroyAllActivities(null, "always-finish"); 21194 } 21195 21196 if (allChanged) { 21197 requestPssAllProcsLocked(now, false, mProcessStats.isMemFactorLowered()); 21198 } 21199 21200 // Update from any uid changes. 21201 if (mLocalPowerManager != null) { 21202 mLocalPowerManager.startUidChanges(); 21203 } 21204 for (int i=mActiveUids.size()-1; i>=0; i--) { 21205 final UidRecord uidRec = mActiveUids.valueAt(i); 21206 int uidChange = UidRecord.CHANGE_PROCSTATE; 21207 if (uidRec.setProcState != uidRec.curProcState) { 21208 if (DEBUG_UID_OBSERVERS) Slog.i(TAG_UID_OBSERVERS, 21209 "Changes in " + uidRec + ": proc state from " + uidRec.setProcState 21210 + " to " + uidRec.curProcState); 21211 if (ActivityManager.isProcStateBackground(uidRec.curProcState)) { 21212 if (!ActivityManager.isProcStateBackground(uidRec.setProcState)) { 21213 uidRec.lastBackgroundTime = nowElapsed; 21214 if (!mHandler.hasMessages(IDLE_UIDS_MSG)) { 21215 // Note: the background settle time is in elapsed realtime, while 21216 // the handler time base is uptime. All this means is that we may 21217 // stop background uids later than we had intended, but that only 21218 // happens because the device was sleeping so we are okay anyway. 21219 mHandler.sendEmptyMessageDelayed(IDLE_UIDS_MSG, BACKGROUND_SETTLE_TIME); 21220 } 21221 } 21222 } else { 21223 if (uidRec.idle) { 21224 uidChange = UidRecord.CHANGE_ACTIVE; 21225 uidRec.idle = false; 21226 } 21227 uidRec.lastBackgroundTime = 0; 21228 } 21229 uidRec.setProcState = uidRec.curProcState; 21230 enqueueUidChangeLocked(uidRec, -1, uidChange); 21231 noteUidProcessState(uidRec.uid, uidRec.curProcState); 21232 } 21233 } 21234 if (mLocalPowerManager != null) { 21235 mLocalPowerManager.finishUidChanges(); 21236 } 21237 21238 if (mProcessStats.shouldWriteNowLocked(now)) { 21239 mHandler.post(new Runnable() { 21240 @Override public void run() { 21241 synchronized (ActivityManagerService.this) { 21242 mProcessStats.writeStateAsyncLocked(); 21243 } 21244 } 21245 }); 21246 } 21247 21248 if (DEBUG_OOM_ADJ) { 21249 final long duration = SystemClock.uptimeMillis() - now; 21250 if (false) { 21251 Slog.d(TAG_OOM_ADJ, "Did OOM ADJ in " + duration + "ms", 21252 new RuntimeException("here").fillInStackTrace()); 21253 } else { 21254 Slog.d(TAG_OOM_ADJ, "Did OOM ADJ in " + duration + "ms"); 21255 } 21256 } 21257 } 21258 21259 final void idleUids() { 21260 synchronized (this) { 21261 final int N = mActiveUids.size(); 21262 if (N <= 0) { 21263 return; 21264 } 21265 final long nowElapsed = SystemClock.elapsedRealtime(); 21266 final long maxBgTime = nowElapsed - BACKGROUND_SETTLE_TIME; 21267 long nextTime = 0; 21268 if (mLocalPowerManager != null) { 21269 mLocalPowerManager.startUidChanges(); 21270 } 21271 for (int i=N-1; i>=0; i--) { 21272 final UidRecord uidRec = mActiveUids.valueAt(i); 21273 final long bgTime = uidRec.lastBackgroundTime; 21274 if (bgTime > 0 && !uidRec.idle) { 21275 if (bgTime <= maxBgTime) { 21276 uidRec.idle = true; 21277 doStopUidLocked(uidRec.uid, uidRec); 21278 } else { 21279 if (nextTime == 0 || nextTime > bgTime) { 21280 nextTime = bgTime; 21281 } 21282 } 21283 } 21284 } 21285 if (mLocalPowerManager != null) { 21286 mLocalPowerManager.finishUidChanges(); 21287 } 21288 if (nextTime > 0) { 21289 mHandler.removeMessages(IDLE_UIDS_MSG); 21290 mHandler.sendEmptyMessageDelayed(IDLE_UIDS_MSG, 21291 nextTime + BACKGROUND_SETTLE_TIME - nowElapsed); 21292 } 21293 } 21294 } 21295 21296 final void runInBackgroundDisabled(int uid) { 21297 synchronized (this) { 21298 UidRecord uidRec = mActiveUids.get(uid); 21299 if (uidRec != null) { 21300 // This uid is actually running... should it be considered background now? 21301 if (uidRec.idle) { 21302 doStopUidLocked(uidRec.uid, uidRec); 21303 } 21304 } else { 21305 // This uid isn't actually running... still send a report about it being "stopped". 21306 doStopUidLocked(uid, null); 21307 } 21308 } 21309 } 21310 21311 final void doStopUidLocked(int uid, final UidRecord uidRec) { 21312 mServices.stopInBackgroundLocked(uid); 21313 enqueueUidChangeLocked(uidRec, uid, UidRecord.CHANGE_IDLE); 21314 } 21315 21316 final void trimApplications() { 21317 synchronized (this) { 21318 int i; 21319 21320 // First remove any unused application processes whose package 21321 // has been removed. 21322 for (i=mRemovedProcesses.size()-1; i>=0; i--) { 21323 final ProcessRecord app = mRemovedProcesses.get(i); 21324 if (app.activities.size() == 0 21325 && app.curReceivers.isEmpty() && app.services.size() == 0) { 21326 Slog.i( 21327 TAG, "Exiting empty application process " 21328 + app.toShortString() + " (" 21329 + (app.thread != null ? app.thread.asBinder() : null) 21330 + ")\n"); 21331 if (app.pid > 0 && app.pid != MY_PID) { 21332 app.kill("empty", false); 21333 } else { 21334 try { 21335 app.thread.scheduleExit(); 21336 } catch (Exception e) { 21337 // Ignore exceptions. 21338 } 21339 } 21340 cleanUpApplicationRecordLocked(app, false, true, -1, false /*replacingPid*/); 21341 mRemovedProcesses.remove(i); 21342 21343 if (app.persistent) { 21344 addAppLocked(app.info, false, null /* ABI override */); 21345 } 21346 } 21347 } 21348 21349 // Now update the oom adj for all processes. 21350 updateOomAdjLocked(); 21351 } 21352 } 21353 21354 /** This method sends the specified signal to each of the persistent apps */ 21355 public void signalPersistentProcesses(int sig) throws RemoteException { 21356 if (sig != Process.SIGNAL_USR1) { 21357 throw new SecurityException("Only SIGNAL_USR1 is allowed"); 21358 } 21359 21360 synchronized (this) { 21361 if (checkCallingPermission(android.Manifest.permission.SIGNAL_PERSISTENT_PROCESSES) 21362 != PackageManager.PERMISSION_GRANTED) { 21363 throw new SecurityException("Requires permission " 21364 + android.Manifest.permission.SIGNAL_PERSISTENT_PROCESSES); 21365 } 21366 21367 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 21368 ProcessRecord r = mLruProcesses.get(i); 21369 if (r.thread != null && r.persistent) { 21370 Process.sendSignal(r.pid, sig); 21371 } 21372 } 21373 } 21374 } 21375 21376 private void stopProfilerLocked(ProcessRecord proc, int profileType) { 21377 if (proc == null || proc == mProfileProc) { 21378 proc = mProfileProc; 21379 profileType = mProfileType; 21380 clearProfilerLocked(); 21381 } 21382 if (proc == null) { 21383 return; 21384 } 21385 try { 21386 proc.thread.profilerControl(false, null, profileType); 21387 } catch (RemoteException e) { 21388 throw new IllegalStateException("Process disappeared"); 21389 } 21390 } 21391 21392 private void clearProfilerLocked() { 21393 if (mProfileFd != null) { 21394 try { 21395 mProfileFd.close(); 21396 } catch (IOException e) { 21397 } 21398 } 21399 mProfileApp = null; 21400 mProfileProc = null; 21401 mProfileFile = null; 21402 mProfileType = 0; 21403 mAutoStopProfiler = false; 21404 mSamplingInterval = 0; 21405 } 21406 21407 public boolean profileControl(String process, int userId, boolean start, 21408 ProfilerInfo profilerInfo, int profileType) throws RemoteException { 21409 21410 try { 21411 synchronized (this) { 21412 // note: hijacking SET_ACTIVITY_WATCHER, but should be changed to 21413 // its own permission. 21414 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 21415 != PackageManager.PERMISSION_GRANTED) { 21416 throw new SecurityException("Requires permission " 21417 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 21418 } 21419 21420 if (start && (profilerInfo == null || profilerInfo.profileFd == null)) { 21421 throw new IllegalArgumentException("null profile info or fd"); 21422 } 21423 21424 ProcessRecord proc = null; 21425 if (process != null) { 21426 proc = findProcessLocked(process, userId, "profileControl"); 21427 } 21428 21429 if (start && (proc == null || proc.thread == null)) { 21430 throw new IllegalArgumentException("Unknown process: " + process); 21431 } 21432 21433 if (start) { 21434 stopProfilerLocked(null, 0); 21435 setProfileApp(proc.info, proc.processName, profilerInfo); 21436 mProfileProc = proc; 21437 mProfileType = profileType; 21438 ParcelFileDescriptor fd = profilerInfo.profileFd; 21439 try { 21440 fd = fd.dup(); 21441 } catch (IOException e) { 21442 fd = null; 21443 } 21444 profilerInfo.profileFd = fd; 21445 proc.thread.profilerControl(start, profilerInfo, profileType); 21446 fd = null; 21447 mProfileFd = null; 21448 } else { 21449 stopProfilerLocked(proc, profileType); 21450 if (profilerInfo != null && profilerInfo.profileFd != null) { 21451 try { 21452 profilerInfo.profileFd.close(); 21453 } catch (IOException e) { 21454 } 21455 } 21456 } 21457 21458 return true; 21459 } 21460 } catch (RemoteException e) { 21461 throw new IllegalStateException("Process disappeared"); 21462 } finally { 21463 if (profilerInfo != null && profilerInfo.profileFd != null) { 21464 try { 21465 profilerInfo.profileFd.close(); 21466 } catch (IOException e) { 21467 } 21468 } 21469 } 21470 } 21471 21472 private ProcessRecord findProcessLocked(String process, int userId, String callName) { 21473 userId = mUserController.handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 21474 userId, true, ALLOW_FULL_ONLY, callName, null); 21475 ProcessRecord proc = null; 21476 try { 21477 int pid = Integer.parseInt(process); 21478 synchronized (mPidsSelfLocked) { 21479 proc = mPidsSelfLocked.get(pid); 21480 } 21481 } catch (NumberFormatException e) { 21482 } 21483 21484 if (proc == null) { 21485 ArrayMap<String, SparseArray<ProcessRecord>> all 21486 = mProcessNames.getMap(); 21487 SparseArray<ProcessRecord> procs = all.get(process); 21488 if (procs != null && procs.size() > 0) { 21489 proc = procs.valueAt(0); 21490 if (userId != UserHandle.USER_ALL && proc.userId != userId) { 21491 for (int i=1; i<procs.size(); i++) { 21492 ProcessRecord thisProc = procs.valueAt(i); 21493 if (thisProc.userId == userId) { 21494 proc = thisProc; 21495 break; 21496 } 21497 } 21498 } 21499 } 21500 } 21501 21502 return proc; 21503 } 21504 21505 public boolean dumpHeap(String process, int userId, boolean managed, 21506 String path, ParcelFileDescriptor fd) throws RemoteException { 21507 21508 try { 21509 synchronized (this) { 21510 // note: hijacking SET_ACTIVITY_WATCHER, but should be changed to 21511 // its own permission (same as profileControl). 21512 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 21513 != PackageManager.PERMISSION_GRANTED) { 21514 throw new SecurityException("Requires permission " 21515 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 21516 } 21517 21518 if (fd == null) { 21519 throw new IllegalArgumentException("null fd"); 21520 } 21521 21522 ProcessRecord proc = findProcessLocked(process, userId, "dumpHeap"); 21523 if (proc == null || proc.thread == null) { 21524 throw new IllegalArgumentException("Unknown process: " + process); 21525 } 21526 21527 boolean isDebuggable = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 21528 if (!isDebuggable) { 21529 if ((proc.info.flags&ApplicationInfo.FLAG_DEBUGGABLE) == 0) { 21530 throw new SecurityException("Process not debuggable: " + proc); 21531 } 21532 } 21533 21534 proc.thread.dumpHeap(managed, path, fd); 21535 fd = null; 21536 return true; 21537 } 21538 } catch (RemoteException e) { 21539 throw new IllegalStateException("Process disappeared"); 21540 } finally { 21541 if (fd != null) { 21542 try { 21543 fd.close(); 21544 } catch (IOException e) { 21545 } 21546 } 21547 } 21548 } 21549 21550 @Override 21551 public void setDumpHeapDebugLimit(String processName, int uid, long maxMemSize, 21552 String reportPackage) { 21553 if (processName != null) { 21554 enforceCallingPermission(android.Manifest.permission.SET_DEBUG_APP, 21555 "setDumpHeapDebugLimit()"); 21556 } else { 21557 synchronized (mPidsSelfLocked) { 21558 ProcessRecord proc = mPidsSelfLocked.get(Binder.getCallingPid()); 21559 if (proc == null) { 21560 throw new SecurityException("No process found for calling pid " 21561 + Binder.getCallingPid()); 21562 } 21563 if (!Build.IS_DEBUGGABLE 21564 && (proc.info.flags&ApplicationInfo.FLAG_DEBUGGABLE) == 0) { 21565 throw new SecurityException("Not running a debuggable build"); 21566 } 21567 processName = proc.processName; 21568 uid = proc.uid; 21569 if (reportPackage != null && !proc.pkgList.containsKey(reportPackage)) { 21570 throw new SecurityException("Package " + reportPackage + " is not running in " 21571 + proc); 21572 } 21573 } 21574 } 21575 synchronized (this) { 21576 if (maxMemSize > 0) { 21577 mMemWatchProcesses.put(processName, uid, new Pair(maxMemSize, reportPackage)); 21578 } else { 21579 if (uid != 0) { 21580 mMemWatchProcesses.remove(processName, uid); 21581 } else { 21582 mMemWatchProcesses.getMap().remove(processName); 21583 } 21584 } 21585 } 21586 } 21587 21588 @Override 21589 public void dumpHeapFinished(String path) { 21590 synchronized (this) { 21591 if (Binder.getCallingPid() != mMemWatchDumpPid) { 21592 Slog.w(TAG, "dumpHeapFinished: Calling pid " + Binder.getCallingPid() 21593 + " does not match last pid " + mMemWatchDumpPid); 21594 return; 21595 } 21596 if (mMemWatchDumpFile == null || !mMemWatchDumpFile.equals(path)) { 21597 Slog.w(TAG, "dumpHeapFinished: Calling path " + path 21598 + " does not match last path " + mMemWatchDumpFile); 21599 return; 21600 } 21601 if (DEBUG_PSS) Slog.d(TAG_PSS, "Dump heap finished for " + path); 21602 mHandler.sendEmptyMessage(POST_DUMP_HEAP_NOTIFICATION_MSG); 21603 } 21604 } 21605 21606 /** In this method we try to acquire our lock to make sure that we have not deadlocked */ 21607 public void monitor() { 21608 synchronized (this) { } 21609 } 21610 21611 void onCoreSettingsChange(Bundle settings) { 21612 for (int i = mLruProcesses.size() - 1; i >= 0; i--) { 21613 ProcessRecord processRecord = mLruProcesses.get(i); 21614 try { 21615 if (processRecord.thread != null) { 21616 processRecord.thread.setCoreSettings(settings); 21617 } 21618 } catch (RemoteException re) { 21619 /* ignore */ 21620 } 21621 } 21622 } 21623 21624 // Multi-user methods 21625 21626 /** 21627 * Start user, if its not already running, but don't bring it to foreground. 21628 */ 21629 @Override 21630 public boolean startUserInBackground(final int userId) { 21631 return mUserController.startUser(userId, /* foreground */ false); 21632 } 21633 21634 @Override 21635 public boolean unlockUser(int userId, byte[] token, byte[] secret, IProgressListener listener) { 21636 return mUserController.unlockUser(userId, token, secret, listener); 21637 } 21638 21639 @Override 21640 public boolean switchUser(final int targetUserId) { 21641 enforceShellRestriction(UserManager.DISALLOW_DEBUGGING_FEATURES, targetUserId); 21642 int currentUserId; 21643 UserInfo targetUserInfo; 21644 synchronized (this) { 21645 currentUserId = mUserController.getCurrentUserIdLocked(); 21646 targetUserInfo = mUserController.getUserInfo(targetUserId); 21647 if (targetUserId == currentUserId) { 21648 Slog.i(TAG, "user #" + targetUserId + " is already the current user"); 21649 return true; 21650 } 21651 if (targetUserInfo == null) { 21652 Slog.w(TAG, "No user info for user #" + targetUserId); 21653 return false; 21654 } 21655 if (!targetUserInfo.isDemo() && UserManager.isDeviceInDemoMode(mContext)) { 21656 Slog.w(TAG, "Cannot switch to non-demo user #" + targetUserId 21657 + " when device is in demo mode"); 21658 return false; 21659 } 21660 if (!targetUserInfo.supportsSwitchTo()) { 21661 Slog.w(TAG, "Cannot switch to User #" + targetUserId + ": not supported"); 21662 return false; 21663 } 21664 if (targetUserInfo.isManagedProfile()) { 21665 Slog.w(TAG, "Cannot switch to User #" + targetUserId + ": not a full user"); 21666 return false; 21667 } 21668 mUserController.setTargetUserIdLocked(targetUserId); 21669 } 21670 if (mUserController.mUserSwitchUiEnabled) { 21671 UserInfo currentUserInfo = mUserController.getUserInfo(currentUserId); 21672 Pair<UserInfo, UserInfo> userNames = new Pair<>(currentUserInfo, targetUserInfo); 21673 mUiHandler.removeMessages(START_USER_SWITCH_UI_MSG); 21674 mUiHandler.sendMessage(mHandler.obtainMessage( 21675 START_USER_SWITCH_UI_MSG, userNames)); 21676 } else { 21677 mHandler.removeMessages(START_USER_SWITCH_FG_MSG); 21678 mHandler.sendMessage(mHandler.obtainMessage( 21679 START_USER_SWITCH_FG_MSG, targetUserId, 0)); 21680 } 21681 return true; 21682 } 21683 21684 void scheduleStartProfilesLocked() { 21685 if (!mHandler.hasMessages(START_PROFILES_MSG)) { 21686 mHandler.sendMessageDelayed(mHandler.obtainMessage(START_PROFILES_MSG), 21687 DateUtils.SECOND_IN_MILLIS); 21688 } 21689 } 21690 21691 @Override 21692 public int stopUser(final int userId, boolean force, final IStopUserCallback callback) { 21693 return mUserController.stopUser(userId, force, callback); 21694 } 21695 21696 @Override 21697 public UserInfo getCurrentUser() { 21698 return mUserController.getCurrentUser(); 21699 } 21700 21701 String getStartedUserState(int userId) { 21702 synchronized (this) { 21703 final UserState userState = mUserController.getStartedUserStateLocked(userId); 21704 return UserState.stateToString(userState.state); 21705 } 21706 } 21707 21708 @Override 21709 public boolean isUserRunning(int userId, int flags) { 21710 if (!mUserController.isSameProfileGroup(userId, UserHandle.getCallingUserId()) 21711 && checkCallingPermission(INTERACT_ACROSS_USERS) 21712 != PackageManager.PERMISSION_GRANTED) { 21713 String msg = "Permission Denial: isUserRunning() from pid=" 21714 + Binder.getCallingPid() 21715 + ", uid=" + Binder.getCallingUid() 21716 + " requires " + INTERACT_ACROSS_USERS; 21717 Slog.w(TAG, msg); 21718 throw new SecurityException(msg); 21719 } 21720 synchronized (this) { 21721 return mUserController.isUserRunningLocked(userId, flags); 21722 } 21723 } 21724 21725 @Override 21726 public int[] getRunningUserIds() { 21727 if (checkCallingPermission(INTERACT_ACROSS_USERS) 21728 != PackageManager.PERMISSION_GRANTED) { 21729 String msg = "Permission Denial: isUserRunning() from pid=" 21730 + Binder.getCallingPid() 21731 + ", uid=" + Binder.getCallingUid() 21732 + " requires " + INTERACT_ACROSS_USERS; 21733 Slog.w(TAG, msg); 21734 throw new SecurityException(msg); 21735 } 21736 synchronized (this) { 21737 return mUserController.getStartedUserArrayLocked(); 21738 } 21739 } 21740 21741 @Override 21742 public void registerUserSwitchObserver(IUserSwitchObserver observer, String name) { 21743 mUserController.registerUserSwitchObserver(observer, name); 21744 } 21745 21746 @Override 21747 public void unregisterUserSwitchObserver(IUserSwitchObserver observer) { 21748 mUserController.unregisterUserSwitchObserver(observer); 21749 } 21750 21751 ApplicationInfo getAppInfoForUser(ApplicationInfo info, int userId) { 21752 if (info == null) return null; 21753 ApplicationInfo newInfo = new ApplicationInfo(info); 21754 newInfo.initForUser(userId); 21755 return newInfo; 21756 } 21757 21758 public boolean isUserStopped(int userId) { 21759 synchronized (this) { 21760 return mUserController.getStartedUserStateLocked(userId) == null; 21761 } 21762 } 21763 21764 ActivityInfo getActivityInfoForUser(ActivityInfo aInfo, int userId) { 21765 if (aInfo == null 21766 || (userId < 1 && aInfo.applicationInfo.uid < UserHandle.PER_USER_RANGE)) { 21767 return aInfo; 21768 } 21769 21770 ActivityInfo info = new ActivityInfo(aInfo); 21771 info.applicationInfo = getAppInfoForUser(info.applicationInfo, userId); 21772 return info; 21773 } 21774 21775 private boolean processSanityChecksLocked(ProcessRecord process) { 21776 if (process == null || process.thread == null) { 21777 return false; 21778 } 21779 21780 boolean isDebuggable = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 21781 if (!isDebuggable) { 21782 if ((process.info.flags&ApplicationInfo.FLAG_DEBUGGABLE) == 0) { 21783 return false; 21784 } 21785 } 21786 21787 return true; 21788 } 21789 21790 public boolean startBinderTracking() throws RemoteException { 21791 synchronized (this) { 21792 mBinderTransactionTrackingEnabled = true; 21793 // TODO: hijacking SET_ACTIVITY_WATCHER, but should be changed to its own 21794 // permission (same as profileControl). 21795 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 21796 != PackageManager.PERMISSION_GRANTED) { 21797 throw new SecurityException("Requires permission " 21798 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 21799 } 21800 21801 for (int i = 0; i < mLruProcesses.size(); i++) { 21802 ProcessRecord process = mLruProcesses.get(i); 21803 if (!processSanityChecksLocked(process)) { 21804 continue; 21805 } 21806 try { 21807 process.thread.startBinderTracking(); 21808 } catch (RemoteException e) { 21809 Log.v(TAG, "Process disappared"); 21810 } 21811 } 21812 return true; 21813 } 21814 } 21815 21816 public boolean stopBinderTrackingAndDump(ParcelFileDescriptor fd) throws RemoteException { 21817 try { 21818 synchronized (this) { 21819 mBinderTransactionTrackingEnabled = false; 21820 // TODO: hijacking SET_ACTIVITY_WATCHER, but should be changed to its own 21821 // permission (same as profileControl). 21822 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 21823 != PackageManager.PERMISSION_GRANTED) { 21824 throw new SecurityException("Requires permission " 21825 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 21826 } 21827 21828 if (fd == null) { 21829 throw new IllegalArgumentException("null fd"); 21830 } 21831 21832 PrintWriter pw = new FastPrintWriter(new FileOutputStream(fd.getFileDescriptor())); 21833 pw.println("Binder transaction traces for all processes.\n"); 21834 for (ProcessRecord process : mLruProcesses) { 21835 if (!processSanityChecksLocked(process)) { 21836 continue; 21837 } 21838 21839 pw.println("Traces for process: " + process.processName); 21840 pw.flush(); 21841 try { 21842 TransferPipe tp = new TransferPipe(); 21843 try { 21844 process.thread.stopBinderTrackingAndDump(tp.getWriteFd()); 21845 tp.go(fd.getFileDescriptor()); 21846 } finally { 21847 tp.kill(); 21848 } 21849 } catch (IOException e) { 21850 pw.println("Failure while dumping IPC traces from " + process + 21851 ". Exception: " + e); 21852 pw.flush(); 21853 } catch (RemoteException e) { 21854 pw.println("Got a RemoteException while dumping IPC traces from " + 21855 process + ". Exception: " + e); 21856 pw.flush(); 21857 } 21858 } 21859 fd = null; 21860 return true; 21861 } 21862 } finally { 21863 if (fd != null) { 21864 try { 21865 fd.close(); 21866 } catch (IOException e) { 21867 } 21868 } 21869 } 21870 } 21871 21872 private final class LocalService extends ActivityManagerInternal { 21873 @Override 21874 public void onWakefulnessChanged(int wakefulness) { 21875 ActivityManagerService.this.onWakefulnessChanged(wakefulness); 21876 } 21877 21878 @Override 21879 public int startIsolatedProcess(String entryPoint, String[] entryPointArgs, 21880 String processName, String abiOverride, int uid, Runnable crashHandler) { 21881 return ActivityManagerService.this.startIsolatedProcess(entryPoint, entryPointArgs, 21882 processName, abiOverride, uid, crashHandler); 21883 } 21884 21885 @Override 21886 public SleepToken acquireSleepToken(String tag) { 21887 Preconditions.checkNotNull(tag); 21888 21889 ComponentName requestedVrService = null; 21890 ComponentName callingVrActivity = null; 21891 int userId = -1; 21892 synchronized (ActivityManagerService.this) { 21893 final ActivityRecord resumedActivity = mStackSupervisor.getResumedActivityLocked(); 21894 if (resumedActivity != null) { 21895 requestedVrService = resumedActivity.requestedVrComponent; 21896 callingVrActivity = resumedActivity.info.getComponentName(); 21897 userId = resumedActivity.userId; 21898 } 21899 } 21900 21901 if (requestedVrService != null) { 21902 applyVrMode(false, requestedVrService, userId, callingVrActivity, true); 21903 } 21904 21905 synchronized (ActivityManagerService.this) { 21906 SleepTokenImpl token = new SleepTokenImpl(tag); 21907 mSleepTokens.add(token); 21908 updateSleepIfNeededLocked(); 21909 return token; 21910 } 21911 } 21912 21913 @Override 21914 public ComponentName getHomeActivityForUser(int userId) { 21915 synchronized (ActivityManagerService.this) { 21916 ActivityRecord homeActivity = mStackSupervisor.getHomeActivityForUser(userId); 21917 return homeActivity == null ? null : homeActivity.realActivity; 21918 } 21919 } 21920 21921 @Override 21922 public void onUserRemoved(int userId) { 21923 synchronized (ActivityManagerService.this) { 21924 ActivityManagerService.this.onUserStoppedLocked(userId); 21925 } 21926 } 21927 21928 @Override 21929 public void onLocalVoiceInteractionStarted(IBinder activity, 21930 IVoiceInteractionSession voiceSession, IVoiceInteractor voiceInteractor) { 21931 synchronized (ActivityManagerService.this) { 21932 ActivityManagerService.this.onLocalVoiceInteractionStartedLocked(activity, 21933 voiceSession, voiceInteractor); 21934 } 21935 } 21936 21937 @Override 21938 public void notifyStartingWindowDrawn() { 21939 synchronized (ActivityManagerService.this) { 21940 mStackSupervisor.mActivityMetricsLogger.notifyStartingWindowDrawn(); 21941 } 21942 } 21943 21944 @Override 21945 public void notifyAppTransitionStarting(int reason) { 21946 synchronized (ActivityManagerService.this) { 21947 mStackSupervisor.mActivityMetricsLogger.notifyTransitionStarting(reason); 21948 } 21949 } 21950 21951 @Override 21952 public void notifyAppTransitionFinished() { 21953 synchronized (ActivityManagerService.this) { 21954 mStackSupervisor.notifyAppTransitionDone(); 21955 } 21956 } 21957 21958 @Override 21959 public void notifyAppTransitionCancelled() { 21960 synchronized (ActivityManagerService.this) { 21961 mStackSupervisor.notifyAppTransitionDone(); 21962 } 21963 } 21964 21965 @Override 21966 public List<IBinder> getTopVisibleActivities() { 21967 synchronized (ActivityManagerService.this) { 21968 return mStackSupervisor.getTopVisibleActivities(); 21969 } 21970 } 21971 21972 @Override 21973 public void notifyDockedStackMinimizedChanged(boolean minimized) { 21974 synchronized (ActivityManagerService.this) { 21975 mStackSupervisor.setDockedStackMinimized(minimized); 21976 } 21977 } 21978 21979 @Override 21980 public void killForegroundAppsForUser(int userHandle) { 21981 synchronized (ActivityManagerService.this) { 21982 final ArrayList<ProcessRecord> procs = new ArrayList<>(); 21983 final int NP = mProcessNames.getMap().size(); 21984 for (int ip = 0; ip < NP; ip++) { 21985 final SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 21986 final int NA = apps.size(); 21987 for (int ia = 0; ia < NA; ia++) { 21988 final ProcessRecord app = apps.valueAt(ia); 21989 if (app.persistent) { 21990 // We don't kill persistent processes. 21991 continue; 21992 } 21993 if (app.removed) { 21994 procs.add(app); 21995 } else if (app.userId == userHandle && app.foregroundActivities) { 21996 app.removed = true; 21997 procs.add(app); 21998 } 21999 } 22000 } 22001 22002 final int N = procs.size(); 22003 for (int i = 0; i < N; i++) { 22004 removeProcessLocked(procs.get(i), false, true, "kill all fg"); 22005 } 22006 } 22007 } 22008 22009 @Override 22010 public void setPendingIntentWhitelistDuration(IIntentSender target, long duration) { 22011 if (!(target instanceof PendingIntentRecord)) { 22012 Slog.w(TAG, "markAsSentFromNotification(): not a PendingIntentRecord: " + target); 22013 return; 22014 } 22015 ((PendingIntentRecord) target).setWhitelistDuration(duration); 22016 } 22017 22018 @Override 22019 public void updatePersistentConfigurationForUser(@NonNull Configuration values, 22020 int userId) { 22021 Preconditions.checkNotNull(values, "Configuration must not be null"); 22022 Preconditions.checkArgumentNonnegative(userId, "userId " + userId + " not supported"); 22023 synchronized (ActivityManagerService.this) { 22024 updateConfigurationLocked(values, null, false, true, userId, 22025 false /* deferResume */); 22026 } 22027 } 22028 22029 @Override 22030 public int startActivitiesAsPackage(String packageName, int userId, Intent[] intents, 22031 Bundle bOptions) { 22032 Preconditions.checkNotNull(intents, "intents"); 22033 final String[] resolvedTypes = new String[intents.length]; 22034 for (int i = 0; i < intents.length; i++) { 22035 resolvedTypes[i] = intents[i].resolveTypeIfNeeded(mContext.getContentResolver()); 22036 } 22037 22038 // UID of the package on user userId. 22039 // "= 0" is needed because otherwise catch(RemoteException) would make it look like 22040 // packageUid may not be initialized. 22041 int packageUid = 0; 22042 try { 22043 packageUid = AppGlobals.getPackageManager().getPackageUid( 22044 packageName, PackageManager.MATCH_DEBUG_TRIAGED_MISSING, userId); 22045 } catch (RemoteException e) { 22046 // Shouldn't happen. 22047 } 22048 22049 synchronized (ActivityManagerService.this) { 22050 return startActivitiesInPackage(packageUid, packageName, intents, resolvedTypes, 22051 /*resultTo*/ null, bOptions, userId); 22052 } 22053 } 22054 22055 @Override 22056 public int getUidProcessState(int uid) { 22057 return getUidState(uid); 22058 } 22059 22060 @Override 22061 public void notifyKeyguardFlagsChanged(@Nullable Runnable callback) { 22062 synchronized (ActivityManagerService.this) { 22063 22064 // We might change the visibilities here, so prepare an empty app transition which 22065 // might be overridden later if we actually change visibilities. 22066 mWindowManager.prepareAppTransition(TRANSIT_NONE, false /* alwaysKeepCurrent */); 22067 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0, !PRESERVE_WINDOWS); 22068 mWindowManager.executeAppTransition(); 22069 } 22070 if (callback != null) { 22071 callback.run(); 22072 } 22073 } 22074 22075 @Override 22076 public boolean isSystemReady() { 22077 // no need to synchronize(this) just to read & return the value 22078 return mSystemReady; 22079 } 22080 22081 @Override 22082 public void notifyKeyguardTrustedChanged() { 22083 synchronized (ActivityManagerService.this) { 22084 if (mKeyguardController.isKeyguardShowing()) { 22085 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0, !PRESERVE_WINDOWS); 22086 } 22087 } 22088 } 22089 } 22090 22091 private final class SleepTokenImpl extends SleepToken { 22092 private final String mTag; 22093 private final long mAcquireTime; 22094 22095 public SleepTokenImpl(String tag) { 22096 mTag = tag; 22097 mAcquireTime = SystemClock.uptimeMillis(); 22098 } 22099 22100 @Override 22101 public void release() { 22102 synchronized (ActivityManagerService.this) { 22103 if (mSleepTokens.remove(this)) { 22104 updateSleepIfNeededLocked(); 22105 } 22106 } 22107 } 22108 22109 @Override 22110 public String toString() { 22111 return "{\"" + mTag + "\", acquire at " + TimeUtils.formatUptime(mAcquireTime) + "}"; 22112 } 22113 } 22114 22115 /** 22116 * An implementation of IAppTask, that allows an app to manage its own tasks via 22117 * {@link android.app.ActivityManager.AppTask}. We keep track of the callingUid to ensure that 22118 * only the process that calls getAppTasks() can call the AppTask methods. 22119 */ 22120 class AppTaskImpl extends IAppTask.Stub { 22121 private int mTaskId; 22122 private int mCallingUid; 22123 22124 public AppTaskImpl(int taskId, int callingUid) { 22125 mTaskId = taskId; 22126 mCallingUid = callingUid; 22127 } 22128 22129 private void checkCaller() { 22130 if (mCallingUid != Binder.getCallingUid()) { 22131 throw new SecurityException("Caller " + mCallingUid 22132 + " does not match caller of getAppTasks(): " + Binder.getCallingUid()); 22133 } 22134 } 22135 22136 @Override 22137 public void finishAndRemoveTask() { 22138 checkCaller(); 22139 22140 synchronized (ActivityManagerService.this) { 22141 long origId = Binder.clearCallingIdentity(); 22142 try { 22143 // We remove the task from recents to preserve backwards 22144 if (!removeTaskByIdLocked(mTaskId, false, REMOVE_FROM_RECENTS)) { 22145 throw new IllegalArgumentException("Unable to find task ID " + mTaskId); 22146 } 22147 } finally { 22148 Binder.restoreCallingIdentity(origId); 22149 } 22150 } 22151 } 22152 22153 @Override 22154 public ActivityManager.RecentTaskInfo getTaskInfo() { 22155 checkCaller(); 22156 22157 synchronized (ActivityManagerService.this) { 22158 long origId = Binder.clearCallingIdentity(); 22159 try { 22160 TaskRecord tr = mStackSupervisor.anyTaskForIdLocked(mTaskId); 22161 if (tr == null) { 22162 throw new IllegalArgumentException("Unable to find task ID " + mTaskId); 22163 } 22164 return createRecentTaskInfoFromTaskRecord(tr); 22165 } finally { 22166 Binder.restoreCallingIdentity(origId); 22167 } 22168 } 22169 } 22170 22171 @Override 22172 public void moveToFront() { 22173 checkCaller(); 22174 // Will bring task to front if it already has a root activity. 22175 final long origId = Binder.clearCallingIdentity(); 22176 try { 22177 synchronized (this) { 22178 mStackSupervisor.startActivityFromRecentsInner(mTaskId, null); 22179 } 22180 } finally { 22181 Binder.restoreCallingIdentity(origId); 22182 } 22183 } 22184 22185 @Override 22186 public int startActivity(IBinder whoThread, String callingPackage, 22187 Intent intent, String resolvedType, Bundle bOptions) { 22188 checkCaller(); 22189 22190 int callingUser = UserHandle.getCallingUserId(); 22191 TaskRecord tr; 22192 IApplicationThread appThread; 22193 synchronized (ActivityManagerService.this) { 22194 tr = mStackSupervisor.anyTaskForIdLocked(mTaskId); 22195 if (tr == null) { 22196 throw new IllegalArgumentException("Unable to find task ID " + mTaskId); 22197 } 22198 appThread = IApplicationThread.Stub.asInterface(whoThread); 22199 if (appThread == null) { 22200 throw new IllegalArgumentException("Bad app thread " + appThread); 22201 } 22202 } 22203 return mActivityStarter.startActivityMayWait(appThread, -1, callingPackage, intent, 22204 resolvedType, null, null, null, null, 0, 0, null, null, 22205 null, bOptions, false, callingUser, null, tr); 22206 } 22207 22208 @Override 22209 public void setExcludeFromRecents(boolean exclude) { 22210 checkCaller(); 22211 22212 synchronized (ActivityManagerService.this) { 22213 long origId = Binder.clearCallingIdentity(); 22214 try { 22215 TaskRecord tr = mStackSupervisor.anyTaskForIdLocked(mTaskId); 22216 if (tr == null) { 22217 throw new IllegalArgumentException("Unable to find task ID " + mTaskId); 22218 } 22219 Intent intent = tr.getBaseIntent(); 22220 if (exclude) { 22221 intent.addFlags(Intent.FLAG_ACTIVITY_EXCLUDE_FROM_RECENTS); 22222 } else { 22223 intent.setFlags(intent.getFlags() 22224 & ~Intent.FLAG_ACTIVITY_EXCLUDE_FROM_RECENTS); 22225 } 22226 } finally { 22227 Binder.restoreCallingIdentity(origId); 22228 } 22229 } 22230 } 22231 } 22232 22233 /** 22234 * Kill processes for the user with id userId and that depend on the package named packageName 22235 */ 22236 @Override 22237 public void killPackageDependents(String packageName, int userId) { 22238 enforceCallingPermission(android.Manifest.permission.KILL_UID, "killPackageDependents()"); 22239 if (packageName == null) { 22240 throw new NullPointerException( 22241 "Cannot kill the dependents of a package without its name."); 22242 } 22243 22244 long callingId = Binder.clearCallingIdentity(); 22245 IPackageManager pm = AppGlobals.getPackageManager(); 22246 int pkgUid = -1; 22247 try { 22248 pkgUid = pm.getPackageUid(packageName, MATCH_DEBUG_TRIAGED_MISSING, userId); 22249 } catch (RemoteException e) { 22250 } 22251 if (userId != UserHandle.USER_ALL && pkgUid == -1) { 22252 throw new IllegalArgumentException( 22253 "Cannot kill dependents of non-existing package " + packageName); 22254 } 22255 try { 22256 synchronized(this) { 22257 killPackageProcessesLocked(packageName, UserHandle.getAppId(pkgUid), userId, 22258 ProcessList.FOREGROUND_APP_ADJ, false, true, true, false, 22259 "dep: " + packageName); 22260 } 22261 } finally { 22262 Binder.restoreCallingIdentity(callingId); 22263 } 22264 } 22265 22266 @Override 22267 public boolean canBypassWorkChallenge(PendingIntent intent) throws RemoteException { 22268 final int userId = intent.getCreatorUserHandle().getIdentifier(); 22269 if (!mUserController.isUserRunningLocked(userId, ActivityManager.FLAG_AND_LOCKED)) { 22270 return false; 22271 } 22272 IIntentSender target = intent.getTarget(); 22273 if (!(target instanceof PendingIntentRecord)) { 22274 return false; 22275 } 22276 final PendingIntentRecord record = (PendingIntentRecord) target; 22277 final ResolveInfo rInfo = mStackSupervisor.resolveIntent(record.key.requestIntent, 22278 record.key.requestResolvedType, userId, PackageManager.MATCH_DIRECT_BOOT_AWARE); 22279 // For direct boot aware activities, they can be shown without triggering a work challenge 22280 // before the profile user is unlocked. 22281 return rInfo != null && rInfo.activityInfo != null; 22282 } 22283 22284 /** 22285 * Attach an agent to the specified process (proces name or PID) 22286 */ 22287 public void attachAgent(String process, String path) { 22288 try { 22289 synchronized (this) { 22290 ProcessRecord proc = findProcessLocked(process, UserHandle.USER_SYSTEM, "attachAgent"); 22291 if (proc == null || proc.thread == null) { 22292 throw new IllegalArgumentException("Unknown process: " + process); 22293 } 22294 22295 boolean isDebuggable = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 22296 if (!isDebuggable) { 22297 if ((proc.info.flags & ApplicationInfo.FLAG_DEBUGGABLE) == 0) { 22298 throw new SecurityException("Process not debuggable: " + proc); 22299 } 22300 } 22301 22302 proc.thread.attachAgent(path); 22303 } 22304 } catch (RemoteException e) { 22305 throw new IllegalStateException("Process disappeared"); 22306 } 22307 } 22308} 22309