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 17 package com.android.server.am; 18 19 import static android.Manifest.permission.BIND_VOICE_INTERACTION; 20 import static android.Manifest.permission.CHANGE_CONFIGURATION; 21 import static android.Manifest.permission.CHANGE_DEVICE_IDLE_TEMP_WHITELIST; 22 import static android.Manifest.permission.CONTROL_REMOTE_APP_TRANSITION_ANIMATIONS; 23 import static android.Manifest.permission.INTERACT_ACROSS_USERS; 24 import static android.Manifest.permission.INTERACT_ACROSS_USERS_FULL; 25 import static android.Manifest.permission.INTERNAL_SYSTEM_WINDOW; 26 import static android.Manifest.permission.MANAGE_ACTIVITY_STACKS; 27 import static android.Manifest.permission.READ_FRAME_BUFFER; 28 import static android.Manifest.permission.REMOVE_TASKS; 29 import static android.Manifest.permission.START_TASKS_FROM_RECENTS; 30 import static android.Manifest.permission.STOP_APP_SWITCHES; 31 import static android.app.ActivityManager.LOCK_TASK_MODE_NONE; 32 import static android.app.ActivityManager.RESIZE_MODE_PRESERVE_WINDOW; 33 import static android.app.ActivityManager.SPLIT_SCREEN_CREATE_MODE_TOP_OR_LEFT; 34 import static android.app.ActivityManager.StackId.INVALID_STACK_ID; 35 import static android.app.ActivityManagerInternal.ASSIST_KEY_CONTENT; 36 import static android.app.ActivityManagerInternal.ASSIST_KEY_DATA; 37 import static android.app.ActivityManagerInternal.ASSIST_KEY_RECEIVER_EXTRAS; 38 import static android.app.ActivityManagerInternal.ASSIST_KEY_STRUCTURE; 39 import static android.app.ActivityThread.PROC_START_SEQ_IDENT; 40 import static android.app.AppOpsManager.OP_NONE; 41 import static android.app.WindowConfiguration.ACTIVITY_TYPE_STANDARD; 42 import static android.app.WindowConfiguration.ACTIVITY_TYPE_UNDEFINED; 43 import static android.app.WindowConfiguration.WINDOWING_MODE_FREEFORM; 44 import static android.app.WindowConfiguration.WINDOWING_MODE_FULLSCREEN; 45 import static android.app.WindowConfiguration.WINDOWING_MODE_FULLSCREEN_OR_SPLIT_SCREEN_SECONDARY; 46 import static android.app.WindowConfiguration.WINDOWING_MODE_PINNED; 47 import static android.app.WindowConfiguration.WINDOWING_MODE_SPLIT_SCREEN_PRIMARY; 48 import static android.app.WindowConfiguration.WINDOWING_MODE_SPLIT_SCREEN_SECONDARY; 49 import static android.app.WindowConfiguration.WINDOWING_MODE_UNDEFINED; 50 import static android.content.Intent.FLAG_ACTIVITY_EXCLUDE_FROM_RECENTS; 51 import static android.content.Intent.FLAG_ACTIVITY_NEW_TASK; 52 import static android.content.Intent.FLAG_ACTIVITY_TASK_ON_HOME; 53 import static android.content.pm.ApplicationInfo.HIDDEN_API_ENFORCEMENT_DEFAULT; 54 import static android.content.pm.PackageManager.FEATURE_ACTIVITIES_ON_SECONDARY_DISPLAYS; 55 import static android.content.pm.PackageManager.FEATURE_FREEFORM_WINDOW_MANAGEMENT; 56 import static android.content.pm.PackageManager.FEATURE_LEANBACK_ONLY; 57 import static android.content.pm.PackageManager.FEATURE_PICTURE_IN_PICTURE; 58 import static android.content.pm.PackageManager.GET_PROVIDERS; 59 import static android.content.pm.PackageManager.MATCH_ANY_USER; 60 import static android.content.pm.PackageManager.MATCH_DEBUG_TRIAGED_MISSING; 61 import static android.content.pm.PackageManager.MATCH_DIRECT_BOOT_AWARE; 62 import static android.content.pm.PackageManager.MATCH_DIRECT_BOOT_UNAWARE; 63 import static android.content.pm.PackageManager.MATCH_SYSTEM_ONLY; 64 import static android.content.pm.PackageManager.MATCH_UNINSTALLED_PACKAGES; 65 import static android.content.pm.PackageManager.PERMISSION_GRANTED; 66 import static android.content.res.Configuration.UI_MODE_TYPE_TELEVISION; 67 import static android.net.NetworkPolicyManager.isProcStateAllowedWhileIdleOrPowerSaveMode; 68 import static android.net.NetworkPolicyManager.isProcStateAllowedWhileOnRestrictBackground; 69 import static android.os.Build.VERSION_CODES.N; 70 import static android.os.IServiceManager.DUMP_FLAG_PRIORITY_CRITICAL; 71 import static android.os.IServiceManager.DUMP_FLAG_PRIORITY_HIGH; 72 import static android.os.IServiceManager.DUMP_FLAG_PRIORITY_NORMAL; 73 import static android.os.IServiceManager.DUMP_FLAG_PROTO; 74 import static android.os.Process.BLUETOOTH_UID; 75 import static android.os.Process.FIRST_APPLICATION_UID; 76 import static android.os.Process.FIRST_ISOLATED_UID; 77 import static android.os.Process.LAST_ISOLATED_UID; 78 import static android.os.Process.NFC_UID; 79 import static android.os.Process.PHONE_UID; 80 import static android.os.Process.PROC_CHAR; 81 import static android.os.Process.PROC_OUT_LONG; 82 import static android.os.Process.PROC_PARENS; 83 import static android.os.Process.PROC_SPACE_TERM; 84 import static android.os.Process.ProcessStartResult; 85 import static android.os.Process.ROOT_UID; 86 import static android.os.Process.SCHED_FIFO; 87 import static android.os.Process.SCHED_OTHER; 88 import static android.os.Process.SCHED_RESET_ON_FORK; 89 import static android.os.Process.SE_UID; 90 import static android.os.Process.SHELL_UID; 91 import static android.os.Process.SIGNAL_QUIT; 92 import static android.os.Process.SIGNAL_USR1; 93 import static android.os.Process.SYSTEM_UID; 94 import static android.os.Process.THREAD_GROUP_BG_NONINTERACTIVE; 95 import static android.os.Process.THREAD_GROUP_DEFAULT; 96 import static android.os.Process.THREAD_GROUP_RESTRICTED; 97 import static android.os.Process.THREAD_GROUP_TOP_APP; 98 import static android.os.Process.THREAD_PRIORITY_BACKGROUND; 99 import static android.os.Process.THREAD_PRIORITY_FOREGROUND; 100 import static android.os.Process.getFreeMemory; 101 import static android.os.Process.getTotalMemory; 102 import static android.os.Process.isThreadInProcess; 103 import static android.os.Process.killProcess; 104 import static android.os.Process.killProcessQuiet; 105 import static android.os.Process.myPid; 106 import static android.os.Process.myUid; 107 import static android.os.Process.readProcFile; 108 import static android.os.Process.removeAllProcessGroups; 109 import static android.os.Process.sendSignal; 110 import static android.os.Process.setProcessGroup; 111 import static android.os.Process.setThreadPriority; 112 import static android.os.Process.setThreadScheduler; 113 import static android.os.Process.startWebView; 114 import static android.os.Process.zygoteProcess; 115 import static android.os.Trace.TRACE_TAG_ACTIVITY_MANAGER; 116 import static android.provider.Settings.Global.ALWAYS_FINISH_ACTIVITIES; 117 import static android.provider.Settings.Global.DEBUG_APP; 118 import static android.provider.Settings.Global.DEVELOPMENT_ENABLE_FREEFORM_WINDOWS_SUPPORT; 119 import static android.provider.Settings.Global.DEVELOPMENT_FORCE_RESIZABLE_ACTIVITIES; 120 import static android.provider.Settings.Global.DEVELOPMENT_FORCE_RTL; 121 import static android.provider.Settings.Global.HIDE_ERROR_DIALOGS; 122 import static android.provider.Settings.Global.NETWORK_ACCESS_TIMEOUT_MS; 123 import static android.provider.Settings.Global.WAIT_FOR_DEBUGGER; 124 import static android.provider.Settings.System.FONT_SCALE; 125 import static android.service.voice.VoiceInteractionSession.SHOW_SOURCE_APPLICATION; 126 import static android.text.format.DateUtils.DAY_IN_MILLIS; 127 import static android.view.Display.DEFAULT_DISPLAY; 128 import static android.view.Display.INVALID_DISPLAY; 129 import static com.android.internal.util.XmlUtils.readBooleanAttribute; 130 import static com.android.internal.util.XmlUtils.readIntAttribute; 131 import static com.android.internal.util.XmlUtils.readLongAttribute; 132 import static com.android.internal.util.XmlUtils.writeBooleanAttribute; 133 import static com.android.internal.util.XmlUtils.writeIntAttribute; 134 import static com.android.internal.util.XmlUtils.writeLongAttribute; 135 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_ALL; 136 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_ANR; 137 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_BACKGROUND_CHECK; 138 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_BACKUP; 139 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_BROADCAST; 140 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_BROADCAST_BACKGROUND; 141 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_BROADCAST_LIGHT; 142 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_CLEANUP; 143 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_CONFIGURATION; 144 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_FOCUS; 145 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_IMMERSIVE; 146 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_LOCKTASK; 147 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_LRU; 148 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_MU; 149 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_NETWORK; 150 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_OOM_ADJ; 151 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_OOM_ADJ_REASON; 152 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_PERMISSIONS_REVIEW; 153 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_POWER; 154 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_PROCESSES; 155 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_PROCESS_OBSERVERS; 156 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_PROVIDER; 157 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_PSS; 158 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_SERVICE; 159 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_STACK; 160 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_SWITCH; 161 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_TASKS; 162 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_UID_OBSERVERS; 163 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_URI_PERMISSION; 164 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_USAGE_STATS; 165 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_VISIBILITY; 166 import static com.android.server.am.ActivityManagerDebugConfig.DEBUG_WHITELISTS; 167 import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_BACKUP; 168 import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_BROADCAST; 169 import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_CLEANUP; 170 import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_CONFIGURATION; 171 import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_FOCUS; 172 import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_IMMERSIVE; 173 import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_LOCKTASK; 174 import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_LRU; 175 import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_MU; 176 import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_NETWORK; 177 import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_OOM_ADJ; 178 import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_POWER; 179 import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_PROCESSES; 180 import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_PROCESS_OBSERVERS; 181 import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_PROVIDER; 182 import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_PSS; 183 import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_RECENTS; 184 import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_SERVICE; 185 import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_STACK; 186 import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_SWITCH; 187 import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_UID_OBSERVERS; 188 import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_URI_PERMISSION; 189 import static com.android.server.am.ActivityManagerDebugConfig.POSTFIX_VISIBILITY; 190 import static com.android.server.am.ActivityManagerDebugConfig.TAG_AM; 191 import static com.android.server.am.ActivityManagerDebugConfig.TAG_WITH_CLASS_NAME; 192 import static com.android.server.am.ActivityStack.REMOVE_TASK_MODE_DESTROYING; 193 import static com.android.server.am.ActivityStackSupervisor.DEFER_RESUME; 194 import static com.android.server.am.ActivityStackSupervisor.MATCH_TASK_IN_STACKS_ONLY; 195 import static com.android.server.am.ActivityStackSupervisor.MATCH_TASK_IN_STACKS_OR_RECENT_TASKS; 196 import static com.android.server.am.ActivityStackSupervisor.ON_TOP; 197 import static com.android.server.am.ActivityStackSupervisor.PRESERVE_WINDOWS; 198 import static com.android.server.am.ActivityStackSupervisor.REMOVE_FROM_RECENTS; 199 import static com.android.server.am.MemoryStatUtil.readMemoryStatFromFilesystem; 200 import static com.android.server.am.MemoryStatUtil.hasMemcg; 201 import static com.android.server.am.TaskRecord.INVALID_TASK_ID; 202 import static com.android.server.am.TaskRecord.LOCK_TASK_AUTH_DONT_LOCK; 203 import static com.android.server.am.TaskRecord.REPARENT_KEEP_STACK_AT_FRONT; 204 import static com.android.server.am.TaskRecord.REPARENT_LEAVE_STACK_IN_PLACE; 205 import static android.view.WindowManager.TRANSIT_ACTIVITY_OPEN; 206 import static android.view.WindowManager.TRANSIT_NONE; 207 import static android.view.WindowManager.TRANSIT_TASK_IN_PLACE; 208 import static android.view.WindowManager.TRANSIT_TASK_OPEN; 209 import static android.view.WindowManager.TRANSIT_TASK_TO_FRONT; 210 import static com.android.server.wm.RecentsAnimationController.REORDER_MOVE_TO_ORIGINAL_POSITION; 211 import static com.android.server.wm.RecentsAnimationController.REORDER_KEEP_IN_PLACE; 212 import static org.xmlpull.v1.XmlPullParser.END_DOCUMENT; 213 import static org.xmlpull.v1.XmlPullParser.START_TAG; 214 215 import android.Manifest; 216 import android.Manifest.permission; 217 import android.annotation.NonNull; 218 import android.annotation.Nullable; 219 import android.annotation.UserIdInt; 220 import android.app.Activity; 221 import android.app.ActivityManager; 222 import android.app.ActivityManager.RunningTaskInfo; 223 import android.app.ActivityManager.StackInfo; 224 import android.app.ActivityManager.TaskSnapshot; 225 import android.app.ActivityManagerInternal; 226 import android.app.ActivityManagerInternal.ScreenObserver; 227 import android.app.ActivityManagerInternal.SleepToken; 228 import android.app.ActivityManagerProto; 229 import android.app.ActivityOptions; 230 import android.app.ActivityThread; 231 import android.app.AlertDialog; 232 import android.app.AppGlobals; 233 import android.app.AppOpsManager; 234 import android.app.ApplicationErrorReport; 235 import android.app.ApplicationThreadConstants; 236 import android.app.BroadcastOptions; 237 import android.app.ContentProviderHolder; 238 import android.app.Dialog; 239 import android.app.GrantedUriPermission; 240 import android.app.IActivityController; 241 import android.app.IActivityManager; 242 import android.app.IApplicationThread; 243 import android.app.IAssistDataReceiver; 244 import android.app.IInstrumentationWatcher; 245 import android.app.INotificationManager; 246 import android.app.IProcessObserver; 247 import android.app.IServiceConnection; 248 import android.app.IStopUserCallback; 249 import android.app.ITaskStackListener; 250 import android.app.IUiAutomationConnection; 251 import android.app.IUidObserver; 252 import android.app.IUserSwitchObserver; 253 import android.app.Instrumentation; 254 import android.app.Notification; 255 import android.app.NotificationManager; 256 import android.app.PendingIntent; 257 import android.app.PictureInPictureParams; 258 import android.app.ProcessMemoryState; 259 import android.app.ProfilerInfo; 260 import android.app.RemoteAction; 261 import android.app.WaitResult; 262 import android.app.WindowConfiguration.ActivityType; 263 import android.app.WindowConfiguration.WindowingMode; 264 import android.app.admin.DevicePolicyCache; 265 import android.app.assist.AssistContent; 266 import android.app.assist.AssistStructure; 267 import android.app.backup.IBackupManager; 268 import android.app.servertransaction.ConfigurationChangeItem; 269 import android.app.usage.UsageEvents; 270 import android.app.usage.UsageStatsManagerInternal; 271 import android.appwidget.AppWidgetManager; 272 import android.content.ActivityNotFoundException; 273 import android.content.BroadcastReceiver; 274 import android.content.ClipData; 275 import android.content.ComponentCallbacks2; 276 import android.content.ComponentName; 277 import android.content.ContentProvider; 278 import android.content.ContentResolver; 279 import android.content.Context; 280 import android.content.DialogInterface; 281 import android.content.IContentProvider; 282 import android.content.IIntentReceiver; 283 import android.content.IIntentSender; 284 import android.content.Intent; 285 import android.content.IntentFilter; 286 import android.content.pm.ActivityInfo; 287 import android.content.pm.ApplicationInfo; 288 import android.content.pm.ApplicationInfo.HiddenApiEnforcementPolicy; 289 import android.content.pm.ConfigurationInfo; 290 import android.content.pm.IPackageDataObserver; 291 import android.content.pm.IPackageManager; 292 import android.content.pm.InstrumentationInfo; 293 import android.content.pm.PackageInfo; 294 import android.content.pm.PackageManager; 295 import android.content.pm.PackageManager.NameNotFoundException; 296 import android.content.pm.PackageManagerInternal; 297 import android.content.pm.ParceledListSlice; 298 import android.content.pm.PathPermission; 299 import android.content.pm.PermissionInfo; 300 import android.content.pm.ProviderInfo; 301 import android.content.pm.ResolveInfo; 302 import android.content.pm.SELinuxUtil; 303 import android.content.pm.ServiceInfo; 304 import android.content.pm.UserInfo; 305 import android.content.res.CompatibilityInfo; 306 import android.content.res.Configuration; 307 import android.content.res.Resources; 308 import android.database.ContentObserver; 309 import android.graphics.Bitmap; 310 import android.graphics.Point; 311 import android.graphics.Rect; 312 import android.hardware.display.DisplayManagerInternal; 313 import android.location.LocationManager; 314 import android.media.audiofx.AudioEffect; 315 import android.metrics.LogMaker; 316 import android.net.Proxy; 317 import android.net.ProxyInfo; 318 import android.net.Uri; 319 import android.os.BatteryStats; 320 import android.os.Binder; 321 import android.os.Build; 322 import android.os.Bundle; 323 import android.os.Debug; 324 import android.os.DropBoxManager; 325 import android.os.Environment; 326 import android.os.FactoryTest; 327 import android.os.FileObserver; 328 import android.os.FileUtils; 329 import android.os.Handler; 330 import android.os.IBinder; 331 import android.os.IDeviceIdentifiersPolicyService; 332 import android.os.IPermissionController; 333 import android.os.IProcessInfoService; 334 import android.os.IProgressListener; 335 import android.os.LocaleList; 336 import android.os.Looper; 337 import android.os.Message; 338 import android.os.Parcel; 339 import android.os.ParcelFileDescriptor; 340 import android.os.PersistableBundle; 341 import android.os.PowerManager; 342 import android.os.PowerManager.ServiceType; 343 import android.os.PowerManagerInternal; 344 import android.os.Process; 345 import android.os.RemoteCallbackList; 346 import android.os.RemoteException; 347 import android.os.ResultReceiver; 348 import android.os.ServiceManager; 349 import android.os.ShellCallback; 350 import android.os.StrictMode; 351 import android.os.SystemClock; 352 import android.os.SystemProperties; 353 import android.os.Trace; 354 import android.os.TransactionTooLargeException; 355 import android.os.UpdateLock; 356 import android.os.UserHandle; 357 import android.os.UserManager; 358 import android.os.WorkSource; 359 import android.os.storage.IStorageManager; 360 import android.os.storage.StorageManager; 361 import android.os.storage.StorageManagerInternal; 362 import android.provider.Downloads; 363 import android.provider.Settings; 364 import android.service.voice.IVoiceInteractionSession; 365 import android.service.voice.VoiceInteractionManagerInternal; 366 import android.telecom.TelecomManager; 367 import android.text.TextUtils; 368 import android.text.format.DateUtils; 369 import android.text.format.Time; 370 import android.text.style.SuggestionSpan; 371 import android.util.ArrayMap; 372 import android.util.ArraySet; 373 import android.util.AtomicFile; 374 import android.util.DebugUtils; 375 import android.util.EventLog; 376 import android.util.Log; 377 import android.util.LongSparseArray; 378 import android.util.Pair; 379 import android.util.PrintWriterPrinter; 380 import android.util.Slog; 381 import android.util.SparseArray; 382 import android.util.SparseIntArray; 383 import android.util.StatsLog; 384 import android.util.TimeUtils; 385 import android.util.TimingsTraceLog; 386 import android.util.Xml; 387 import android.util.proto.ProtoOutputStream; 388 import android.util.proto.ProtoUtils; 389 import android.view.Gravity; 390 import android.view.IRecentsAnimationRunner; 391 import android.view.LayoutInflater; 392 import android.view.RemoteAnimationAdapter; 393 import android.view.RemoteAnimationDefinition; 394 import android.view.View; 395 import android.view.WindowManager; 396 import android.view.autofill.AutofillManagerInternal; 397 398 import com.android.internal.R; 399 import com.android.internal.annotations.GuardedBy; 400 import com.android.internal.annotations.VisibleForTesting; 401 import com.android.internal.app.AssistUtils; 402 import com.android.internal.app.DumpHeapActivity; 403 import com.android.internal.app.IAppOpsCallback; 404 import com.android.internal.app.IAppOpsService; 405 import com.android.internal.app.IVoiceInteractor; 406 import com.android.internal.app.ProcessMap; 407 import com.android.internal.app.SystemUserHomeActivity; 408 import com.android.internal.app.procstats.ProcessStats; 409 import com.android.internal.logging.MetricsLogger; 410 import com.android.internal.logging.nano.MetricsProto.MetricsEvent; 411 import com.android.internal.messages.nano.SystemMessageProto.SystemMessage; 412 import com.android.internal.notification.SystemNotificationChannels; 413 import com.android.internal.os.BackgroundThread; 414 import com.android.internal.os.BatteryStatsImpl; 415 import com.android.internal.os.BinderInternal; 416 import com.android.internal.os.logging.MetricsLoggerWrapper; 417 import com.android.internal.os.ByteTransferPipe; 418 import com.android.internal.os.IResultReceiver; 419 import com.android.internal.os.ProcessCpuTracker; 420 import com.android.internal.os.TransferPipe; 421 import com.android.internal.os.Zygote; 422 import com.android.internal.policy.IKeyguardDismissCallback; 423 import com.android.internal.policy.KeyguardDismissCallback; 424 import com.android.internal.telephony.TelephonyIntents; 425 import com.android.internal.util.ArrayUtils; 426 import com.android.internal.util.DumpUtils; 427 import com.android.internal.util.FastPrintWriter; 428 import com.android.internal.util.FastXmlSerializer; 429 import com.android.internal.util.MemInfoReader; 430 import com.android.internal.util.Preconditions; 431 import com.android.server.AlarmManagerInternal; 432 import com.android.server.AppOpsService; 433 import com.android.server.AttributeCache; 434 import com.android.server.BinderCallsStatsService; 435 import com.android.server.DeviceIdleController; 436 import com.android.server.IntentResolver; 437 import com.android.server.IoThread; 438 import com.android.server.LocalServices; 439 import com.android.server.LockGuard; 440 import com.android.server.NetworkManagementInternal; 441 import com.android.server.RescueParty; 442 import com.android.server.ServiceThread; 443 import com.android.server.SystemConfig; 444 import com.android.server.SystemService; 445 import com.android.server.SystemServiceManager; 446 import com.android.server.ThreadPriorityBooster; 447 import com.android.server.Watchdog; 448 import com.android.server.am.ActivityStack.ActivityState; 449 import com.android.server.am.MemoryStatUtil.MemoryStat; 450 import com.android.server.am.ActivityManagerServiceProto; 451 import com.android.server.am.ActivityManagerServiceDumpActivitiesProto; 452 import com.android.server.am.ActivityManagerServiceDumpBroadcastsProto; 453 import com.android.server.am.ActivityManagerServiceDumpProcessesProto; 454 import com.android.server.am.ActivityManagerServiceDumpProcessesProto.UidObserverRegistrationProto; 455 import com.android.server.am.ActivityManagerServiceDumpServicesProto; 456 import com.android.server.am.GrantUriProto; 457 import com.android.server.am.ImportanceTokenProto; 458 import com.android.server.am.MemInfoDumpProto; 459 import com.android.server.am.NeededUriGrantsProto; 460 import com.android.server.am.ProcessOomProto; 461 import com.android.server.am.ProcessToGcProto; 462 import com.android.server.am.StickyBroadcastProto; 463 import com.android.server.firewall.IntentFirewall; 464 import com.android.server.job.JobSchedulerInternal; 465 import com.android.server.pm.Installer; 466 import com.android.server.pm.Installer.InstallerException; 467 import com.android.server.pm.dex.DexManager; 468 import com.android.server.utils.PriorityDump; 469 import com.android.server.vr.VrManagerInternal; 470 import com.android.server.wm.PinnedStackWindowController; 471 import com.android.server.wm.WindowManagerService; 472 473 import dalvik.system.VMRuntime; 474 475 import libcore.io.IoUtils; 476 import libcore.util.EmptyArray; 477 478 import com.google.android.collect.Lists; 479 import com.google.android.collect.Maps; 480 481 import org.xmlpull.v1.XmlPullParser; 482 import org.xmlpull.v1.XmlPullParserException; 483 import org.xmlpull.v1.XmlSerializer; 484 485 import java.io.File; 486 import java.io.FileDescriptor; 487 import java.io.FileInputStream; 488 import java.io.FileNotFoundException; 489 import java.io.FileOutputStream; 490 import java.io.IOException; 491 import java.io.InputStreamReader; 492 import java.io.PrintWriter; 493 import java.io.StringWriter; 494 import java.io.UnsupportedEncodingException; 495 import java.lang.ref.WeakReference; 496 import java.nio.charset.StandardCharsets; 497 import java.text.DateFormat; 498 import java.text.SimpleDateFormat; 499 import java.util.ArrayList; 500 import java.util.Arrays; 501 import java.util.Collections; 502 import java.util.Comparator; 503 import java.util.Date; 504 import java.util.HashMap; 505 import java.util.HashSet; 506 import java.util.Iterator; 507 import java.util.List; 508 import java.util.Locale; 509 import java.util.Map; 510 import java.util.Objects; 511 import java.util.Set; 512 import java.util.concurrent.CountDownLatch; 513 import java.util.concurrent.Executor; 514 import java.util.concurrent.atomic.AtomicBoolean; 515 import java.util.concurrent.atomic.AtomicLong; 516 517 public class ActivityManagerService extends IActivityManager.Stub 518 implements Watchdog.Monitor, BatteryStatsImpl.BatteryCallback { 519 520 /** 521 * Priority we boost main thread and RT of top app to. 522 */ 523 public static final int TOP_APP_PRIORITY_BOOST = -10; 524 525 private static final String TAG = TAG_WITH_CLASS_NAME ? "ActivityManagerService" : TAG_AM; 526 private static final String TAG_BACKUP = TAG + POSTFIX_BACKUP; 527 private static final String TAG_BROADCAST = TAG + POSTFIX_BROADCAST; 528 private static final String TAG_CLEANUP = TAG + POSTFIX_CLEANUP; 529 private static final String TAG_CONFIGURATION = TAG + POSTFIX_CONFIGURATION; 530 private static final String TAG_FOCUS = TAG + POSTFIX_FOCUS; 531 private static final String TAG_IMMERSIVE = TAG + POSTFIX_IMMERSIVE; 532 private static final String TAG_LOCKTASK = TAG + POSTFIX_LOCKTASK; 533 private static final String TAG_LRU = TAG + POSTFIX_LRU; 534 private static final String TAG_MU = TAG + POSTFIX_MU; 535 private static final String TAG_NETWORK = TAG + POSTFIX_NETWORK; 536 private static final String TAG_OOM_ADJ = TAG + POSTFIX_OOM_ADJ; 537 private static final String TAG_POWER = TAG + POSTFIX_POWER; 538 private static final String TAG_PROCESS_OBSERVERS = TAG + POSTFIX_PROCESS_OBSERVERS; 539 private static final String TAG_PROCESSES = TAG + POSTFIX_PROCESSES; 540 private static final String TAG_PROVIDER = TAG + POSTFIX_PROVIDER; 541 private static final String TAG_PSS = TAG + POSTFIX_PSS; 542 private static final String TAG_RECENTS = TAG + POSTFIX_RECENTS; 543 private static final String TAG_SERVICE = TAG + POSTFIX_SERVICE; 544 private static final String TAG_STACK = TAG + POSTFIX_STACK; 545 private static final String TAG_SWITCH = TAG + POSTFIX_SWITCH; 546 private static final String TAG_UID_OBSERVERS = TAG + POSTFIX_UID_OBSERVERS; 547 private static final String TAG_URI_PERMISSION = TAG + POSTFIX_URI_PERMISSION; 548 private static final String TAG_VISIBILITY = TAG + POSTFIX_VISIBILITY; 549 550 // Mock "pretend we're idle now" broadcast action to the job scheduler; declared 551 // here so that while the job scheduler can depend on AMS, the other way around 552 // need not be the case. 553 public static final String ACTION_TRIGGER_IDLE = "com.android.server.ACTION_TRIGGER_IDLE"; 554 555 /** Control over CPU and battery monitoring */ 556 // write battery stats every 30 minutes. 557 static final long BATTERY_STATS_TIME = 30 * 60 * 1000; 558 static final boolean MONITOR_CPU_USAGE = true; 559 // don't sample cpu less than every 5 seconds. 560 static final long MONITOR_CPU_MIN_TIME = 5 * 1000; 561 // wait possibly forever for next cpu sample. 562 static final long MONITOR_CPU_MAX_TIME = 0x0fffffff; 563 static final boolean MONITOR_THREAD_CPU_USAGE = false; 564 565 // The flags that are set for all calls we make to the package manager. 566 static final int STOCK_PM_FLAGS = PackageManager.GET_SHARED_LIBRARY_FILES; 567 568 static final String SYSTEM_DEBUGGABLE = "ro.debuggable"; 569 570 // Maximum number of receivers an app can register. 571 private static final int MAX_RECEIVERS_ALLOWED_PER_APP = 1000; 572 573 // Amount of time after a call to stopAppSwitches() during which we will 574 // prevent further untrusted switches from happening. 575 static final long APP_SWITCH_DELAY_TIME = 5*1000; 576 577 // How long we wait for a launched process to attach to the activity manager 578 // before we decide it's never going to come up for real. 579 static final int PROC_START_TIMEOUT = 10*1000; 580 // How long we wait for an attached process to publish its content providers 581 // before we decide it must be hung. 582 static final int CONTENT_PROVIDER_PUBLISH_TIMEOUT = 10*1000; 583 584 // How long we wait for a launched process to attach to the activity manager 585 // before we decide it's never going to come up for real, when the process was 586 // started with a wrapper for instrumentation (such as Valgrind) because it 587 // could take much longer than usual. 588 static final int PROC_START_TIMEOUT_WITH_WRAPPER = 1200*1000; 589 590 // How long we allow a receiver to run before giving up on it. 591 static final int BROADCAST_FG_TIMEOUT = 10*1000; 592 static final int BROADCAST_BG_TIMEOUT = 60*1000; 593 594 // How long we wait until we timeout on key dispatching. 595 static final int KEY_DISPATCHING_TIMEOUT = 5*1000; 596 597 // How long we wait until we timeout on key dispatching during instrumentation. 598 static final int INSTRUMENTATION_KEY_DISPATCHING_TIMEOUT = 60*1000; 599 600 // Disable hidden API checks for the newly started instrumentation. 601 // Must be kept in sync with Am. 602 private static final int INSTRUMENTATION_FLAG_DISABLE_HIDDEN_API_CHECKS = 1 << 0; 603 604 // How long to wait in getAssistContextExtras for the activity and foreground services 605 // to respond with the result. 606 static final int PENDING_ASSIST_EXTRAS_TIMEOUT = 500; 607 608 // How long top wait when going through the modern assist (which doesn't need to block 609 // on getting this result before starting to launch its UI). 610 static final int PENDING_ASSIST_EXTRAS_LONG_TIMEOUT = 2000; 611 612 // How long to wait in getAutofillAssistStructure() for the activity to respond with the result. 613 static final int PENDING_AUTOFILL_ASSIST_STRUCTURE_TIMEOUT = 2000; 614 615 // Maximum number of persisted Uri grants a package is allowed 616 static final int MAX_PERSISTED_URI_GRANTS = 128; 617 618 static final int MY_PID = myPid(); 619 620 static final String[] EMPTY_STRING_ARRAY = new String[0]; 621 622 // How many bytes to write into the dropbox log before truncating 623 static final int DROPBOX_MAX_SIZE = 192 * 1024; 624 // Assumes logcat entries average around 100 bytes; that's not perfect stack traces count 625 // as one line, but close enough for now. 626 static final int RESERVED_BYTES_PER_LOGCAT_LINE = 100; 627 628 /** If a UID observer takes more than this long, send a WTF. */ 629 private static final int SLOW_UID_OBSERVER_THRESHOLD_MS = 20; 630 631 // Access modes for handleIncomingUser. 632 static final int ALLOW_NON_FULL = 0; 633 static final int ALLOW_NON_FULL_IN_PROFILE = 1; 634 static final int ALLOW_FULL_ONLY = 2; 635 636 // Necessary ApplicationInfo flags to mark an app as persistent 637 private static final int PERSISTENT_MASK = 638 ApplicationInfo.FLAG_SYSTEM|ApplicationInfo.FLAG_PERSISTENT; 639 640 // Intent sent when remote bugreport collection has been completed 641 private static final String INTENT_REMOTE_BUGREPORT_FINISHED = 642 "com.android.internal.intent.action.REMOTE_BUGREPORT_FINISHED"; 643 644 // Used to indicate that an app transition should be animated. 645 static final boolean ANIMATE = true; 646 647 // Determines whether to take full screen screenshots 648 static final boolean TAKE_FULLSCREEN_SCREENSHOTS = true; 649 650 /** 651 * Default value for {@link Settings.Global#NETWORK_ACCESS_TIMEOUT_MS}. 652 */ 653 private static final long NETWORK_ACCESS_TIMEOUT_DEFAULT_MS = 200; // 0.2 sec 654 655 /** 656 * State indicating that there is no need for any blocking for network. 657 */ 658 @VisibleForTesting 659 static final int NETWORK_STATE_NO_CHANGE = 0; 660 661 /** 662 * State indicating that the main thread needs to be informed about the network wait. 663 */ 664 @VisibleForTesting 665 static final int NETWORK_STATE_BLOCK = 1; 666 667 /** 668 * State indicating that any threads waiting for network state to get updated can be unblocked. 669 */ 670 @VisibleForTesting 671 static final int NETWORK_STATE_UNBLOCK = 2; 672 673 // Max character limit for a notification title. If the notification title is larger than this 674 // the notification will not be legible to the user. 675 private static final int MAX_BUGREPORT_TITLE_SIZE = 50; 676 677 private static final int NATIVE_DUMP_TIMEOUT_MS = 2000; // 2 seconds; 678 679 /** All system services */ 680 SystemServiceManager mSystemServiceManager; 681 682 // Wrapper around VoiceInteractionServiceManager 683 private AssistUtils mAssistUtils; 684 685 // Keeps track of the active voice interaction service component, notified from 686 // VoiceInteractionManagerService 687 ComponentName mActiveVoiceInteractionServiceComponent; 688 689 private Installer mInstaller; 690 691 /** Run all ActivityStacks through this */ 692 final ActivityStackSupervisor mStackSupervisor; 693 private final KeyguardController mKeyguardController; 694 695 private final ActivityStartController mActivityStartController; 696 697 private final ClientLifecycleManager mLifecycleManager; 698 699 final TaskChangeNotificationController mTaskChangeNotificationController; 700 701 final InstrumentationReporter mInstrumentationReporter = new InstrumentationReporter(); 702 703 final ArrayList<ActiveInstrumentation> mActiveInstrumentation = new ArrayList<>(); 704 705 public final IntentFirewall mIntentFirewall; 706 707 // Whether we should show our dialogs (ANR, crash, etc) or just perform their 708 // default action automatically. Important for devices without direct input 709 // devices. 710 private boolean mShowDialogs = true; 711 712 private final VrController mVrController; 713 714 // VR Vr2d Display Id. 715 int mVr2dDisplayId = INVALID_DISPLAY; 716 717 // Whether we should use SCHED_FIFO for UI and RenderThreads. 718 private boolean mUseFifoUiScheduling = false; 719 720 private static final String SYSUI_COMPONENT_NAME = "com.android.systemui/.SystemUIService"; 721 722 BroadcastQueue mFgBroadcastQueue; 723 BroadcastQueue mBgBroadcastQueue; 724 // Convenient for easy iteration over the queues. Foreground is first 725 // so that dispatch of foreground broadcasts gets precedence. 726 final BroadcastQueue[] mBroadcastQueues = new BroadcastQueue[2]; 727 728 BroadcastStats mLastBroadcastStats; 729 BroadcastStats mCurBroadcastStats; 730 731 BroadcastQueue broadcastQueueForIntent(Intent intent) { 732 final boolean isFg = (intent.getFlags() & Intent.FLAG_RECEIVER_FOREGROUND) != 0; 733 if (DEBUG_BROADCAST_BACKGROUND) Slog.i(TAG_BROADCAST, 734 "Broadcast intent " + intent + " on " 735 + (isFg ? "foreground" : "background") + " queue"); 736 return (isFg) ? mFgBroadcastQueue : mBgBroadcastQueue; 737 } 738 739 /** 740 * The last resumed activity. This is identical to the current resumed activity most 741 * of the time but could be different when we're pausing one activity before we resume 742 * another activity. 743 */ 744 private ActivityRecord mLastResumedActivity; 745 746 /** 747 * The activity that is currently being traced as the active resumed activity. 748 * 749 * @see #updateResumedAppTrace 750 */ 751 private @Nullable ActivityRecord mTracedResumedActivity; 752 753 /** 754 * If non-null, we are tracking the time the user spends in the currently focused app. 755 */ 756 private AppTimeTracker mCurAppTimeTracker; 757 758 /** 759 * List of intents that were used to start the most recent tasks. 760 */ 761 private final RecentTasks mRecentTasks; 762 763 /** 764 * The package name of the DeviceOwner. This package is not permitted to have its data cleared. 765 */ 766 String mDeviceOwnerName; 767 768 /** 769 * The controller for all operations related to locktask. 770 */ 771 private final LockTaskController mLockTaskController; 772 773 final UserController mUserController; 774 775 /** 776 * Packages that are being allowed to perform unrestricted app switches. Mapping is 777 * User -> Type -> uid. 778 */ 779 final SparseArray<ArrayMap<String, Integer>> mAllowAppSwitchUids = new SparseArray<>(); 780 781 final AppErrors mAppErrors; 782 783 final AppWarnings mAppWarnings; 784 785 /** 786 * Dump of the activity state at the time of the last ANR. Cleared after 787 * {@link WindowManagerService#LAST_ANR_LIFETIME_DURATION_MSECS} 788 */ 789 String mLastANRState; 790 791 /** 792 * Indicates the maximum time spent waiting for the network rules to get updated. 793 */ 794 @VisibleForTesting 795 long mWaitForNetworkTimeoutMs; 796 797 /** Total # of UID change events dispatched, shown in dumpsys. */ 798 int mUidChangeDispatchCount; 799 800 /** 801 * Helper class which strips out priority and proto arguments then calls the dump function with 802 * the appropriate arguments. If priority arguments are omitted, function calls the legacy 803 * dump command. 804 * If priority arguments are omitted all sections are dumped, otherwise sections are dumped 805 * according to their priority. 806 */ 807 private final PriorityDump.PriorityDumper mPriorityDumper = new PriorityDump.PriorityDumper() { 808 @Override 809 public void dumpCritical(FileDescriptor fd, PrintWriter pw, String[] args, 810 boolean asProto) { 811 if (asProto) return; 812 doDump(fd, pw, new String[]{"activities"}, asProto); 813 doDump(fd, pw, new String[]{"service", SYSUI_COMPONENT_NAME}, asProto); 814 } 815 816 @Override 817 public void dumpNormal(FileDescriptor fd, PrintWriter pw, String[] args, boolean asProto) { 818 doDump(fd, pw, new String[]{"-a", "--normal-priority"}, asProto); 819 } 820 821 @Override 822 public void dump(FileDescriptor fd, PrintWriter pw, String[] args, boolean asProto) { 823 doDump(fd, pw, args, asProto); 824 } 825 }; 826 827 public boolean canShowErrorDialogs() { 828 return mShowDialogs && !mSleeping && !mShuttingDown 829 && !mKeyguardController.isKeyguardOrAodShowing(DEFAULT_DISPLAY) 830 && !mUserController.hasUserRestriction(UserManager.DISALLOW_SYSTEM_ERROR_DIALOGS, 831 mUserController.getCurrentUserId()) 832 && !(UserManager.isDeviceInDemoMode(mContext) 833 && mUserController.getCurrentUser().isDemo()); 834 } 835 836 private static ThreadPriorityBooster sThreadPriorityBooster = new ThreadPriorityBooster( 837 THREAD_PRIORITY_FOREGROUND, LockGuard.INDEX_ACTIVITY); 838 839 static void boostPriorityForLockedSection() { 840 sThreadPriorityBooster.boost(); 841 } 842 843 static void resetPriorityAfterLockedSection() { 844 sThreadPriorityBooster.reset(); 845 } 846 847 public class PendingAssistExtras extends Binder implements Runnable { 848 public final ActivityRecord activity; 849 public boolean isHome; 850 public final Bundle extras; 851 public final Intent intent; 852 public final String hint; 853 public final IAssistDataReceiver receiver; 854 public final int userHandle; 855 public boolean haveResult = false; 856 public Bundle result = null; 857 public AssistStructure structure = null; 858 public AssistContent content = null; 859 public Bundle receiverExtras; 860 861 public PendingAssistExtras(ActivityRecord _activity, Bundle _extras, Intent _intent, 862 String _hint, IAssistDataReceiver _receiver, Bundle _receiverExtras, 863 int _userHandle) { 864 activity = _activity; 865 extras = _extras; 866 intent = _intent; 867 hint = _hint; 868 receiver = _receiver; 869 receiverExtras = _receiverExtras; 870 userHandle = _userHandle; 871 } 872 873 @Override 874 public void run() { 875 Slog.w(TAG, "getAssistContextExtras failed: timeout retrieving from " + activity); 876 synchronized (this) { 877 haveResult = true; 878 notifyAll(); 879 } 880 pendingAssistExtrasTimedOut(this); 881 } 882 } 883 884 final ArrayList<PendingAssistExtras> mPendingAssistExtras = new ArrayList<>(); 885 886 /** 887 * Process management. 888 */ 889 final ProcessList mProcessList = new ProcessList(); 890 891 /** 892 * All of the applications we currently have running organized by name. 893 * The keys are strings of the application package name (as 894 * returned by the package manager), and the keys are ApplicationRecord 895 * objects. 896 */ 897 final ProcessMap<ProcessRecord> mProcessNames = new ProcessMap<ProcessRecord>(); 898 899 /** 900 * Tracking long-term execution of processes to look for abuse and other 901 * bad app behavior. 902 */ 903 final ProcessStatsService mProcessStats; 904 905 /** 906 * The currently running isolated processes. 907 */ 908 final SparseArray<ProcessRecord> mIsolatedProcesses = new SparseArray<ProcessRecord>(); 909 910 /** 911 * Counter for assigning isolated process uids, to avoid frequently reusing the 912 * same ones. 913 */ 914 int mNextIsolatedProcessUid = 0; 915 916 /** 917 * The currently running heavy-weight process, if any. 918 */ 919 ProcessRecord mHeavyWeightProcess = null; 920 921 /** 922 * Non-persistent appId whitelist for background restrictions 923 */ 924 int[] mBackgroundAppIdWhitelist = new int[] { 925 BLUETOOTH_UID 926 }; 927 928 /** 929 * Broadcast actions that will always be deliverable to unlaunched/background apps 930 */ 931 ArraySet<String> mBackgroundLaunchBroadcasts; 932 933 /** 934 * All of the processes we currently have running organized by pid. 935 * The keys are the pid running the application. 936 * 937 * <p>NOTE: This object is protected by its own lock, NOT the global 938 * activity manager lock! 939 */ 940 final SparseArray<ProcessRecord> mPidsSelfLocked = new SparseArray<ProcessRecord>(); 941 942 /** 943 * All of the processes that have been forced to be important. The key 944 * is the pid of the caller who requested it (we hold a death 945 * link on it). 946 */ 947 abstract class ImportanceToken implements IBinder.DeathRecipient { 948 final int pid; 949 final IBinder token; 950 final String reason; 951 952 ImportanceToken(int _pid, IBinder _token, String _reason) { 953 pid = _pid; 954 token = _token; 955 reason = _reason; 956 } 957 958 @Override 959 public String toString() { 960 return "ImportanceToken { " + Integer.toHexString(System.identityHashCode(this)) 961 + " " + reason + " " + pid + " " + token + " }"; 962 } 963 964 void writeToProto(ProtoOutputStream proto, long fieldId) { 965 final long pToken = proto.start(fieldId); 966 proto.write(ImportanceTokenProto.PID, pid); 967 if (token != null) { 968 proto.write(ImportanceTokenProto.TOKEN, token.toString()); 969 } 970 proto.write(ImportanceTokenProto.REASON, reason); 971 proto.end(pToken); 972 } 973 } 974 final SparseArray<ImportanceToken> mImportantProcesses = new SparseArray<ImportanceToken>(); 975 976 /** 977 * List of records for processes that someone had tried to start before the 978 * system was ready. We don't start them at that point, but ensure they 979 * are started by the time booting is complete. 980 */ 981 final ArrayList<ProcessRecord> mProcessesOnHold = new ArrayList<ProcessRecord>(); 982 983 /** 984 * List of persistent applications that are in the process 985 * of being started. 986 */ 987 final ArrayList<ProcessRecord> mPersistentStartingProcesses = new ArrayList<ProcessRecord>(); 988 989 /** 990 * Processes that are being forcibly torn down. 991 */ 992 final ArrayList<ProcessRecord> mRemovedProcesses = new ArrayList<ProcessRecord>(); 993 994 /** 995 * List of running applications, sorted by recent usage. 996 * The first entry in the list is the least recently used. 997 */ 998 final ArrayList<ProcessRecord> mLruProcesses = new ArrayList<ProcessRecord>(); 999 1000 /** 1001 * Where in mLruProcesses that the processes hosting activities start. 1002 */ 1003 int mLruProcessActivityStart = 0; 1004 1005 /** 1006 * Where in mLruProcesses that the processes hosting services start. 1007 * This is after (lower index) than mLruProcessesActivityStart. 1008 */ 1009 int mLruProcessServiceStart = 0; 1010 1011 /** 1012 * List of processes that should gc as soon as things are idle. 1013 */ 1014 final ArrayList<ProcessRecord> mProcessesToGc = new ArrayList<ProcessRecord>(); 1015 1016 /** 1017 * Processes we want to collect PSS data from. 1018 */ 1019 final ArrayList<ProcessRecord> mPendingPssProcesses = new ArrayList<ProcessRecord>(); 1020 1021 private boolean mBinderTransactionTrackingEnabled = false; 1022 1023 /** 1024 * Last time we requested PSS data of all processes. 1025 */ 1026 long mLastFullPssTime = SystemClock.uptimeMillis(); 1027 1028 /** 1029 * If set, the next time we collect PSS data we should do a full collection 1030 * with data from native processes and the kernel. 1031 */ 1032 boolean mFullPssPending = false; 1033 1034 /** 1035 * This is the process holding what we currently consider to be 1036 * the "home" activity. 1037 */ 1038 ProcessRecord mHomeProcess; 1039 1040 /** 1041 * This is the process holding the activity the user last visited that 1042 * is in a different process from the one they are currently in. 1043 */ 1044 ProcessRecord mPreviousProcess; 1045 1046 /** 1047 * The time at which the previous process was last visible. 1048 */ 1049 long mPreviousProcessVisibleTime; 1050 1051 /** 1052 * Track all uids that have actively running processes. 1053 */ 1054 final SparseArray<UidRecord> mActiveUids = new SparseArray<>(); 1055 1056 /** 1057 * This is for verifying the UID report flow. 1058 */ 1059 static final boolean VALIDATE_UID_STATES = true; 1060 final SparseArray<UidRecord> mValidateUids = new SparseArray<>(); 1061 1062 /** 1063 * Packages that the user has asked to have run in screen size 1064 * compatibility mode instead of filling the screen. 1065 */ 1066 final CompatModePackages mCompatModePackages; 1067 1068 /** 1069 * Set of IntentSenderRecord objects that are currently active. 1070 */ 1071 final HashMap<PendingIntentRecord.Key, WeakReference<PendingIntentRecord>> mIntentSenderRecords 1072 = new HashMap<PendingIntentRecord.Key, WeakReference<PendingIntentRecord>>(); 1073 1074 /** 1075 * Fingerprints (hashCode()) of stack traces that we've 1076 * already logged DropBox entries for. Guarded by itself. If 1077 * something (rogue user app) forces this over 1078 * MAX_DUP_SUPPRESSED_STACKS entries, the contents are cleared. 1079 */ 1080 private final HashSet<Integer> mAlreadyLoggedViolatedStacks = new HashSet<Integer>(); 1081 private static final int MAX_DUP_SUPPRESSED_STACKS = 5000; 1082 1083 /** 1084 * Keeps track of all IIntentReceivers that have been registered for broadcasts. 1085 * Hash keys are the receiver IBinder, hash value is a ReceiverList. 1086 */ 1087 final HashMap<IBinder, ReceiverList> mRegisteredReceivers = new HashMap<>(); 1088 1089 /** 1090 * Resolver for broadcast intents to registered receivers. 1091 * Holds BroadcastFilter (subclass of IntentFilter). 1092 */ 1093 final IntentResolver<BroadcastFilter, BroadcastFilter> mReceiverResolver 1094 = new IntentResolver<BroadcastFilter, BroadcastFilter>() { 1095 @Override 1096 protected boolean allowFilterResult( 1097 BroadcastFilter filter, List<BroadcastFilter> dest) { 1098 IBinder target = filter.receiverList.receiver.asBinder(); 1099 for (int i = dest.size() - 1; i >= 0; i--) { 1100 if (dest.get(i).receiverList.receiver.asBinder() == target) { 1101 return false; 1102 } 1103 } 1104 return true; 1105 } 1106 1107 @Override 1108 protected BroadcastFilter newResult(BroadcastFilter filter, int match, int userId) { 1109 if (userId == UserHandle.USER_ALL || filter.owningUserId == UserHandle.USER_ALL 1110 || userId == filter.owningUserId) { 1111 return super.newResult(filter, match, userId); 1112 } 1113 return null; 1114 } 1115 1116 @Override 1117 protected BroadcastFilter[] newArray(int size) { 1118 return new BroadcastFilter[size]; 1119 } 1120 1121 @Override 1122 protected boolean isPackageForFilter(String packageName, BroadcastFilter filter) { 1123 return packageName.equals(filter.packageName); 1124 } 1125 }; 1126 1127 /** 1128 * State of all active sticky broadcasts per user. Keys are the action of the 1129 * sticky Intent, values are an ArrayList of all broadcasted intents with 1130 * that action (which should usually be one). The SparseArray is keyed 1131 * by the user ID the sticky is for, and can include UserHandle.USER_ALL 1132 * for stickies that are sent to all users. 1133 */ 1134 final SparseArray<ArrayMap<String, ArrayList<Intent>>> mStickyBroadcasts = 1135 new SparseArray<ArrayMap<String, ArrayList<Intent>>>(); 1136 1137 final ActiveServices mServices; 1138 1139 final static class Association { 1140 final int mSourceUid; 1141 final String mSourceProcess; 1142 final int mTargetUid; 1143 final ComponentName mTargetComponent; 1144 final String mTargetProcess; 1145 1146 int mCount; 1147 long mTime; 1148 1149 int mNesting; 1150 long mStartTime; 1151 1152 // states of the source process when the bind occurred. 1153 int mLastState = ActivityManager.MAX_PROCESS_STATE + 1; 1154 long mLastStateUptime; 1155 long[] mStateTimes = new long[ActivityManager.MAX_PROCESS_STATE 1156 - ActivityManager.MIN_PROCESS_STATE+1]; 1157 1158 Association(int sourceUid, String sourceProcess, int targetUid, 1159 ComponentName targetComponent, String targetProcess) { 1160 mSourceUid = sourceUid; 1161 mSourceProcess = sourceProcess; 1162 mTargetUid = targetUid; 1163 mTargetComponent = targetComponent; 1164 mTargetProcess = targetProcess; 1165 } 1166 } 1167 1168 /** 1169 * When service association tracking is enabled, this is all of the associations we 1170 * have seen. Mapping is target uid -> target component -> source uid -> source process name 1171 * -> association data. 1172 */ 1173 final SparseArray<ArrayMap<ComponentName, SparseArray<ArrayMap<String, Association>>>> 1174 mAssociations = new SparseArray<>(); 1175 boolean mTrackingAssociations; 1176 1177 /** 1178 * Backup/restore process management 1179 */ 1180 String mBackupAppName = null; 1181 BackupRecord mBackupTarget = null; 1182 1183 final ProviderMap mProviderMap; 1184 1185 /** 1186 * List of content providers who have clients waiting for them. The 1187 * application is currently being launched and the provider will be 1188 * removed from this list once it is published. 1189 */ 1190 final ArrayList<ContentProviderRecord> mLaunchingProviders 1191 = new ArrayList<ContentProviderRecord>(); 1192 1193 /** 1194 * File storing persisted {@link #mGrantedUriPermissions}. 1195 */ 1196 private final AtomicFile mGrantFile; 1197 1198 /** XML constants used in {@link #mGrantFile} */ 1199 private static final String TAG_URI_GRANTS = "uri-grants"; 1200 private static final String TAG_URI_GRANT = "uri-grant"; 1201 private static final String ATTR_USER_HANDLE = "userHandle"; 1202 private static final String ATTR_SOURCE_USER_ID = "sourceUserId"; 1203 private static final String ATTR_TARGET_USER_ID = "targetUserId"; 1204 private static final String ATTR_SOURCE_PKG = "sourcePkg"; 1205 private static final String ATTR_TARGET_PKG = "targetPkg"; 1206 private static final String ATTR_URI = "uri"; 1207 private static final String ATTR_MODE_FLAGS = "modeFlags"; 1208 private static final String ATTR_CREATED_TIME = "createdTime"; 1209 private static final String ATTR_PREFIX = "prefix"; 1210 1211 /** 1212 * Global set of specific {@link Uri} permissions that have been granted. 1213 * This optimized lookup structure maps from {@link UriPermission#targetUid} 1214 * to {@link UriPermission#uri} to {@link UriPermission}. 1215 */ 1216 @GuardedBy("this") 1217 private final SparseArray<ArrayMap<GrantUri, UriPermission>> 1218 mGrantedUriPermissions = new SparseArray<ArrayMap<GrantUri, UriPermission>>(); 1219 1220 public static class GrantUri { 1221 public final int sourceUserId; 1222 public final Uri uri; 1223 public boolean prefix; 1224 1225 public GrantUri(int sourceUserId, Uri uri, boolean prefix) { 1226 this.sourceUserId = sourceUserId; 1227 this.uri = uri; 1228 this.prefix = prefix; 1229 } 1230 1231 @Override 1232 public int hashCode() { 1233 int hashCode = 1; 1234 hashCode = 31 * hashCode + sourceUserId; 1235 hashCode = 31 * hashCode + uri.hashCode(); 1236 hashCode = 31 * hashCode + (prefix ? 1231 : 1237); 1237 return hashCode; 1238 } 1239 1240 @Override 1241 public boolean equals(Object o) { 1242 if (o instanceof GrantUri) { 1243 GrantUri other = (GrantUri) o; 1244 return uri.equals(other.uri) && (sourceUserId == other.sourceUserId) 1245 && prefix == other.prefix; 1246 } 1247 return false; 1248 } 1249 1250 @Override 1251 public String toString() { 1252 String result = uri.toString() + " [user " + sourceUserId + "]"; 1253 if (prefix) result += " [prefix]"; 1254 return result; 1255 } 1256 1257 public String toSafeString() { 1258 String result = uri.toSafeString() + " [user " + sourceUserId + "]"; 1259 if (prefix) result += " [prefix]"; 1260 return result; 1261 } 1262 1263 public void writeToProto(ProtoOutputStream proto, long fieldId) { 1264 long token = proto.start(fieldId); 1265 proto.write(GrantUriProto.URI, uri.toString()); 1266 proto.write(GrantUriProto.SOURCE_USER_ID, sourceUserId); 1267 proto.end(token); 1268 } 1269 1270 public static GrantUri resolve(int defaultSourceUserHandle, Uri uri) { 1271 if (ContentResolver.SCHEME_CONTENT.equals(uri.getScheme())) { 1272 return new GrantUri(ContentProvider.getUserIdFromUri(uri, defaultSourceUserHandle), 1273 ContentProvider.getUriWithoutUserId(uri), false); 1274 } else { 1275 return new GrantUri(defaultSourceUserHandle, uri, false); 1276 } 1277 } 1278 } 1279 1280 boolean mSystemProvidersInstalled; 1281 1282 CoreSettingsObserver mCoreSettingsObserver; 1283 1284 FontScaleSettingObserver mFontScaleSettingObserver; 1285 1286 private final class FontScaleSettingObserver extends ContentObserver { 1287 private final Uri mFontScaleUri = Settings.System.getUriFor(FONT_SCALE); 1288 private final Uri mHideErrorDialogsUri = Settings.Global.getUriFor(HIDE_ERROR_DIALOGS); 1289 1290 public FontScaleSettingObserver() { 1291 super(mHandler); 1292 ContentResolver resolver = mContext.getContentResolver(); 1293 resolver.registerContentObserver(mFontScaleUri, false, this, UserHandle.USER_ALL); 1294 resolver.registerContentObserver(mHideErrorDialogsUri, false, this, 1295 UserHandle.USER_ALL); 1296 } 1297 1298 @Override 1299 public void onChange(boolean selfChange, Uri uri, @UserIdInt int userId) { 1300 if (mFontScaleUri.equals(uri)) { 1301 updateFontScaleIfNeeded(userId); 1302 } else if (mHideErrorDialogsUri.equals(uri)) { 1303 synchronized (ActivityManagerService.this) { 1304 updateShouldShowDialogsLocked(getGlobalConfiguration()); 1305 } 1306 } 1307 } 1308 } 1309 1310 DevelopmentSettingsObserver mDevelopmentSettingsObserver; 1311 1312 private final class DevelopmentSettingsObserver extends ContentObserver { 1313 private final Uri mUri = Settings.Global 1314 .getUriFor(Settings.Global.DEVELOPMENT_SETTINGS_ENABLED); 1315 1316 private final ComponentName mBugreportStorageProvider = new ComponentName( 1317 "com.android.shell", "com.android.shell.BugreportStorageProvider"); 1318 1319 public DevelopmentSettingsObserver() { 1320 super(mHandler); 1321 mContext.getContentResolver().registerContentObserver(mUri, false, this, 1322 UserHandle.USER_ALL); 1323 // Always kick once to ensure that we match current state 1324 onChange(); 1325 } 1326 1327 @Override 1328 public void onChange(boolean selfChange, Uri uri, @UserIdInt int userId) { 1329 if (mUri.equals(uri)) { 1330 onChange(); 1331 } 1332 } 1333 1334 public void onChange() { 1335 final boolean enabled = Settings.Global.getInt(mContext.getContentResolver(), 1336 Settings.Global.DEVELOPMENT_SETTINGS_ENABLED, Build.IS_ENG ? 1 : 0) != 0; 1337 mContext.getPackageManager().setComponentEnabledSetting(mBugreportStorageProvider, 1338 enabled ? PackageManager.COMPONENT_ENABLED_STATE_ENABLED 1339 : PackageManager.COMPONENT_ENABLED_STATE_DEFAULT, 1340 0); 1341 } 1342 } 1343 1344 /** 1345 * Thread-local storage used to carry caller permissions over through 1346 * indirect content-provider access. 1347 */ 1348 private class Identity { 1349 public final IBinder token; 1350 public final int pid; 1351 public final int uid; 1352 1353 Identity(IBinder _token, int _pid, int _uid) { 1354 token = _token; 1355 pid = _pid; 1356 uid = _uid; 1357 } 1358 } 1359 1360 private static final ThreadLocal<Identity> sCallerIdentity = new ThreadLocal<Identity>(); 1361 1362 /** 1363 * All information we have collected about the runtime performance of 1364 * any user id that can impact battery performance. 1365 */ 1366 final BatteryStatsService mBatteryStatsService; 1367 1368 /** 1369 * Information about component usage 1370 */ 1371 UsageStatsManagerInternal mUsageStatsService; 1372 1373 /** 1374 * Access to DeviceIdleController service. 1375 */ 1376 DeviceIdleController.LocalService mLocalDeviceIdleController; 1377 1378 /** 1379 * Power-save whitelisted app-ids (not including except-idle-whitelisted ones). 1380 */ 1381 int[] mDeviceIdleWhitelist = new int[0]; 1382 1383 /** 1384 * Power-save whitelisted app-ids (including except-idle-whitelisted ones). 1385 */ 1386 int[] mDeviceIdleExceptIdleWhitelist = new int[0]; 1387 1388 /** 1389 * Set of app ids that are temporarily allowed to escape bg check due to high-pri message 1390 */ 1391 int[] mDeviceIdleTempWhitelist = new int[0]; 1392 1393 static final class PendingTempWhitelist { 1394 final int targetUid; 1395 final long duration; 1396 final String tag; 1397 1398 PendingTempWhitelist(int _targetUid, long _duration, String _tag) { 1399 targetUid = _targetUid; 1400 duration = _duration; 1401 tag = _tag; 1402 } 1403 1404 void writeToProto(ProtoOutputStream proto, long fieldId) { 1405 final long token = proto.start(fieldId); 1406 proto.write(ActivityManagerServiceDumpProcessesProto.PendingTempWhitelist.TARGET_UID, targetUid); 1407 proto.write(ActivityManagerServiceDumpProcessesProto.PendingTempWhitelist.DURATION_MS, duration); 1408 proto.write(ActivityManagerServiceDumpProcessesProto.PendingTempWhitelist.TAG, tag); 1409 proto.end(token); 1410 } 1411 } 1412 1413 final SparseArray<PendingTempWhitelist> mPendingTempWhitelist = new SparseArray<>(); 1414 1415 /** 1416 * Information about and control over application operations 1417 */ 1418 final AppOpsService mAppOpsService; 1419 1420 /** Current sequencing integer of the configuration, for skipping old configurations. */ 1421 private int mConfigurationSeq; 1422 1423 /** 1424 * Temp object used when global and/or display override configuration is updated. It is also 1425 * sent to outer world instead of {@link #getGlobalConfiguration} because we don't trust 1426 * anyone... 1427 */ 1428 private Configuration mTempConfig = new Configuration(); 1429 1430 private final UpdateConfigurationResult mTmpUpdateConfigurationResult = 1431 new UpdateConfigurationResult(); 1432 private static final class UpdateConfigurationResult { 1433 // Configuration changes that were updated. 1434 int changes; 1435 // If the activity was relaunched to match the new configuration. 1436 boolean activityRelaunched; 1437 1438 void reset() { 1439 changes = 0; 1440 activityRelaunched = false; 1441 } 1442 } 1443 1444 boolean mSuppressResizeConfigChanges; 1445 1446 /** 1447 * Hardware-reported OpenGLES version. 1448 */ 1449 final int GL_ES_VERSION; 1450 1451 /** 1452 * List of initialization arguments to pass to all processes when binding applications to them. 1453 * For example, references to the commonly used services. 1454 */ 1455 ArrayMap<String, IBinder> mAppBindArgs; 1456 ArrayMap<String, IBinder> mIsolatedAppBindArgs; 1457 1458 /** 1459 * Temporary to avoid allocations. Protected by main lock. 1460 */ 1461 final StringBuilder mStringBuilder = new StringBuilder(256); 1462 1463 /** 1464 * Used to control how we initialize the service. 1465 */ 1466 ComponentName mTopComponent; 1467 String mTopAction = Intent.ACTION_MAIN; 1468 String mTopData; 1469 1470 volatile boolean mProcessesReady = false; 1471 volatile boolean mSystemReady = false; 1472 volatile boolean mOnBattery = false; 1473 volatile int mFactoryTest; 1474 1475 @GuardedBy("this") boolean mBooting = false; 1476 @GuardedBy("this") boolean mCallFinishBooting = false; 1477 @GuardedBy("this") boolean mBootAnimationComplete = false; 1478 @GuardedBy("this") boolean mLaunchWarningShown = false; 1479 private @GuardedBy("this") boolean mCheckedForSetup = false; 1480 1481 final Context mContext; 1482 1483 /** 1484 * This Context is themable and meant for UI display (AlertDialogs, etc.). The theme can 1485 * change at runtime. Use mContext for non-UI purposes. 1486 */ 1487 final Context mUiContext; 1488 1489 /** 1490 * The time at which we will allow normal application switches again, 1491 * after a call to {@link #stopAppSwitches()}. 1492 */ 1493 long mAppSwitchesAllowedTime; 1494 1495 /** 1496 * This is set to true after the first switch after mAppSwitchesAllowedTime 1497 * is set; any switches after that will clear the time. 1498 */ 1499 boolean mDidAppSwitch; 1500 1501 /** 1502 * Last time (in uptime) at which we checked for power usage. 1503 */ 1504 long mLastPowerCheckUptime; 1505 1506 /** 1507 * Set while we are wanting to sleep, to prevent any 1508 * activities from being started/resumed. 1509 * 1510 * TODO(b/33594039): Clarify the actual state transitions represented by mSleeping. 1511 * 1512 * Currently mSleeping is set to true when transitioning into the sleep state, and remains true 1513 * while in the sleep state until there is a pending transition out of sleep, in which case 1514 * mSleeping is set to false, and remains false while awake. 1515 * 1516 * Whether mSleeping can quickly toggled between true/false without the device actually 1517 * display changing states is undefined. 1518 */ 1519 private boolean mSleeping = false; 1520 1521 /** 1522 * The process state used for processes that are running the top activities. 1523 * This changes between TOP and TOP_SLEEPING to following mSleeping. 1524 */ 1525 int mTopProcessState = ActivityManager.PROCESS_STATE_TOP; 1526 1527 /** 1528 * Set while we are running a voice interaction. This overrides 1529 * sleeping while it is active. 1530 */ 1531 IVoiceInteractionSession mRunningVoice; 1532 1533 /** 1534 * For some direct access we need to power manager. 1535 */ 1536 PowerManagerInternal mLocalPowerManager; 1537 1538 /** 1539 * We want to hold a wake lock while running a voice interaction session, since 1540 * this may happen with the screen off and we need to keep the CPU running to 1541 * be able to continue to interact with the user. 1542 */ 1543 PowerManager.WakeLock mVoiceWakeLock; 1544 1545 /** 1546 * State of external calls telling us if the device is awake or asleep. 1547 */ 1548 private int mWakefulness = PowerManagerInternal.WAKEFULNESS_AWAKE; 1549 1550 /** 1551 * State of external calls telling us if the device is awake or asleep. 1552 */ 1553 private boolean mKeyguardShown = false; 1554 1555 /** 1556 * Set if we are shutting down the system, similar to sleeping. 1557 */ 1558 boolean mShuttingDown = false; 1559 1560 /** 1561 * Current sequence id for oom_adj computation traversal. 1562 */ 1563 int mAdjSeq = 0; 1564 1565 /** 1566 * Current sequence id for process LRU updating. 1567 */ 1568 int mLruSeq = 0; 1569 1570 /** 1571 * Keep track of the non-cached/empty process we last found, to help 1572 * determine how to distribute cached/empty processes next time. 1573 */ 1574 int mNumNonCachedProcs = 0; 1575 1576 /** 1577 * Keep track of the number of cached hidden procs, to balance oom adj 1578 * distribution between those and empty procs. 1579 */ 1580 int mNumCachedHiddenProcs = 0; 1581 1582 /** 1583 * Keep track of the number of service processes we last found, to 1584 * determine on the next iteration which should be B services. 1585 */ 1586 int mNumServiceProcs = 0; 1587 int mNewNumAServiceProcs = 0; 1588 int mNewNumServiceProcs = 0; 1589 1590 /** 1591 * Allow the current computed overall memory level of the system to go down? 1592 * This is set to false when we are killing processes for reasons other than 1593 * memory management, so that the now smaller process list will not be taken as 1594 * an indication that memory is tighter. 1595 */ 1596 boolean mAllowLowerMemLevel = false; 1597 1598 /** 1599 * The last computed memory level, for holding when we are in a state that 1600 * processes are going away for other reasons. 1601 */ 1602 int mLastMemoryLevel = ProcessStats.ADJ_MEM_FACTOR_NORMAL; 1603 1604 /** 1605 * The last total number of process we have, to determine if changes actually look 1606 * like a shrinking number of process due to lower RAM. 1607 */ 1608 int mLastNumProcesses; 1609 1610 /** 1611 * The uptime of the last time we performed idle maintenance. 1612 */ 1613 long mLastIdleTime = SystemClock.uptimeMillis(); 1614 1615 /** 1616 * Total time spent with RAM that has been added in the past since the last idle time. 1617 */ 1618 long mLowRamTimeSinceLastIdle = 0; 1619 1620 /** 1621 * If RAM is currently low, when that horrible situation started. 1622 */ 1623 long mLowRamStartTime = 0; 1624 1625 /** 1626 * For reporting to battery stats the current top application. 1627 */ 1628 private String mCurResumedPackage = null; 1629 private int mCurResumedUid = -1; 1630 1631 /** 1632 * For reporting to battery stats the apps currently running foreground 1633 * service. The ProcessMap is package/uid tuples; each of these contain 1634 * an array of the currently foreground processes. 1635 */ 1636 final ProcessMap<ArrayList<ProcessRecord>> mForegroundPackages 1637 = new ProcessMap<ArrayList<ProcessRecord>>(); 1638 1639 /** 1640 * Set if the systemServer made a call to enterSafeMode. 1641 */ 1642 boolean mSafeMode; 1643 1644 /** 1645 * If true, we are running under a test environment so will sample PSS from processes 1646 * much more rapidly to try to collect better data when the tests are rapidly 1647 * running through apps. 1648 */ 1649 boolean mTestPssMode = false; 1650 1651 String mDebugApp = null; 1652 boolean mWaitForDebugger = false; 1653 boolean mDebugTransient = false; 1654 String mOrigDebugApp = null; 1655 boolean mOrigWaitForDebugger = false; 1656 boolean mAlwaysFinishActivities = false; 1657 boolean mForceResizableActivities; 1658 /** 1659 * Flag that indicates if multi-window is enabled. 1660 * 1661 * For any particular form of multi-window to be enabled, generic multi-window must be enabled 1662 * in {@link com.android.internal.R.bool#config_supportsMultiWindow} config or 1663 * {@link Settings.Global#DEVELOPMENT_FORCE_RESIZABLE_ACTIVITIES} development option set. 1664 * At least one of the forms of multi-window must be enabled in order for this flag to be 1665 * initialized to 'true'. 1666 * 1667 * @see #mSupportsSplitScreenMultiWindow 1668 * @see #mSupportsFreeformWindowManagement 1669 * @see #mSupportsPictureInPicture 1670 * @see #mSupportsMultiDisplay 1671 */ 1672 boolean mSupportsMultiWindow; 1673 boolean mSupportsSplitScreenMultiWindow; 1674 boolean mSupportsFreeformWindowManagement; 1675 boolean mSupportsPictureInPicture; 1676 boolean mSupportsMultiDisplay; 1677 boolean mSupportsLeanbackOnly; 1678 IActivityController mController = null; 1679 boolean mControllerIsAMonkey = false; 1680 String mProfileApp = null; 1681 ProcessRecord mProfileProc = null; 1682 ProfilerInfo mProfilerInfo = null; 1683 1684 /** 1685 * Stores a map of process name -> agent string. When a process is started and mAgentAppMap 1686 * is not null, this map is checked and the mapped agent installed during bind-time. Note: 1687 * A non-null agent in mProfileInfo overrides this. 1688 */ 1689 private @Nullable Map<String, String> mAppAgentMap = null; 1690 1691 int mProfileType = 0; 1692 final ProcessMap<Pair<Long, String>> mMemWatchProcesses = new ProcessMap<>(); 1693 String mMemWatchDumpProcName; 1694 String mMemWatchDumpFile; 1695 int mMemWatchDumpPid; 1696 int mMemWatchDumpUid; 1697 String mTrackAllocationApp = null; 1698 String mNativeDebuggingApp = null; 1699 1700 final long[] mTmpLong = new long[3]; 1701 1702 private final ArraySet<BroadcastQueue> mTmpBroadcastQueue = new ArraySet(); 1703 1704 /** 1705 * A global counter for generating sequence numbers. 1706 * This value will be used when incrementing sequence numbers in individual uidRecords. 1707 * 1708 * Having a global counter ensures that seq numbers are monotonically increasing for a 1709 * particular uid even when the uidRecord is re-created. 1710 */ 1711 @GuardedBy("this") 1712 @VisibleForTesting 1713 long mProcStateSeqCounter = 0; 1714 1715 /** 1716 * A global counter for generating sequence numbers to uniquely identify pending process starts. 1717 */ 1718 @GuardedBy("this") 1719 private long mProcStartSeqCounter = 0; 1720 1721 /** 1722 * Contains {@link ProcessRecord} objects for pending process starts. 1723 * 1724 * Mapping: {@link #mProcStartSeqCounter} -> {@link ProcessRecord} 1725 */ 1726 @GuardedBy("this") 1727 private final LongSparseArray<ProcessRecord> mPendingStarts = new LongSparseArray<>(); 1728 1729 private final Injector mInjector; 1730 1731 static final class ProcessChangeItem { 1732 static final int CHANGE_ACTIVITIES = 1<<0; 1733 int changes; 1734 int uid; 1735 int pid; 1736 int processState; 1737 boolean foregroundActivities; 1738 } 1739 1740 static final class UidObserverRegistration { 1741 final int uid; 1742 final String pkg; 1743 final int which; 1744 final int cutpoint; 1745 1746 /** 1747 * Total # of callback calls that took more than {@link #SLOW_UID_OBSERVER_THRESHOLD_MS}. 1748 * We show it in dumpsys. 1749 */ 1750 int mSlowDispatchCount; 1751 1752 /** Max time it took for each dispatch. */ 1753 int mMaxDispatchTime; 1754 1755 final SparseIntArray lastProcStates; 1756 1757 // Please keep the enum lists in sync 1758 private static int[] ORIG_ENUMS = new int[]{ 1759 ActivityManager.UID_OBSERVER_IDLE, 1760 ActivityManager.UID_OBSERVER_ACTIVE, 1761 ActivityManager.UID_OBSERVER_GONE, 1762 ActivityManager.UID_OBSERVER_PROCSTATE, 1763 }; 1764 private static int[] PROTO_ENUMS = new int[]{ 1765 ActivityManagerProto.UID_OBSERVER_FLAG_IDLE, 1766 ActivityManagerProto.UID_OBSERVER_FLAG_ACTIVE, 1767 ActivityManagerProto.UID_OBSERVER_FLAG_GONE, 1768 ActivityManagerProto.UID_OBSERVER_FLAG_PROCSTATE, 1769 }; 1770 1771 UidObserverRegistration(int _uid, String _pkg, int _which, int _cutpoint) { 1772 uid = _uid; 1773 pkg = _pkg; 1774 which = _which; 1775 cutpoint = _cutpoint; 1776 if (cutpoint >= ActivityManager.MIN_PROCESS_STATE) { 1777 lastProcStates = new SparseIntArray(); 1778 } else { 1779 lastProcStates = null; 1780 } 1781 } 1782 1783 void writeToProto(ProtoOutputStream proto, long fieldId) { 1784 final long token = proto.start(fieldId); 1785 proto.write(UidObserverRegistrationProto.UID, uid); 1786 proto.write(UidObserverRegistrationProto.PACKAGE, pkg); 1787 ProtoUtils.writeBitWiseFlagsToProtoEnum(proto, UidObserverRegistrationProto.FLAGS, 1788 which, ORIG_ENUMS, PROTO_ENUMS); 1789 proto.write(UidObserverRegistrationProto.CUT_POINT, cutpoint); 1790 if (lastProcStates != null) { 1791 final int NI = lastProcStates.size(); 1792 for (int i=0; i<NI; i++) { 1793 final long pToken = proto.start(UidObserverRegistrationProto.LAST_PROC_STATES); 1794 proto.write(UidObserverRegistrationProto.ProcState.UID, lastProcStates.keyAt(i)); 1795 proto.write(UidObserverRegistrationProto.ProcState.STATE, lastProcStates.valueAt(i)); 1796 proto.end(pToken); 1797 } 1798 } 1799 proto.end(token); 1800 } 1801 } 1802 1803 final List<ScreenObserver> mScreenObservers = new ArrayList<>(); 1804 1805 final RemoteCallbackList<IProcessObserver> mProcessObservers = new RemoteCallbackList<>(); 1806 ProcessChangeItem[] mActiveProcessChanges = new ProcessChangeItem[5]; 1807 1808 final ArrayList<ProcessChangeItem> mPendingProcessChanges = new ArrayList<>(); 1809 final ArrayList<ProcessChangeItem> mAvailProcessChanges = new ArrayList<>(); 1810 1811 final RemoteCallbackList<IUidObserver> mUidObservers = new RemoteCallbackList<>(); 1812 UidRecord.ChangeItem[] mActiveUidChanges = new UidRecord.ChangeItem[5]; 1813 1814 final ArrayList<UidRecord.ChangeItem> mPendingUidChanges = new ArrayList<>(); 1815 final ArrayList<UidRecord.ChangeItem> mAvailUidChanges = new ArrayList<>(); 1816 1817 OomAdjObserver mCurOomAdjObserver; 1818 int mCurOomAdjUid; 1819 1820 interface OomAdjObserver { 1821 void onOomAdjMessage(String msg); 1822 } 1823 1824 /** 1825 * Runtime CPU use collection thread. This object's lock is used to 1826 * perform synchronization with the thread (notifying it to run). 1827 */ 1828 final Thread mProcessCpuThread; 1829 1830 /** 1831 * Used to collect per-process CPU use for ANRs, battery stats, etc. 1832 * Must acquire this object's lock when accessing it. 1833 * NOTE: this lock will be held while doing long operations (trawling 1834 * through all processes in /proc), so it should never be acquired by 1835 * any critical paths such as when holding the main activity manager lock. 1836 */ 1837 final ProcessCpuTracker mProcessCpuTracker = new ProcessCpuTracker( 1838 MONITOR_THREAD_CPU_USAGE); 1839 final AtomicLong mLastCpuTime = new AtomicLong(0); 1840 final AtomicBoolean mProcessCpuMutexFree = new AtomicBoolean(true); 1841 final CountDownLatch mProcessCpuInitLatch = new CountDownLatch(1); 1842 1843 long mLastWriteTime = 0; 1844 1845 /** 1846 * Used to retain an update lock when the foreground activity is in 1847 * immersive mode. 1848 */ 1849 final UpdateLock mUpdateLock = new UpdateLock("immersive"); 1850 1851 /** 1852 * Set to true after the system has finished booting. 1853 */ 1854 boolean mBooted = false; 1855 1856 /** 1857 * Current boot phase. 1858 */ 1859 int mBootPhase; 1860 1861 WindowManagerService mWindowManager; 1862 final ActivityThread mSystemThread; 1863 1864 private final class AppDeathRecipient implements IBinder.DeathRecipient { 1865 final ProcessRecord mApp; 1866 final int mPid; 1867 final IApplicationThread mAppThread; 1868 1869 AppDeathRecipient(ProcessRecord app, int pid, 1870 IApplicationThread thread) { 1871 if (DEBUG_ALL) Slog.v( 1872 TAG, "New death recipient " + this 1873 + " for thread " + thread.asBinder()); 1874 mApp = app; 1875 mPid = pid; 1876 mAppThread = thread; 1877 } 1878 1879 @Override 1880 public void binderDied() { 1881 if (DEBUG_ALL) Slog.v( 1882 TAG, "Death received in " + this 1883 + " for thread " + mAppThread.asBinder()); 1884 synchronized(ActivityManagerService.this) { 1885 appDiedLocked(mApp, mPid, mAppThread, true); 1886 } 1887 } 1888 } 1889 1890 static final int SHOW_ERROR_UI_MSG = 1; 1891 static final int SHOW_NOT_RESPONDING_UI_MSG = 2; 1892 static final int SHOW_FACTORY_ERROR_UI_MSG = 3; 1893 static final int UPDATE_CONFIGURATION_MSG = 4; 1894 static final int GC_BACKGROUND_PROCESSES_MSG = 5; 1895 static final int WAIT_FOR_DEBUGGER_UI_MSG = 6; 1896 static final int SERVICE_TIMEOUT_MSG = 12; 1897 static final int UPDATE_TIME_ZONE = 13; 1898 static final int SHOW_UID_ERROR_UI_MSG = 14; 1899 static final int SHOW_FINGERPRINT_ERROR_UI_MSG = 15; 1900 static final int PROC_START_TIMEOUT_MSG = 20; 1901 static final int KILL_APPLICATION_MSG = 22; 1902 static final int FINALIZE_PENDING_INTENT_MSG = 23; 1903 static final int POST_HEAVY_NOTIFICATION_MSG = 24; 1904 static final int CANCEL_HEAVY_NOTIFICATION_MSG = 25; 1905 static final int SHOW_STRICT_MODE_VIOLATION_UI_MSG = 26; 1906 static final int CHECK_EXCESSIVE_POWER_USE_MSG = 27; 1907 static final int CLEAR_DNS_CACHE_MSG = 28; 1908 static final int UPDATE_HTTP_PROXY_MSG = 29; 1909 static final int SHOW_COMPAT_MODE_DIALOG_UI_MSG = 30; 1910 static final int DISPATCH_PROCESSES_CHANGED_UI_MSG = 31; 1911 static final int DISPATCH_PROCESS_DIED_UI_MSG = 32; 1912 static final int REPORT_MEM_USAGE_MSG = 33; 1913 static final int IMMERSIVE_MODE_LOCK_MSG = 37; 1914 static final int PERSIST_URI_GRANTS_MSG = 38; 1915 static final int UPDATE_TIME_PREFERENCE_MSG = 41; 1916 static final int ENTER_ANIMATION_COMPLETE_MSG = 44; 1917 static final int FINISH_BOOTING_MSG = 45; 1918 static final int SEND_LOCALE_TO_MOUNT_DAEMON_MSG = 47; 1919 static final int DISMISS_DIALOG_UI_MSG = 48; 1920 static final int NOTIFY_CLEARTEXT_NETWORK_MSG = 49; 1921 static final int POST_DUMP_HEAP_NOTIFICATION_MSG = 50; 1922 static final int DELETE_DUMPHEAP_MSG = 51; 1923 static final int DISPATCH_UIDS_CHANGED_UI_MSG = 53; 1924 static final int REPORT_TIME_TRACKER_MSG = 54; 1925 static final int SHUTDOWN_UI_AUTOMATION_CONNECTION_MSG = 56; 1926 static final int CONTENT_PROVIDER_PUBLISH_TIMEOUT_MSG = 57; 1927 static final int IDLE_UIDS_MSG = 58; 1928 static final int LOG_STACK_STATE = 60; 1929 static final int VR_MODE_CHANGE_MSG = 61; 1930 static final int HANDLE_TRUST_STORAGE_UPDATE_MSG = 63; 1931 static final int DISPATCH_SCREEN_AWAKE_MSG = 64; 1932 static final int DISPATCH_SCREEN_KEYGUARD_MSG = 65; 1933 static final int SERVICE_FOREGROUND_TIMEOUT_MSG = 66; 1934 static final int DISPATCH_PENDING_INTENT_CANCEL_MSG = 67; 1935 static final int PUSH_TEMP_WHITELIST_UI_MSG = 68; 1936 static final int SERVICE_FOREGROUND_CRASH_MSG = 69; 1937 static final int DISPATCH_OOM_ADJ_OBSERVER_MSG = 70; 1938 1939 static final int FIRST_ACTIVITY_STACK_MSG = 100; 1940 static final int FIRST_BROADCAST_QUEUE_MSG = 200; 1941 static final int FIRST_COMPAT_MODE_MSG = 300; 1942 static final int FIRST_SUPERVISOR_STACK_MSG = 100; 1943 1944 static final String SERVICE_RECORD_KEY = "servicerecord"; 1945 1946 static ServiceThread sKillThread = null; 1947 static KillHandler sKillHandler = null; 1948 1949 CompatModeDialog mCompatModeDialog; 1950 long mLastMemUsageReportTime = 0; 1951 1952 /** 1953 * Flag whether the current user is a "monkey", i.e. whether 1954 * the UI is driven by a UI automation tool. 1955 */ 1956 private boolean mUserIsMonkey; 1957 1958 /** The dimensions of the thumbnails in the Recents UI. */ 1959 int mThumbnailWidth; 1960 int mThumbnailHeight; 1961 float mFullscreenThumbnailScale; 1962 1963 final ServiceThread mHandlerThread; 1964 final MainHandler mHandler; 1965 final Handler mUiHandler; 1966 final ServiceThread mProcStartHandlerThread; 1967 final Handler mProcStartHandler; 1968 1969 final ActivityManagerConstants mConstants; 1970 1971 // Encapsulates the global setting "hidden_api_blacklist_exemptions" 1972 final HiddenApiSettings mHiddenApiBlacklist; 1973 1974 PackageManagerInternal mPackageManagerInt; 1975 1976 // VoiceInteraction session ID that changes for each new request except when 1977 // being called for multiwindow assist in a single session. 1978 private int mViSessionId = 1000; 1979 1980 final boolean mPermissionReviewRequired; 1981 1982 boolean mHasHeavyWeightFeature; 1983 1984 /** 1985 * Whether to force background check on all apps (for battery saver) or not. 1986 */ 1987 boolean mForceBackgroundCheck; 1988 1989 private static String sTheRealBuildSerial = Build.UNKNOWN; 1990 1991 /** 1992 * Current global configuration information. Contains general settings for the entire system, 1993 * also corresponds to the merged configuration of the default display. 1994 */ 1995 Configuration getGlobalConfiguration() { 1996 return mStackSupervisor.getConfiguration(); 1997 } 1998 1999 final class KillHandler extends Handler { 2000 static final int KILL_PROCESS_GROUP_MSG = 4000; 2001 2002 public KillHandler(Looper looper) { 2003 super(looper, null, true); 2004 } 2005 2006 @Override 2007 public void handleMessage(Message msg) { 2008 switch (msg.what) { 2009 case KILL_PROCESS_GROUP_MSG: 2010 { 2011 Trace.traceBegin(Trace.TRACE_TAG_ACTIVITY_MANAGER, "killProcessGroup"); 2012 Process.killProcessGroup(msg.arg1 /* uid */, msg.arg2 /* pid */); 2013 Trace.traceEnd(Trace.TRACE_TAG_ACTIVITY_MANAGER); 2014 } 2015 break; 2016 2017 default: 2018 super.handleMessage(msg); 2019 } 2020 } 2021 } 2022 2023 final class UiHandler extends Handler { 2024 public UiHandler() { 2025 super(com.android.server.UiThread.get().getLooper(), null, true); 2026 } 2027 2028 @Override 2029 public void handleMessage(Message msg) { 2030 switch (msg.what) { 2031 case SHOW_ERROR_UI_MSG: { 2032 mAppErrors.handleShowAppErrorUi(msg); 2033 ensureBootCompleted(); 2034 } break; 2035 case SHOW_NOT_RESPONDING_UI_MSG: { 2036 mAppErrors.handleShowAnrUi(msg); 2037 ensureBootCompleted(); 2038 } break; 2039 case SHOW_STRICT_MODE_VIOLATION_UI_MSG: { 2040 HashMap<String, Object> data = (HashMap<String, Object>) msg.obj; 2041 synchronized (ActivityManagerService.this) { 2042 ProcessRecord proc = (ProcessRecord) data.get("app"); 2043 if (proc == null) { 2044 Slog.e(TAG, "App not found when showing strict mode dialog."); 2045 break; 2046 } 2047 if (proc.crashDialog != null) { 2048 Slog.e(TAG, "App already has strict mode dialog: " + proc); 2049 return; 2050 } 2051 AppErrorResult res = (AppErrorResult) data.get("result"); 2052 if (mShowDialogs && !mSleeping && !mShuttingDown) { 2053 Dialog d = new StrictModeViolationDialog(mUiContext, 2054 ActivityManagerService.this, res, proc); 2055 d.show(); 2056 proc.crashDialog = d; 2057 } else { 2058 // The device is asleep, so just pretend that the user 2059 // saw a crash dialog and hit "force quit". 2060 res.set(0); 2061 } 2062 } 2063 ensureBootCompleted(); 2064 } break; 2065 case SHOW_FACTORY_ERROR_UI_MSG: { 2066 Dialog d = new FactoryErrorDialog( 2067 mUiContext, msg.getData().getCharSequence("msg")); 2068 d.show(); 2069 ensureBootCompleted(); 2070 } break; 2071 case WAIT_FOR_DEBUGGER_UI_MSG: { 2072 synchronized (ActivityManagerService.this) { 2073 ProcessRecord app = (ProcessRecord)msg.obj; 2074 if (msg.arg1 != 0) { 2075 if (!app.waitedForDebugger) { 2076 Dialog d = new AppWaitingForDebuggerDialog( 2077 ActivityManagerService.this, 2078 mUiContext, app); 2079 app.waitDialog = d; 2080 app.waitedForDebugger = true; 2081 d.show(); 2082 } 2083 } else { 2084 if (app.waitDialog != null) { 2085 app.waitDialog.dismiss(); 2086 app.waitDialog = null; 2087 } 2088 } 2089 } 2090 } break; 2091 case SHOW_UID_ERROR_UI_MSG: { 2092 if (mShowDialogs) { 2093 AlertDialog d = new BaseErrorDialog(mUiContext); 2094 d.getWindow().setType(WindowManager.LayoutParams.TYPE_SYSTEM_ERROR); 2095 d.setCancelable(false); 2096 d.setTitle(mUiContext.getText(R.string.android_system_label)); 2097 d.setMessage(mUiContext.getText(R.string.system_error_wipe_data)); 2098 d.setButton(DialogInterface.BUTTON_POSITIVE, mUiContext.getText(R.string.ok), 2099 obtainMessage(DISMISS_DIALOG_UI_MSG, d)); 2100 d.show(); 2101 } 2102 } break; 2103 case SHOW_FINGERPRINT_ERROR_UI_MSG: { 2104 if (mShowDialogs) { 2105 AlertDialog d = new BaseErrorDialog(mUiContext); 2106 d.getWindow().setType(WindowManager.LayoutParams.TYPE_SYSTEM_ERROR); 2107 d.setCancelable(false); 2108 d.setTitle(mUiContext.getText(R.string.android_system_label)); 2109 d.setMessage(mUiContext.getText(R.string.system_error_manufacturer)); 2110 d.setButton(DialogInterface.BUTTON_POSITIVE, mUiContext.getText(R.string.ok), 2111 obtainMessage(DISMISS_DIALOG_UI_MSG, d)); 2112 d.show(); 2113 } 2114 } break; 2115 case SHOW_COMPAT_MODE_DIALOG_UI_MSG: { 2116 synchronized (ActivityManagerService.this) { 2117 ActivityRecord ar = (ActivityRecord) msg.obj; 2118 if (mCompatModeDialog != null) { 2119 if (mCompatModeDialog.mAppInfo.packageName.equals( 2120 ar.info.applicationInfo.packageName)) { 2121 return; 2122 } 2123 mCompatModeDialog.dismiss(); 2124 mCompatModeDialog = null; 2125 } 2126 if (ar != null && false) { 2127 if (mCompatModePackages.getPackageAskCompatModeLocked( 2128 ar.packageName)) { 2129 int mode = mCompatModePackages.computeCompatModeLocked( 2130 ar.info.applicationInfo); 2131 if (mode == ActivityManager.COMPAT_MODE_DISABLED 2132 || mode == ActivityManager.COMPAT_MODE_ENABLED) { 2133 mCompatModeDialog = new CompatModeDialog( 2134 ActivityManagerService.this, mUiContext, 2135 ar.info.applicationInfo); 2136 mCompatModeDialog.show(); 2137 } 2138 } 2139 } 2140 } 2141 break; 2142 } 2143 case DISMISS_DIALOG_UI_MSG: { 2144 final Dialog d = (Dialog) msg.obj; 2145 d.dismiss(); 2146 break; 2147 } 2148 case DISPATCH_PROCESSES_CHANGED_UI_MSG: { 2149 dispatchProcessesChanged(); 2150 break; 2151 } 2152 case DISPATCH_PROCESS_DIED_UI_MSG: { 2153 final int pid = msg.arg1; 2154 final int uid = msg.arg2; 2155 dispatchProcessDied(pid, uid); 2156 break; 2157 } 2158 case DISPATCH_UIDS_CHANGED_UI_MSG: { 2159 dispatchUidsChanged(); 2160 } break; 2161 case DISPATCH_OOM_ADJ_OBSERVER_MSG: { 2162 dispatchOomAdjObserver((String)msg.obj); 2163 } break; 2164 case PUSH_TEMP_WHITELIST_UI_MSG: { 2165 pushTempWhitelist(); 2166 } break; 2167 } 2168 } 2169 } 2170 2171 final class MainHandler extends Handler { 2172 public MainHandler(Looper looper) { 2173 super(looper, null, true); 2174 } 2175 2176 @Override 2177 public void handleMessage(Message msg) { 2178 switch (msg.what) { 2179 case UPDATE_CONFIGURATION_MSG: { 2180 final ContentResolver resolver = mContext.getContentResolver(); 2181 Settings.System.putConfigurationForUser(resolver, (Configuration) msg.obj, 2182 msg.arg1); 2183 } break; 2184 case GC_BACKGROUND_PROCESSES_MSG: { 2185 synchronized (ActivityManagerService.this) { 2186 performAppGcsIfAppropriateLocked(); 2187 } 2188 } break; 2189 case SERVICE_TIMEOUT_MSG: { 2190 mServices.serviceTimeout((ProcessRecord)msg.obj); 2191 } break; 2192 case SERVICE_FOREGROUND_TIMEOUT_MSG: { 2193 mServices.serviceForegroundTimeout((ServiceRecord)msg.obj); 2194 } break; 2195 case SERVICE_FOREGROUND_CRASH_MSG: { 2196 mServices.serviceForegroundCrash( 2197 (ProcessRecord) msg.obj, msg.getData().getCharSequence(SERVICE_RECORD_KEY)); 2198 } break; 2199 case DISPATCH_PENDING_INTENT_CANCEL_MSG: { 2200 RemoteCallbackList<IResultReceiver> callbacks 2201 = (RemoteCallbackList<IResultReceiver>)msg.obj; 2202 int N = callbacks.beginBroadcast(); 2203 for (int i = 0; i < N; i++) { 2204 try { 2205 callbacks.getBroadcastItem(i).send(Activity.RESULT_CANCELED, null); 2206 } catch (RemoteException e) { 2207 } 2208 } 2209 callbacks.finishBroadcast(); 2210 } break; 2211 case UPDATE_TIME_ZONE: { 2212 synchronized (ActivityManagerService.this) { 2213 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 2214 ProcessRecord r = mLruProcesses.get(i); 2215 if (r.thread != null) { 2216 try { 2217 r.thread.updateTimeZone(); 2218 } catch (RemoteException ex) { 2219 Slog.w(TAG, "Failed to update time zone for: " + r.info.processName); 2220 } 2221 } 2222 } 2223 } 2224 } break; 2225 case CLEAR_DNS_CACHE_MSG: { 2226 synchronized (ActivityManagerService.this) { 2227 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 2228 ProcessRecord r = mLruProcesses.get(i); 2229 if (r.thread != null) { 2230 try { 2231 r.thread.clearDnsCache(); 2232 } catch (RemoteException ex) { 2233 Slog.w(TAG, "Failed to clear dns cache for: " + r.info.processName); 2234 } 2235 } 2236 } 2237 } 2238 } break; 2239 case UPDATE_HTTP_PROXY_MSG: { 2240 ProxyInfo proxy = (ProxyInfo)msg.obj; 2241 String host = ""; 2242 String port = ""; 2243 String exclList = ""; 2244 Uri pacFileUrl = Uri.EMPTY; 2245 if (proxy != null) { 2246 host = proxy.getHost(); 2247 port = Integer.toString(proxy.getPort()); 2248 exclList = proxy.getExclusionListAsString(); 2249 pacFileUrl = proxy.getPacFileUrl(); 2250 } 2251 synchronized (ActivityManagerService.this) { 2252 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 2253 ProcessRecord r = mLruProcesses.get(i); 2254 // Don't dispatch to isolated processes as they can't access 2255 // ConnectivityManager and don't have network privileges anyway. 2256 if (r.thread != null && !r.isolated) { 2257 try { 2258 r.thread.setHttpProxy(host, port, exclList, pacFileUrl); 2259 } catch (RemoteException ex) { 2260 Slog.w(TAG, "Failed to update http proxy for: " + 2261 r.info.processName); 2262 } 2263 } 2264 } 2265 } 2266 } break; 2267 case PROC_START_TIMEOUT_MSG: { 2268 ProcessRecord app = (ProcessRecord)msg.obj; 2269 synchronized (ActivityManagerService.this) { 2270 processStartTimedOutLocked(app); 2271 } 2272 } break; 2273 case CONTENT_PROVIDER_PUBLISH_TIMEOUT_MSG: { 2274 ProcessRecord app = (ProcessRecord)msg.obj; 2275 synchronized (ActivityManagerService.this) { 2276 processContentProviderPublishTimedOutLocked(app); 2277 } 2278 } break; 2279 case KILL_APPLICATION_MSG: { 2280 synchronized (ActivityManagerService.this) { 2281 final int appId = msg.arg1; 2282 final int userId = msg.arg2; 2283 Bundle bundle = (Bundle)msg.obj; 2284 String pkg = bundle.getString("pkg"); 2285 String reason = bundle.getString("reason"); 2286 forceStopPackageLocked(pkg, appId, false, false, true, false, 2287 false, userId, reason); 2288 } 2289 } break; 2290 case FINALIZE_PENDING_INTENT_MSG: { 2291 ((PendingIntentRecord)msg.obj).completeFinalize(); 2292 } break; 2293 case POST_HEAVY_NOTIFICATION_MSG: { 2294 INotificationManager inm = NotificationManager.getService(); 2295 if (inm == null) { 2296 return; 2297 } 2298 2299 ActivityRecord root = (ActivityRecord)msg.obj; 2300 ProcessRecord process = root.app; 2301 if (process == null) { 2302 return; 2303 } 2304 2305 try { 2306 Context context = mContext.createPackageContext(process.info.packageName, 0); 2307 String text = mContext.getString(R.string.heavy_weight_notification, 2308 context.getApplicationInfo().loadLabel(context.getPackageManager())); 2309 Notification notification = 2310 new Notification.Builder(context, 2311 SystemNotificationChannels.HEAVY_WEIGHT_APP) 2312 .setSmallIcon(com.android.internal.R.drawable.stat_sys_adb) 2313 .setWhen(0) 2314 .setOngoing(true) 2315 .setTicker(text) 2316 .setColor(mContext.getColor( 2317 com.android.internal.R.color.system_notification_accent_color)) 2318 .setContentTitle(text) 2319 .setContentText( 2320 mContext.getText(R.string.heavy_weight_notification_detail)) 2321 .setContentIntent(PendingIntent.getActivityAsUser(mContext, 0, 2322 root.intent, PendingIntent.FLAG_CANCEL_CURRENT, null, 2323 new UserHandle(root.userId))) 2324 .build(); 2325 try { 2326 inm.enqueueNotificationWithTag("android", "android", null, 2327 SystemMessage.NOTE_HEAVY_WEIGHT_NOTIFICATION, 2328 notification, root.userId); 2329 } catch (RuntimeException e) { 2330 Slog.w(ActivityManagerService.TAG, 2331 "Error showing notification for heavy-weight app", e); 2332 } catch (RemoteException e) { 2333 } 2334 } catch (NameNotFoundException e) { 2335 Slog.w(TAG, "Unable to create context for heavy notification", e); 2336 } 2337 } break; 2338 case CANCEL_HEAVY_NOTIFICATION_MSG: { 2339 INotificationManager inm = NotificationManager.getService(); 2340 if (inm == null) { 2341 return; 2342 } 2343 try { 2344 inm.cancelNotificationWithTag("android", null, 2345 SystemMessage.NOTE_HEAVY_WEIGHT_NOTIFICATION, msg.arg1); 2346 } catch (RuntimeException e) { 2347 Slog.w(ActivityManagerService.TAG, 2348 "Error canceling notification for service", e); 2349 } catch (RemoteException e) { 2350 } 2351 } break; 2352 case CHECK_EXCESSIVE_POWER_USE_MSG: { 2353 synchronized (ActivityManagerService.this) { 2354 checkExcessivePowerUsageLocked(); 2355 removeMessages(CHECK_EXCESSIVE_POWER_USE_MSG); 2356 Message nmsg = obtainMessage(CHECK_EXCESSIVE_POWER_USE_MSG); 2357 sendMessageDelayed(nmsg, mConstants.POWER_CHECK_INTERVAL); 2358 } 2359 } break; 2360 case REPORT_MEM_USAGE_MSG: { 2361 final ArrayList<ProcessMemInfo> memInfos = (ArrayList<ProcessMemInfo>)msg.obj; 2362 Thread thread = new Thread() { 2363 @Override public void run() { 2364 reportMemUsage(memInfos); 2365 } 2366 }; 2367 thread.start(); 2368 break; 2369 } 2370 case IMMERSIVE_MODE_LOCK_MSG: { 2371 final boolean nextState = (msg.arg1 != 0); 2372 if (mUpdateLock.isHeld() != nextState) { 2373 if (DEBUG_IMMERSIVE) Slog.d(TAG_IMMERSIVE, 2374 "Applying new update lock state '" + nextState 2375 + "' for " + (ActivityRecord)msg.obj); 2376 if (nextState) { 2377 mUpdateLock.acquire(); 2378 } else { 2379 mUpdateLock.release(); 2380 } 2381 } 2382 break; 2383 } 2384 case PERSIST_URI_GRANTS_MSG: { 2385 writeGrantedUriPermissions(); 2386 break; 2387 } 2388 case UPDATE_TIME_PREFERENCE_MSG: { 2389 // The user's time format preference might have changed. 2390 // For convenience we re-use the Intent extra values. 2391 synchronized (ActivityManagerService.this) { 2392 for (int i = mLruProcesses.size() - 1; i >= 0; i--) { 2393 ProcessRecord r = mLruProcesses.get(i); 2394 if (r.thread != null) { 2395 try { 2396 r.thread.updateTimePrefs(msg.arg1); 2397 } catch (RemoteException ex) { 2398 Slog.w(TAG, "Failed to update preferences for: " 2399 + r.info.processName); 2400 } 2401 } 2402 } 2403 } 2404 break; 2405 } 2406 case ENTER_ANIMATION_COMPLETE_MSG: { 2407 synchronized (ActivityManagerService.this) { 2408 ActivityRecord r = ActivityRecord.forTokenLocked((IBinder) msg.obj); 2409 if (r != null && r.app != null && r.app.thread != null) { 2410 try { 2411 r.app.thread.scheduleEnterAnimationComplete(r.appToken); 2412 } catch (RemoteException e) { 2413 } 2414 } 2415 } 2416 break; 2417 } 2418 case FINISH_BOOTING_MSG: { 2419 if (msg.arg1 != 0) { 2420 Trace.traceBegin(Trace.TRACE_TAG_ACTIVITY_MANAGER, "FinishBooting"); 2421 finishBooting(); 2422 Trace.traceEnd(Trace.TRACE_TAG_ACTIVITY_MANAGER); 2423 } 2424 if (msg.arg2 != 0) { 2425 enableScreenAfterBoot(); 2426 } 2427 break; 2428 } 2429 case SEND_LOCALE_TO_MOUNT_DAEMON_MSG: { 2430 try { 2431 Locale l = (Locale) msg.obj; 2432 IBinder service = ServiceManager.getService("mount"); 2433 IStorageManager storageManager = IStorageManager.Stub.asInterface(service); 2434 Log.d(TAG, "Storing locale " + l.toLanguageTag() + " for decryption UI"); 2435 storageManager.setField(StorageManager.SYSTEM_LOCALE_KEY, l.toLanguageTag()); 2436 } catch (RemoteException e) { 2437 Log.e(TAG, "Error storing locale for decryption UI", e); 2438 } 2439 break; 2440 } 2441 case NOTIFY_CLEARTEXT_NETWORK_MSG: { 2442 final int uid = msg.arg1; 2443 final byte[] firstPacket = (byte[]) msg.obj; 2444 2445 synchronized (mPidsSelfLocked) { 2446 for (int i = 0; i < mPidsSelfLocked.size(); i++) { 2447 final ProcessRecord p = mPidsSelfLocked.valueAt(i); 2448 if (p.uid == uid) { 2449 try { 2450 p.thread.notifyCleartextNetwork(firstPacket); 2451 } catch (RemoteException ignored) { 2452 } 2453 } 2454 } 2455 } 2456 break; 2457 } 2458 case POST_DUMP_HEAP_NOTIFICATION_MSG: { 2459 final String procName; 2460 final int uid; 2461 final long memLimit; 2462 final String reportPackage; 2463 synchronized (ActivityManagerService.this) { 2464 procName = mMemWatchDumpProcName; 2465 uid = mMemWatchDumpUid; 2466 Pair<Long, String> val = mMemWatchProcesses.get(procName, uid); 2467 if (val == null) { 2468 val = mMemWatchProcesses.get(procName, 0); 2469 } 2470 if (val != null) { 2471 memLimit = val.first; 2472 reportPackage = val.second; 2473 } else { 2474 memLimit = 0; 2475 reportPackage = null; 2476 } 2477 } 2478 if (procName == null) { 2479 return; 2480 } 2481 2482 if (DEBUG_PSS) Slog.d(TAG_PSS, 2483 "Showing dump heap notification from " + procName + "/" + uid); 2484 2485 INotificationManager inm = NotificationManager.getService(); 2486 if (inm == null) { 2487 return; 2488 } 2489 2490 String text = mContext.getString(R.string.dump_heap_notification, procName); 2491 2492 2493 Intent deleteIntent = new Intent(); 2494 deleteIntent.setAction(DumpHeapActivity.ACTION_DELETE_DUMPHEAP); 2495 Intent intent = new Intent(); 2496 intent.setClassName("android", DumpHeapActivity.class.getName()); 2497 intent.putExtra(DumpHeapActivity.KEY_PROCESS, procName); 2498 intent.putExtra(DumpHeapActivity.KEY_SIZE, memLimit); 2499 if (reportPackage != null) { 2500 intent.putExtra(DumpHeapActivity.KEY_DIRECT_LAUNCH, reportPackage); 2501 } 2502 int userId = UserHandle.getUserId(uid); 2503 Notification notification = 2504 new Notification.Builder(mContext, SystemNotificationChannels.DEVELOPER) 2505 .setSmallIcon(com.android.internal.R.drawable.stat_sys_adb) 2506 .setWhen(0) 2507 .setOngoing(true) 2508 .setAutoCancel(true) 2509 .setTicker(text) 2510 .setColor(mContext.getColor( 2511 com.android.internal.R.color.system_notification_accent_color)) 2512 .setContentTitle(text) 2513 .setContentText( 2514 mContext.getText(R.string.dump_heap_notification_detail)) 2515 .setContentIntent(PendingIntent.getActivityAsUser(mContext, 0, 2516 intent, PendingIntent.FLAG_CANCEL_CURRENT, null, 2517 new UserHandle(userId))) 2518 .setDeleteIntent(PendingIntent.getBroadcastAsUser(mContext, 0, 2519 deleteIntent, 0, UserHandle.SYSTEM)) 2520 .build(); 2521 2522 try { 2523 inm.enqueueNotificationWithTag("android", "android", null, 2524 SystemMessage.NOTE_DUMP_HEAP_NOTIFICATION, 2525 notification, userId); 2526 } catch (RuntimeException e) { 2527 Slog.w(ActivityManagerService.TAG, 2528 "Error showing notification for dump heap", e); 2529 } catch (RemoteException e) { 2530 } 2531 } break; 2532 case DELETE_DUMPHEAP_MSG: { 2533 revokeUriPermission(ActivityThread.currentActivityThread().getApplicationThread(), 2534 null, DumpHeapActivity.JAVA_URI, 2535 Intent.FLAG_GRANT_READ_URI_PERMISSION 2536 | Intent.FLAG_GRANT_WRITE_URI_PERMISSION, 2537 UserHandle.myUserId()); 2538 synchronized (ActivityManagerService.this) { 2539 mMemWatchDumpFile = null; 2540 mMemWatchDumpProcName = null; 2541 mMemWatchDumpPid = -1; 2542 mMemWatchDumpUid = -1; 2543 } 2544 } break; 2545 case REPORT_TIME_TRACKER_MSG: { 2546 AppTimeTracker tracker = (AppTimeTracker)msg.obj; 2547 tracker.deliverResult(mContext); 2548 } break; 2549 case SHUTDOWN_UI_AUTOMATION_CONNECTION_MSG: { 2550 IUiAutomationConnection connection = (IUiAutomationConnection) msg.obj; 2551 try { 2552 connection.shutdown(); 2553 } catch (RemoteException e) { 2554 Slog.w(TAG, "Error shutting down UiAutomationConnection"); 2555 } 2556 // Only a UiAutomation can set this flag and now that 2557 // it is finished we make sure it is reset to its default. 2558 mUserIsMonkey = false; 2559 } break; 2560 case IDLE_UIDS_MSG: { 2561 idleUids(); 2562 } break; 2563 case VR_MODE_CHANGE_MSG: { 2564 if (!mVrController.onVrModeChanged((ActivityRecord) msg.obj)) { 2565 return; 2566 } 2567 synchronized (ActivityManagerService.this) { 2568 final boolean disableNonVrUi = mVrController.shouldDisableNonVrUiLocked(); 2569 mWindowManager.disableNonVrUi(disableNonVrUi); 2570 if (disableNonVrUi) { 2571 // If we are in a VR mode where Picture-in-Picture mode is unsupported, 2572 // then remove the pinned stack. 2573 mStackSupervisor.removeStacksInWindowingModes(WINDOWING_MODE_PINNED); 2574 } 2575 } 2576 } break; 2577 case DISPATCH_SCREEN_AWAKE_MSG: { 2578 final boolean isAwake = msg.arg1 != 0; 2579 for (int i = mScreenObservers.size() - 1; i >= 0; i--) { 2580 mScreenObservers.get(i).onAwakeStateChanged(isAwake); 2581 } 2582 } break; 2583 case DISPATCH_SCREEN_KEYGUARD_MSG: { 2584 final boolean isShowing = msg.arg1 != 0; 2585 for (int i = mScreenObservers.size() - 1; i >= 0; i--) { 2586 mScreenObservers.get(i).onKeyguardStateChanged(isShowing); 2587 } 2588 } break; 2589 case HANDLE_TRUST_STORAGE_UPDATE_MSG: { 2590 synchronized (ActivityManagerService.this) { 2591 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 2592 ProcessRecord r = mLruProcesses.get(i); 2593 if (r.thread != null) { 2594 try { 2595 r.thread.handleTrustStorageUpdate(); 2596 } catch (RemoteException ex) { 2597 Slog.w(TAG, "Failed to handle trust storage update for: " + 2598 r.info.processName); 2599 } 2600 } 2601 } 2602 } 2603 } break; 2604 } 2605 } 2606 }; 2607 2608 static final int COLLECT_PSS_BG_MSG = 1; 2609 2610 final Handler mBgHandler = new Handler(BackgroundThread.getHandler().getLooper()) { 2611 @Override 2612 public void handleMessage(Message msg) { 2613 switch (msg.what) { 2614 case COLLECT_PSS_BG_MSG: { 2615 long start = SystemClock.uptimeMillis(); 2616 MemInfoReader memInfo = null; 2617 synchronized (ActivityManagerService.this) { 2618 if (mFullPssPending) { 2619 mFullPssPending = false; 2620 memInfo = new MemInfoReader(); 2621 } 2622 } 2623 if (memInfo != null) { 2624 updateCpuStatsNow(); 2625 long nativeTotalPss = 0; 2626 final List<ProcessCpuTracker.Stats> stats; 2627 synchronized (mProcessCpuTracker) { 2628 stats = mProcessCpuTracker.getStats( (st)-> { 2629 return st.vsize > 0 && st.uid < FIRST_APPLICATION_UID; 2630 }); 2631 } 2632 final int N = stats.size(); 2633 for (int j = 0; j < N; j++) { 2634 synchronized (mPidsSelfLocked) { 2635 if (mPidsSelfLocked.indexOfKey(stats.get(j).pid) >= 0) { 2636 // This is one of our own processes; skip it. 2637 continue; 2638 } 2639 } 2640 nativeTotalPss += Debug.getPss(stats.get(j).pid, null, null); 2641 } 2642 memInfo.readMemInfo(); 2643 synchronized (ActivityManagerService.this) { 2644 if (DEBUG_PSS) Slog.d(TAG_PSS, "Collected native and kernel memory in " 2645 + (SystemClock.uptimeMillis()-start) + "ms"); 2646 final long cachedKb = memInfo.getCachedSizeKb(); 2647 final long freeKb = memInfo.getFreeSizeKb(); 2648 final long zramKb = memInfo.getZramTotalSizeKb(); 2649 final long kernelKb = memInfo.getKernelUsedSizeKb(); 2650 EventLogTags.writeAmMeminfo(cachedKb*1024, freeKb*1024, zramKb*1024, 2651 kernelKb*1024, nativeTotalPss*1024); 2652 mProcessStats.addSysMemUsageLocked(cachedKb, freeKb, zramKb, kernelKb, 2653 nativeTotalPss); 2654 } 2655 } 2656 2657 int num = 0; 2658 long[] tmp = new long[3]; 2659 do { 2660 ProcessRecord proc; 2661 int procState; 2662 int statType; 2663 int pid; 2664 long lastPssTime; 2665 synchronized (ActivityManagerService.this) { 2666 if (mPendingPssProcesses.size() <= 0) { 2667 if (mTestPssMode || DEBUG_PSS) Slog.d(TAG_PSS, 2668 "Collected pss of " + num + " processes in " 2669 + (SystemClock.uptimeMillis() - start) + "ms"); 2670 mPendingPssProcesses.clear(); 2671 return; 2672 } 2673 proc = mPendingPssProcesses.remove(0); 2674 procState = proc.pssProcState; 2675 statType = proc.pssStatType; 2676 lastPssTime = proc.lastPssTime; 2677 long now = SystemClock.uptimeMillis(); 2678 if (proc.thread != null && procState == proc.setProcState 2679 && (lastPssTime+ProcessList.PSS_SAFE_TIME_FROM_STATE_CHANGE) 2680 < now) { 2681 pid = proc.pid; 2682 } else { 2683 ProcessList.abortNextPssTime(proc.procStateMemTracker); 2684 if (DEBUG_PSS) Slog.d(TAG_PSS, "Skipped pss collection of " + pid + 2685 ": still need " + 2686 (lastPssTime+ProcessList.PSS_SAFE_TIME_FROM_STATE_CHANGE-now) + 2687 "ms until safe"); 2688 proc = null; 2689 pid = 0; 2690 } 2691 } 2692 if (proc != null) { 2693 long startTime = SystemClock.currentThreadTimeMillis(); 2694 long pss = Debug.getPss(pid, tmp, null); 2695 long endTime = SystemClock.currentThreadTimeMillis(); 2696 synchronized (ActivityManagerService.this) { 2697 if (pss != 0 && proc.thread != null && proc.setProcState == procState 2698 && proc.pid == pid && proc.lastPssTime == lastPssTime) { 2699 num++; 2700 ProcessList.commitNextPssTime(proc.procStateMemTracker); 2701 recordPssSampleLocked(proc, procState, pss, tmp[0], tmp[1], tmp[2], 2702 statType, endTime-startTime, SystemClock.uptimeMillis()); 2703 } else { 2704 ProcessList.abortNextPssTime(proc.procStateMemTracker); 2705 if (DEBUG_PSS) Slog.d(TAG_PSS, "Skipped pss collection of " + pid + 2706 ": " + (proc.thread == null ? "NO_THREAD " : "") + 2707 (proc.pid != pid ? "PID_CHANGED " : "") + 2708 " initState=" + procState + " curState=" + 2709 proc.setProcState + " " + 2710 (proc.lastPssTime != lastPssTime ? "TIME_CHANGED" : "")); 2711 } 2712 } 2713 } 2714 } while (true); 2715 } 2716 } 2717 } 2718 }; 2719 2720 public void setSystemProcess() { 2721 try { 2722 ServiceManager.addService(Context.ACTIVITY_SERVICE, this, /* allowIsolated= */ true, 2723 DUMP_FLAG_PRIORITY_CRITICAL | DUMP_FLAG_PRIORITY_NORMAL | DUMP_FLAG_PROTO); 2724 ServiceManager.addService(ProcessStats.SERVICE_NAME, mProcessStats); 2725 ServiceManager.addService("meminfo", new MemBinder(this), /* allowIsolated= */ false, 2726 DUMP_FLAG_PRIORITY_HIGH); 2727 ServiceManager.addService("gfxinfo", new GraphicsBinder(this)); 2728 ServiceManager.addService("dbinfo", new DbBinder(this)); 2729 if (MONITOR_CPU_USAGE) { 2730 ServiceManager.addService("cpuinfo", new CpuBinder(this), 2731 /* allowIsolated= */ false, DUMP_FLAG_PRIORITY_CRITICAL); 2732 } 2733 ServiceManager.addService("permission", new PermissionController(this)); 2734 ServiceManager.addService("processinfo", new ProcessInfoService(this)); 2735 2736 ApplicationInfo info = mContext.getPackageManager().getApplicationInfo( 2737 "android", STOCK_PM_FLAGS | MATCH_SYSTEM_ONLY); 2738 mSystemThread.installSystemApplicationInfo(info, getClass().getClassLoader()); 2739 2740 synchronized (this) { 2741 ProcessRecord app = newProcessRecordLocked(info, info.processName, false, 0); 2742 app.persistent = true; 2743 app.pid = MY_PID; 2744 app.maxAdj = ProcessList.SYSTEM_ADJ; 2745 app.makeActive(mSystemThread.getApplicationThread(), mProcessStats); 2746 synchronized (mPidsSelfLocked) { 2747 mPidsSelfLocked.put(app.pid, app); 2748 } 2749 updateLruProcessLocked(app, false, null); 2750 updateOomAdjLocked(); 2751 } 2752 } catch (PackageManager.NameNotFoundException e) { 2753 throw new RuntimeException( 2754 "Unable to find android system package", e); 2755 } 2756 2757 // Start watching app ops after we and the package manager are up and running. 2758 mAppOpsService.startWatchingMode(AppOpsManager.OP_RUN_IN_BACKGROUND, null, 2759 new IAppOpsCallback.Stub() { 2760 @Override public void opChanged(int op, int uid, String packageName) { 2761 if (op == AppOpsManager.OP_RUN_IN_BACKGROUND && packageName != null) { 2762 if (mAppOpsService.checkOperation(op, uid, packageName) 2763 != AppOpsManager.MODE_ALLOWED) { 2764 runInBackgroundDisabled(uid); 2765 } 2766 } 2767 } 2768 }); 2769 } 2770 2771 public void setWindowManager(WindowManagerService wm) { 2772 synchronized (this) { 2773 mWindowManager = wm; 2774 mStackSupervisor.setWindowManager(wm); 2775 mLockTaskController.setWindowManager(wm); 2776 } 2777 } 2778 2779 public void setUsageStatsManager(UsageStatsManagerInternal usageStatsManager) { 2780 mUsageStatsService = usageStatsManager; 2781 } 2782 2783 public void startObservingNativeCrashes() { 2784 final NativeCrashListener ncl = new NativeCrashListener(this); 2785 ncl.start(); 2786 } 2787 2788 public IAppOpsService getAppOpsService() { 2789 return mAppOpsService; 2790 } 2791 2792 static class MemBinder extends Binder { 2793 ActivityManagerService mActivityManagerService; 2794 private final PriorityDump.PriorityDumper mPriorityDumper = 2795 new PriorityDump.PriorityDumper() { 2796 @Override 2797 public void dumpHigh(FileDescriptor fd, PrintWriter pw, String[] args, 2798 boolean asProto) { 2799 dump(fd, pw, new String[] {"-a"}, asProto); 2800 } 2801 2802 @Override 2803 public void dump(FileDescriptor fd, PrintWriter pw, String[] args, boolean asProto) { 2804 mActivityManagerService.dumpApplicationMemoryUsage( 2805 fd, pw, " ", args, false, null, asProto); 2806 } 2807 }; 2808 2809 MemBinder(ActivityManagerService activityManagerService) { 2810 mActivityManagerService = activityManagerService; 2811 } 2812 2813 @Override 2814 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 2815 if (!DumpUtils.checkDumpAndUsageStatsPermission(mActivityManagerService.mContext, 2816 "meminfo", pw)) return; 2817 PriorityDump.dump(mPriorityDumper, fd, pw, args); 2818 } 2819 } 2820 2821 static class GraphicsBinder extends Binder { 2822 ActivityManagerService mActivityManagerService; 2823 GraphicsBinder(ActivityManagerService activityManagerService) { 2824 mActivityManagerService = activityManagerService; 2825 } 2826 2827 @Override 2828 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 2829 if (!DumpUtils.checkDumpAndUsageStatsPermission(mActivityManagerService.mContext, 2830 "gfxinfo", pw)) return; 2831 mActivityManagerService.dumpGraphicsHardwareUsage(fd, pw, args); 2832 } 2833 } 2834 2835 static class DbBinder extends Binder { 2836 ActivityManagerService mActivityManagerService; 2837 DbBinder(ActivityManagerService activityManagerService) { 2838 mActivityManagerService = activityManagerService; 2839 } 2840 2841 @Override 2842 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 2843 if (!DumpUtils.checkDumpAndUsageStatsPermission(mActivityManagerService.mContext, 2844 "dbinfo", pw)) return; 2845 mActivityManagerService.dumpDbInfo(fd, pw, args); 2846 } 2847 } 2848 2849 static class CpuBinder extends Binder { 2850 ActivityManagerService mActivityManagerService; 2851 private final PriorityDump.PriorityDumper mPriorityDumper = 2852 new PriorityDump.PriorityDumper() { 2853 @Override 2854 public void dumpCritical(FileDescriptor fd, PrintWriter pw, String[] args, 2855 boolean asProto) { 2856 if (asProto) return; 2857 if (!DumpUtils.checkDumpAndUsageStatsPermission(mActivityManagerService.mContext, 2858 "cpuinfo", pw)) return; 2859 synchronized (mActivityManagerService.mProcessCpuTracker) { 2860 pw.print(mActivityManagerService.mProcessCpuTracker.printCurrentLoad()); 2861 pw.print(mActivityManagerService.mProcessCpuTracker.printCurrentState( 2862 SystemClock.uptimeMillis())); 2863 } 2864 } 2865 }; 2866 2867 CpuBinder(ActivityManagerService activityManagerService) { 2868 mActivityManagerService = activityManagerService; 2869 } 2870 2871 @Override 2872 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 2873 PriorityDump.dump(mPriorityDumper, fd, pw, args); 2874 } 2875 } 2876 2877 public static final class Lifecycle extends SystemService { 2878 private final ActivityManagerService mService; 2879 2880 public Lifecycle(Context context) { 2881 super(context); 2882 mService = new ActivityManagerService(context); 2883 } 2884 2885 @Override 2886 public void onStart() { 2887 mService.start(); 2888 } 2889 2890 @Override 2891 public void onBootPhase(int phase) { 2892 mService.mBootPhase = phase; 2893 if (phase == PHASE_SYSTEM_SERVICES_READY) { 2894 mService.mBatteryStatsService.systemServicesReady(); 2895 mService.mServices.systemServicesReady(); 2896 } 2897 } 2898 2899 @Override 2900 public void onCleanupUser(int userId) { 2901 mService.mBatteryStatsService.onCleanupUser(userId); 2902 } 2903 2904 public ActivityManagerService getService() { 2905 return mService; 2906 } 2907 } 2908 2909 /** 2910 * Encapsulates global settings related to hidden API enforcement behaviour, including tracking 2911 * the latest value via a content observer. 2912 */ 2913 static class HiddenApiSettings extends ContentObserver { 2914 2915 private final Context mContext; 2916 private boolean mBlacklistDisabled; 2917 private String mExemptionsStr; 2918 private List<String> mExemptions = Collections.emptyList(); 2919 private int mLogSampleRate = -1; 2920 @HiddenApiEnforcementPolicy private int mPolicyPreP = HIDDEN_API_ENFORCEMENT_DEFAULT; 2921 @HiddenApiEnforcementPolicy private int mPolicyP = HIDDEN_API_ENFORCEMENT_DEFAULT; 2922 2923 public HiddenApiSettings(Handler handler, Context context) { 2924 super(handler); 2925 mContext = context; 2926 } 2927 2928 public void registerObserver() { 2929 mContext.getContentResolver().registerContentObserver( 2930 Settings.Global.getUriFor(Settings.Global.HIDDEN_API_BLACKLIST_EXEMPTIONS), 2931 false, 2932 this); 2933 mContext.getContentResolver().registerContentObserver( 2934 Settings.Global.getUriFor(Settings.Global.HIDDEN_API_ACCESS_LOG_SAMPLING_RATE), 2935 false, 2936 this); 2937 mContext.getContentResolver().registerContentObserver( 2938 Settings.Global.getUriFor(Settings.Global.HIDDEN_API_POLICY_PRE_P_APPS), 2939 false, 2940 this); 2941 mContext.getContentResolver().registerContentObserver( 2942 Settings.Global.getUriFor(Settings.Global.HIDDEN_API_POLICY_P_APPS), 2943 false, 2944 this); 2945 update(); 2946 } 2947 2948 private void update() { 2949 String exemptions = Settings.Global.getString(mContext.getContentResolver(), 2950 Settings.Global.HIDDEN_API_BLACKLIST_EXEMPTIONS); 2951 if (!TextUtils.equals(exemptions, mExemptionsStr)) { 2952 mExemptionsStr = exemptions; 2953 if ("*".equals(exemptions)) { 2954 mBlacklistDisabled = true; 2955 mExemptions = Collections.emptyList(); 2956 } else { 2957 mBlacklistDisabled = false; 2958 mExemptions = TextUtils.isEmpty(exemptions) 2959 ? Collections.emptyList() 2960 : Arrays.asList(exemptions.split(",")); 2961 } 2962 if (!zygoteProcess.setApiBlacklistExemptions(mExemptions)) { 2963 Slog.e(TAG, "Failed to set API blacklist exemptions!"); 2964 // leave mExemptionsStr as is, so we don't try to send the same list again. 2965 mExemptions = Collections.emptyList(); 2966 } 2967 } 2968 int logSampleRate = Settings.Global.getInt(mContext.getContentResolver(), 2969 Settings.Global.HIDDEN_API_ACCESS_LOG_SAMPLING_RATE, -1); 2970 if (logSampleRate < 0 || logSampleRate > 0x10000) { 2971 logSampleRate = -1; 2972 } 2973 if (logSampleRate != -1 && logSampleRate != mLogSampleRate) { 2974 mLogSampleRate = logSampleRate; 2975 zygoteProcess.setHiddenApiAccessLogSampleRate(mLogSampleRate); 2976 } 2977 mPolicyPreP = getValidEnforcementPolicy(Settings.Global.HIDDEN_API_POLICY_PRE_P_APPS); 2978 mPolicyP = getValidEnforcementPolicy(Settings.Global.HIDDEN_API_POLICY_P_APPS); 2979 } 2980 2981 private @HiddenApiEnforcementPolicy int getValidEnforcementPolicy(String settingsKey) { 2982 int policy = Settings.Global.getInt(mContext.getContentResolver(), settingsKey, 2983 ApplicationInfo.HIDDEN_API_ENFORCEMENT_DEFAULT); 2984 if (ApplicationInfo.isValidHiddenApiEnforcementPolicy(policy)) { 2985 return policy; 2986 } else { 2987 return ApplicationInfo.HIDDEN_API_ENFORCEMENT_DEFAULT; 2988 } 2989 } 2990 2991 boolean isDisabled() { 2992 return mBlacklistDisabled; 2993 } 2994 2995 @HiddenApiEnforcementPolicy int getPolicyForPrePApps() { 2996 return mPolicyPreP; 2997 } 2998 2999 @HiddenApiEnforcementPolicy int getPolicyForPApps() { 3000 return mPolicyP; 3001 } 3002 3003 public void onChange(boolean selfChange) { 3004 update(); 3005 } 3006 } 3007 3008 @VisibleForTesting 3009 public ActivityManagerService(Injector injector) { 3010 mInjector = injector; 3011 mContext = mInjector.getContext(); 3012 mUiContext = null; 3013 GL_ES_VERSION = 0; 3014 mActivityStartController = null; 3015 mAppErrors = null; 3016 mAppWarnings = null; 3017 mAppOpsService = mInjector.getAppOpsService(null, null); 3018 mBatteryStatsService = null; 3019 mCompatModePackages = null; 3020 mConstants = null; 3021 mGrantFile = null; 3022 mHandler = null; 3023 mHandlerThread = null; 3024 mIntentFirewall = null; 3025 mKeyguardController = null; 3026 mPermissionReviewRequired = false; 3027 mProcessCpuThread = null; 3028 mProcessStats = null; 3029 mProviderMap = null; 3030 mRecentTasks = null; 3031 mServices = null; 3032 mStackSupervisor = null; 3033 mSystemThread = null; 3034 mTaskChangeNotificationController = null; 3035 mUiHandler = injector.getUiHandler(null); 3036 mUserController = null; 3037 mVrController = null; 3038 mLockTaskController = null; 3039 mLifecycleManager = null; 3040 mProcStartHandlerThread = null; 3041 mProcStartHandler = null; 3042 mHiddenApiBlacklist = null; 3043 } 3044 3045 // Note: This method is invoked on the main thread but may need to attach various 3046 // handlers to other threads. So take care to be explicit about the looper. 3047 public ActivityManagerService(Context systemContext) { 3048 LockGuard.installLock(this, LockGuard.INDEX_ACTIVITY); 3049 mInjector = new Injector(); 3050 mContext = systemContext; 3051 3052 mFactoryTest = FactoryTest.getMode(); 3053 mSystemThread = ActivityThread.currentActivityThread(); 3054 mUiContext = mSystemThread.getSystemUiContext(); 3055 3056 Slog.i(TAG, "Memory class: " + ActivityManager.staticGetMemoryClass()); 3057 3058 mPermissionReviewRequired = mContext.getResources().getBoolean( 3059 com.android.internal.R.bool.config_permissionReviewRequired); 3060 3061 mHandlerThread = new ServiceThread(TAG, 3062 THREAD_PRIORITY_FOREGROUND, false /*allowIo*/); 3063 mHandlerThread.start(); 3064 mHandler = new MainHandler(mHandlerThread.getLooper()); 3065 mUiHandler = mInjector.getUiHandler(this); 3066 3067 mProcStartHandlerThread = new ServiceThread(TAG + ":procStart", 3068 THREAD_PRIORITY_FOREGROUND, false /* allowIo */); 3069 mProcStartHandlerThread.start(); 3070 mProcStartHandler = new Handler(mProcStartHandlerThread.getLooper()); 3071 3072 mConstants = new ActivityManagerConstants(this, mHandler); 3073 3074 /* static; one-time init here */ 3075 if (sKillHandler == null) { 3076 sKillThread = new ServiceThread(TAG + ":kill", 3077 THREAD_PRIORITY_BACKGROUND, true /* allowIo */); 3078 sKillThread.start(); 3079 sKillHandler = new KillHandler(sKillThread.getLooper()); 3080 } 3081 3082 mFgBroadcastQueue = new BroadcastQueue(this, mHandler, 3083 "foreground", BROADCAST_FG_TIMEOUT, false); 3084 mBgBroadcastQueue = new BroadcastQueue(this, mHandler, 3085 "background", BROADCAST_BG_TIMEOUT, true); 3086 mBroadcastQueues[0] = mFgBroadcastQueue; 3087 mBroadcastQueues[1] = mBgBroadcastQueue; 3088 3089 mServices = new ActiveServices(this); 3090 mProviderMap = new ProviderMap(this); 3091 mAppErrors = new AppErrors(mUiContext, this); 3092 3093 File dataDir = Environment.getDataDirectory(); 3094 File systemDir = new File(dataDir, "system"); 3095 systemDir.mkdirs(); 3096 3097 mAppWarnings = new AppWarnings(this, mUiContext, mHandler, mUiHandler, systemDir); 3098 3099 // TODO: Move creation of battery stats service outside of activity manager service. 3100 mBatteryStatsService = new BatteryStatsService(systemContext, systemDir, mHandler); 3101 mBatteryStatsService.getActiveStatistics().readLocked(); 3102 mBatteryStatsService.scheduleWriteToDisk(); 3103 mOnBattery = DEBUG_POWER ? true 3104 : mBatteryStatsService.getActiveStatistics().getIsOnBattery(); 3105 mBatteryStatsService.getActiveStatistics().setCallback(this); 3106 3107 mProcessStats = new ProcessStatsService(this, new File(systemDir, "procstats")); 3108 3109 mAppOpsService = mInjector.getAppOpsService(new File(systemDir, "appops.xml"), mHandler); 3110 3111 mGrantFile = new AtomicFile(new File(systemDir, "urigrants.xml"), "uri-grants"); 3112 3113 mUserController = new UserController(this); 3114 3115 mVrController = new VrController(this); 3116 3117 GL_ES_VERSION = SystemProperties.getInt("ro.opengles.version", 3118 ConfigurationInfo.GL_ES_VERSION_UNDEFINED); 3119 3120 if (SystemProperties.getInt("sys.use_fifo_ui", 0) != 0) { 3121 mUseFifoUiScheduling = true; 3122 } 3123 3124 mTrackingAssociations = "1".equals(SystemProperties.get("debug.track-associations")); 3125 mTempConfig.setToDefaults(); 3126 mTempConfig.setLocales(LocaleList.getDefault()); 3127 mConfigurationSeq = mTempConfig.seq = 1; 3128 mStackSupervisor = createStackSupervisor(); 3129 mStackSupervisor.onConfigurationChanged(mTempConfig); 3130 mKeyguardController = mStackSupervisor.getKeyguardController(); 3131 mCompatModePackages = new CompatModePackages(this, systemDir, mHandler); 3132 mIntentFirewall = new IntentFirewall(new IntentFirewallInterface(), mHandler); 3133 mTaskChangeNotificationController = 3134 new TaskChangeNotificationController(this, mStackSupervisor, mHandler); 3135 mActivityStartController = new ActivityStartController(this); 3136 mRecentTasks = createRecentTasks(); 3137 mStackSupervisor.setRecentTasks(mRecentTasks); 3138 mLockTaskController = new LockTaskController(mContext, mStackSupervisor, mHandler); 3139 mLifecycleManager = new ClientLifecycleManager(); 3140 3141 mProcessCpuThread = new Thread("CpuTracker") { 3142 @Override 3143 public void run() { 3144 synchronized (mProcessCpuTracker) { 3145 mProcessCpuInitLatch.countDown(); 3146 mProcessCpuTracker.init(); 3147 } 3148 while (true) { 3149 try { 3150 try { 3151 synchronized(this) { 3152 final long now = SystemClock.uptimeMillis(); 3153 long nextCpuDelay = (mLastCpuTime.get()+MONITOR_CPU_MAX_TIME)-now; 3154 long nextWriteDelay = (mLastWriteTime+BATTERY_STATS_TIME)-now; 3155 //Slog.i(TAG, "Cpu delay=" + nextCpuDelay 3156 // + ", write delay=" + nextWriteDelay); 3157 if (nextWriteDelay < nextCpuDelay) { 3158 nextCpuDelay = nextWriteDelay; 3159 } 3160 if (nextCpuDelay > 0) { 3161 mProcessCpuMutexFree.set(true); 3162 this.wait(nextCpuDelay); 3163 } 3164 } 3165 } catch (InterruptedException e) { 3166 } 3167 updateCpuStatsNow(); 3168 } catch (Exception e) { 3169 Slog.e(TAG, "Unexpected exception collecting process stats", e); 3170 } 3171 } 3172 } 3173 }; 3174 3175 mHiddenApiBlacklist = new HiddenApiSettings(mHandler, mContext); 3176 3177 Watchdog.getInstance().addMonitor(this); 3178 Watchdog.getInstance().addThread(mHandler); 3179 3180 // bind background thread to little cores 3181 // this is expected to fail inside of framework tests because apps can't touch cpusets directly 3182 // make sure we've already adjusted system_server's internal view of itself first 3183 updateOomAdjLocked(); 3184 try { 3185 Process.setThreadGroupAndCpuset(BackgroundThread.get().getThreadId(), 3186 Process.THREAD_GROUP_BG_NONINTERACTIVE); 3187 } catch (Exception e) { 3188 Slog.w(TAG, "Setting background thread cpuset failed"); 3189 } 3190 3191 } 3192 3193 protected ActivityStackSupervisor createStackSupervisor() { 3194 final ActivityStackSupervisor supervisor = new ActivityStackSupervisor(this, mHandler.getLooper()); 3195 supervisor.initialize(); 3196 return supervisor; 3197 } 3198 3199 protected RecentTasks createRecentTasks() { 3200 return new RecentTasks(this, mStackSupervisor); 3201 } 3202 3203 RecentTasks getRecentTasks() { 3204 return mRecentTasks; 3205 } 3206 3207 public void setSystemServiceManager(SystemServiceManager mgr) { 3208 mSystemServiceManager = mgr; 3209 } 3210 3211 public void setInstaller(Installer installer) { 3212 mInstaller = installer; 3213 } 3214 3215 private void start() { 3216 removeAllProcessGroups(); 3217 mProcessCpuThread.start(); 3218 3219 mBatteryStatsService.publish(); 3220 mAppOpsService.publish(mContext); 3221 Slog.d("AppOps", "AppOpsService published"); 3222 LocalServices.addService(ActivityManagerInternal.class, new LocalService()); 3223 // Wait for the synchronized block started in mProcessCpuThread, 3224 // so that any other acccess to mProcessCpuTracker from main thread 3225 // will be blocked during mProcessCpuTracker initialization. 3226 try { 3227 mProcessCpuInitLatch.await(); 3228 } catch (InterruptedException e) { 3229 Slog.wtf(TAG, "Interrupted wait during start", e); 3230 Thread.currentThread().interrupt(); 3231 throw new IllegalStateException("Interrupted wait during start"); 3232 } 3233 } 3234 3235 void onUserStoppedLocked(int userId) { 3236 mRecentTasks.unloadUserDataFromMemoryLocked(userId); 3237 mAllowAppSwitchUids.remove(userId); 3238 } 3239 3240 public void initPowerManagement() { 3241 mStackSupervisor.initPowerManagement(); 3242 mBatteryStatsService.initPowerManagement(); 3243 mLocalPowerManager = LocalServices.getService(PowerManagerInternal.class); 3244 PowerManager pm = (PowerManager)mContext.getSystemService(Context.POWER_SERVICE); 3245 mVoiceWakeLock = pm.newWakeLock(PowerManager.PARTIAL_WAKE_LOCK, "*voice*"); 3246 mVoiceWakeLock.setReferenceCounted(false); 3247 } 3248 3249 private ArraySet<String> getBackgroundLaunchBroadcasts() { 3250 if (mBackgroundLaunchBroadcasts == null) { 3251 mBackgroundLaunchBroadcasts = SystemConfig.getInstance().getAllowImplicitBroadcasts(); 3252 } 3253 return mBackgroundLaunchBroadcasts; 3254 } 3255 3256 @Override 3257 public boolean onTransact(int code, Parcel data, Parcel reply, int flags) 3258 throws RemoteException { 3259 if (code == SYSPROPS_TRANSACTION) { 3260 // We need to tell all apps about the system property change. 3261 ArrayList<IBinder> procs = new ArrayList<IBinder>(); 3262 synchronized(this) { 3263 final int NP = mProcessNames.getMap().size(); 3264 for (int ip=0; ip<NP; ip++) { 3265 SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 3266 final int NA = apps.size(); 3267 for (int ia=0; ia<NA; ia++) { 3268 ProcessRecord app = apps.valueAt(ia); 3269 if (app.thread != null) { 3270 procs.add(app.thread.asBinder()); 3271 } 3272 } 3273 } 3274 } 3275 3276 int N = procs.size(); 3277 for (int i=0; i<N; i++) { 3278 Parcel data2 = Parcel.obtain(); 3279 try { 3280 procs.get(i).transact(IBinder.SYSPROPS_TRANSACTION, data2, null, 3281 Binder.FLAG_ONEWAY); 3282 } catch (RemoteException e) { 3283 } 3284 data2.recycle(); 3285 } 3286 } 3287 try { 3288 return super.onTransact(code, data, reply, flags); 3289 } catch (RuntimeException e) { 3290 // The activity manager only throws certain exceptions intentionally, so let's 3291 // log all others. 3292 if (!(e instanceof SecurityException 3293 || e instanceof IllegalArgumentException 3294 || e instanceof IllegalStateException)) { 3295 Slog.wtf(TAG, "Activity Manager Crash." 3296 + " UID:" + Binder.getCallingUid() 3297 + " PID:" + Binder.getCallingPid() 3298 + " TRANS:" + code, e); 3299 } 3300 throw e; 3301 } 3302 } 3303 3304 void updateCpuStats() { 3305 final long now = SystemClock.uptimeMillis(); 3306 if (mLastCpuTime.get() >= now - MONITOR_CPU_MIN_TIME) { 3307 return; 3308 } 3309 if (mProcessCpuMutexFree.compareAndSet(true, false)) { 3310 synchronized (mProcessCpuThread) { 3311 mProcessCpuThread.notify(); 3312 } 3313 } 3314 } 3315 3316 void updateCpuStatsNow() { 3317 synchronized (mProcessCpuTracker) { 3318 mProcessCpuMutexFree.set(false); 3319 final long now = SystemClock.uptimeMillis(); 3320 boolean haveNewCpuStats = false; 3321 3322 if (MONITOR_CPU_USAGE && 3323 mLastCpuTime.get() < (now-MONITOR_CPU_MIN_TIME)) { 3324 mLastCpuTime.set(now); 3325 mProcessCpuTracker.update(); 3326 if (mProcessCpuTracker.hasGoodLastStats()) { 3327 haveNewCpuStats = true; 3328 //Slog.i(TAG, mProcessCpu.printCurrentState()); 3329 //Slog.i(TAG, "Total CPU usage: " 3330 // + mProcessCpu.getTotalCpuPercent() + "%"); 3331 3332 // Slog the cpu usage if the property is set. 3333 if ("true".equals(SystemProperties.get("events.cpu"))) { 3334 int user = mProcessCpuTracker.getLastUserTime(); 3335 int system = mProcessCpuTracker.getLastSystemTime(); 3336 int iowait = mProcessCpuTracker.getLastIoWaitTime(); 3337 int irq = mProcessCpuTracker.getLastIrqTime(); 3338 int softIrq = mProcessCpuTracker.getLastSoftIrqTime(); 3339 int idle = mProcessCpuTracker.getLastIdleTime(); 3340 3341 int total = user + system + iowait + irq + softIrq + idle; 3342 if (total == 0) total = 1; 3343 3344 EventLog.writeEvent(EventLogTags.CPU, 3345 ((user+system+iowait+irq+softIrq) * 100) / total, 3346 (user * 100) / total, 3347 (system * 100) / total, 3348 (iowait * 100) / total, 3349 (irq * 100) / total, 3350 (softIrq * 100) / total); 3351 } 3352 } 3353 } 3354 3355 final BatteryStatsImpl bstats = mBatteryStatsService.getActiveStatistics(); 3356 synchronized(bstats) { 3357 synchronized(mPidsSelfLocked) { 3358 if (haveNewCpuStats) { 3359 if (bstats.startAddingCpuLocked()) { 3360 int totalUTime = 0; 3361 int totalSTime = 0; 3362 final int N = mProcessCpuTracker.countStats(); 3363 for (int i=0; i<N; i++) { 3364 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(i); 3365 if (!st.working) { 3366 continue; 3367 } 3368 ProcessRecord pr = mPidsSelfLocked.get(st.pid); 3369 totalUTime += st.rel_utime; 3370 totalSTime += st.rel_stime; 3371 if (pr != null) { 3372 BatteryStatsImpl.Uid.Proc ps = pr.curProcBatteryStats; 3373 if (ps == null || !ps.isActive()) { 3374 pr.curProcBatteryStats = ps = bstats.getProcessStatsLocked( 3375 pr.info.uid, pr.processName); 3376 } 3377 ps.addCpuTimeLocked(st.rel_utime, st.rel_stime); 3378 pr.curCpuTime += st.rel_utime + st.rel_stime; 3379 if (pr.lastCpuTime == 0) { 3380 pr.lastCpuTime = pr.curCpuTime; 3381 } 3382 } else { 3383 BatteryStatsImpl.Uid.Proc ps = st.batteryStats; 3384 if (ps == null || !ps.isActive()) { 3385 st.batteryStats = ps = bstats.getProcessStatsLocked( 3386 bstats.mapUid(st.uid), st.name); 3387 } 3388 ps.addCpuTimeLocked(st.rel_utime, st.rel_stime); 3389 } 3390 } 3391 final int userTime = mProcessCpuTracker.getLastUserTime(); 3392 final int systemTime = mProcessCpuTracker.getLastSystemTime(); 3393 final int iowaitTime = mProcessCpuTracker.getLastIoWaitTime(); 3394 final int irqTime = mProcessCpuTracker.getLastIrqTime(); 3395 final int softIrqTime = mProcessCpuTracker.getLastSoftIrqTime(); 3396 final int idleTime = mProcessCpuTracker.getLastIdleTime(); 3397 bstats.finishAddingCpuLocked(totalUTime, totalSTime, userTime, 3398 systemTime, iowaitTime, irqTime, softIrqTime, idleTime); 3399 } 3400 } 3401 } 3402 3403 if (mLastWriteTime < (now-BATTERY_STATS_TIME)) { 3404 mLastWriteTime = now; 3405 mBatteryStatsService.scheduleWriteToDisk(); 3406 } 3407 } 3408 } 3409 } 3410 3411 @Override 3412 public void batteryNeedsCpuUpdate() { 3413 updateCpuStatsNow(); 3414 } 3415 3416 @Override 3417 public void batteryPowerChanged(boolean onBattery) { 3418 // When plugging in, update the CPU stats first before changing 3419 // the plug state. 3420 updateCpuStatsNow(); 3421 synchronized (this) { 3422 synchronized(mPidsSelfLocked) { 3423 mOnBattery = DEBUG_POWER ? true : onBattery; 3424 } 3425 } 3426 } 3427 3428 @Override 3429 public void batteryStatsReset() { 3430 BinderCallsStatsService.reset(); 3431 } 3432 3433 @Override 3434 public void batterySendBroadcast(Intent intent) { 3435 synchronized (this) { 3436 broadcastIntentLocked(null, null, intent, null, null, 0, null, null, null, 3437 OP_NONE, null, false, false, 3438 -1, SYSTEM_UID, UserHandle.USER_ALL); 3439 } 3440 } 3441 3442 /** 3443 * Initialize the application bind args. These are passed to each 3444 * process when the bindApplication() IPC is sent to the process. They're 3445 * lazily setup to make sure the services are running when they're asked for. 3446 */ 3447 private ArrayMap<String, IBinder> getCommonServicesLocked(boolean isolated) { 3448 // Isolated processes won't get this optimization, so that we don't 3449 // violate the rules about which services they have access to. 3450 if (isolated) { 3451 if (mIsolatedAppBindArgs == null) { 3452 mIsolatedAppBindArgs = new ArrayMap<>(1); 3453 addServiceToMap(mIsolatedAppBindArgs, "package"); 3454 } 3455 return mIsolatedAppBindArgs; 3456 } 3457 3458 if (mAppBindArgs == null) { 3459 mAppBindArgs = new ArrayMap<>(); 3460 3461 // Add common services. 3462 // IMPORTANT: Before adding services here, make sure ephemeral apps can access them too. 3463 // Enable the check in ApplicationThread.bindApplication() to make sure. 3464 addServiceToMap(mAppBindArgs, "package"); 3465 addServiceToMap(mAppBindArgs, Context.WINDOW_SERVICE); 3466 addServiceToMap(mAppBindArgs, Context.ALARM_SERVICE); 3467 addServiceToMap(mAppBindArgs, Context.DISPLAY_SERVICE); 3468 addServiceToMap(mAppBindArgs, Context.NETWORKMANAGEMENT_SERVICE); 3469 addServiceToMap(mAppBindArgs, Context.CONNECTIVITY_SERVICE); 3470 addServiceToMap(mAppBindArgs, Context.ACCESSIBILITY_SERVICE); 3471 addServiceToMap(mAppBindArgs, Context.INPUT_METHOD_SERVICE); 3472 addServiceToMap(mAppBindArgs, Context.INPUT_SERVICE); 3473 addServiceToMap(mAppBindArgs, "graphicsstats"); 3474 addServiceToMap(mAppBindArgs, Context.APP_OPS_SERVICE); 3475 addServiceToMap(mAppBindArgs, "content"); 3476 addServiceToMap(mAppBindArgs, Context.JOB_SCHEDULER_SERVICE); 3477 addServiceToMap(mAppBindArgs, Context.NOTIFICATION_SERVICE); 3478 addServiceToMap(mAppBindArgs, Context.VIBRATOR_SERVICE); 3479 addServiceToMap(mAppBindArgs, Context.ACCOUNT_SERVICE); 3480 addServiceToMap(mAppBindArgs, Context.POWER_SERVICE); 3481 addServiceToMap(mAppBindArgs, Context.USER_SERVICE); 3482 addServiceToMap(mAppBindArgs, "mount"); 3483 } 3484 return mAppBindArgs; 3485 } 3486 3487 private static void addServiceToMap(ArrayMap<String, IBinder> map, String name) { 3488 final IBinder service = ServiceManager.getService(name); 3489 if (service != null) { 3490 map.put(name, service); 3491 if (false) { 3492 Log.i(TAG, "Adding " + name + " to the pre-loaded service cache."); 3493 } 3494 } 3495 } 3496 3497 /** 3498 * Update AMS states when an activity is resumed. This should only be called by 3499 * {@link ActivityStack#onActivityStateChanged(ActivityRecord, ActivityState, String)} when an 3500 * activity is resumed. 3501 */ 3502 @GuardedBy("this") 3503 void setResumedActivityUncheckLocked(ActivityRecord r, String reason) { 3504 final TaskRecord task = r.getTask(); 3505 if (task.isActivityTypeStandard()) { 3506 if (mCurAppTimeTracker != r.appTimeTracker) { 3507 // We are switching app tracking. Complete the current one. 3508 if (mCurAppTimeTracker != null) { 3509 mCurAppTimeTracker.stop(); 3510 mHandler.obtainMessage( 3511 REPORT_TIME_TRACKER_MSG, mCurAppTimeTracker).sendToTarget(); 3512 mStackSupervisor.clearOtherAppTimeTrackers(r.appTimeTracker); 3513 mCurAppTimeTracker = null; 3514 } 3515 if (r.appTimeTracker != null) { 3516 mCurAppTimeTracker = r.appTimeTracker; 3517 startTimeTrackingFocusedActivityLocked(); 3518 } 3519 } else { 3520 startTimeTrackingFocusedActivityLocked(); 3521 } 3522 } else { 3523 r.appTimeTracker = null; 3524 } 3525 // TODO: VI Maybe r.task.voiceInteractor || r.voiceInteractor != null 3526 // TODO: Probably not, because we don't want to resume voice on switching 3527 // back to this activity 3528 if (task.voiceInteractor != null) { 3529 startRunningVoiceLocked(task.voiceSession, r.info.applicationInfo.uid); 3530 } else { 3531 finishRunningVoiceLocked(); 3532 3533 if (mLastResumedActivity != null) { 3534 final IVoiceInteractionSession session; 3535 3536 final TaskRecord lastResumedActivityTask = mLastResumedActivity.getTask(); 3537 if (lastResumedActivityTask != null 3538 && lastResumedActivityTask.voiceSession != null) { 3539 session = lastResumedActivityTask.voiceSession; 3540 } else { 3541 session = mLastResumedActivity.voiceSession; 3542 } 3543 3544 if (session != null) { 3545 // We had been in a voice interaction session, but now focused has 3546 // move to something different. Just finish the session, we can't 3547 // return to it and retain the proper state and synchronization with 3548 // the voice interaction service. 3549 finishVoiceTask(session); 3550 } 3551 } 3552 } 3553 3554 if (mLastResumedActivity != null && r.userId != mLastResumedActivity.userId) { 3555 mUserController.sendForegroundProfileChanged(r.userId); 3556 } 3557 updateResumedAppTrace(r); 3558 mLastResumedActivity = r; 3559 3560 mWindowManager.setFocusedApp(r.appToken, true); 3561 3562 applyUpdateLockStateLocked(r); 3563 applyUpdateVrModeLocked(r); 3564 3565 EventLogTags.writeAmSetResumedActivity( 3566 r == null ? -1 : r.userId, 3567 r == null ? "NULL" : r.shortComponentName, 3568 reason); 3569 } 3570 3571 private void updateResumedAppTrace(@Nullable ActivityRecord resumed) { 3572 if (mTracedResumedActivity != null) { 3573 Trace.asyncTraceEnd(TRACE_TAG_ACTIVITY_MANAGER, 3574 constructResumedTraceName(mTracedResumedActivity.packageName), 0); 3575 } 3576 if (resumed != null) { 3577 Trace.asyncTraceBegin(TRACE_TAG_ACTIVITY_MANAGER, 3578 constructResumedTraceName(resumed.packageName), 0); 3579 } 3580 mTracedResumedActivity = resumed; 3581 } 3582 3583 private String constructResumedTraceName(String packageName) { 3584 return "focused app: " + packageName; 3585 } 3586 3587 @Override 3588 public void setFocusedStack(int stackId) { 3589 enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "setFocusedStack()"); 3590 if (DEBUG_FOCUS) Slog.d(TAG_FOCUS, "setFocusedStack: stackId=" + stackId); 3591 final long callingId = Binder.clearCallingIdentity(); 3592 try { 3593 synchronized (this) { 3594 final ActivityStack stack = mStackSupervisor.getStack(stackId); 3595 if (stack == null) { 3596 Slog.w(TAG, "setFocusedStack: No stack with id=" + stackId); 3597 return; 3598 } 3599 final ActivityRecord r = stack.topRunningActivityLocked(); 3600 if (mStackSupervisor.moveFocusableActivityStackToFrontLocked(r, "setFocusedStack")) { 3601 mStackSupervisor.resumeFocusedStackTopActivityLocked(); 3602 } 3603 } 3604 } finally { 3605 Binder.restoreCallingIdentity(callingId); 3606 } 3607 } 3608 3609 @Override 3610 public void setFocusedTask(int taskId) { 3611 enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "setFocusedTask()"); 3612 if (DEBUG_FOCUS) Slog.d(TAG_FOCUS, "setFocusedTask: taskId=" + taskId); 3613 final long callingId = Binder.clearCallingIdentity(); 3614 try { 3615 synchronized (this) { 3616 final TaskRecord task = mStackSupervisor.anyTaskForIdLocked(taskId); 3617 if (task == null) { 3618 return; 3619 } 3620 final ActivityRecord r = task.topRunningActivityLocked(); 3621 if (mStackSupervisor.moveFocusableActivityStackToFrontLocked(r, "setFocusedTask")) { 3622 mStackSupervisor.resumeFocusedStackTopActivityLocked(); 3623 } 3624 } 3625 } finally { 3626 Binder.restoreCallingIdentity(callingId); 3627 } 3628 } 3629 3630 /** Sets the task stack listener that gets callbacks when a task stack changes. */ 3631 @Override 3632 public void registerTaskStackListener(ITaskStackListener listener) throws RemoteException { 3633 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS, 3634 "registerTaskStackListener()"); 3635 mTaskChangeNotificationController.registerTaskStackListener(listener); 3636 } 3637 3638 /** 3639 * Unregister a task stack listener so that it stops receiving callbacks. 3640 */ 3641 @Override 3642 public void unregisterTaskStackListener(ITaskStackListener listener) throws RemoteException { 3643 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS, 3644 "unregisterTaskStackListener()"); 3645 mTaskChangeNotificationController.unregisterTaskStackListener(listener); 3646 } 3647 3648 @Override 3649 public void notifyActivityDrawn(IBinder token) { 3650 if (DEBUG_VISIBILITY) Slog.d(TAG_VISIBILITY, "notifyActivityDrawn: token=" + token); 3651 synchronized (this) { 3652 ActivityRecord r = mStackSupervisor.isInAnyStackLocked(token); 3653 if (r != null) { 3654 r.getStack().notifyActivityDrawnLocked(r); 3655 } 3656 } 3657 } 3658 3659 final void applyUpdateLockStateLocked(ActivityRecord r) { 3660 // Modifications to the UpdateLock state are done on our handler, outside 3661 // the activity manager's locks. The new state is determined based on the 3662 // state *now* of the relevant activity record. The object is passed to 3663 // the handler solely for logging detail, not to be consulted/modified. 3664 final boolean nextState = r != null && r.immersive; 3665 mHandler.sendMessage( 3666 mHandler.obtainMessage(IMMERSIVE_MODE_LOCK_MSG, (nextState) ? 1 : 0, 0, r)); 3667 } 3668 3669 final void applyUpdateVrModeLocked(ActivityRecord r) { 3670 // VR apps are expected to run in a main display. If an app is turning on VR for 3671 // itself, but lives in a dynamic stack, then make sure that it is moved to the main 3672 // fullscreen stack before enabling VR Mode. 3673 // TODO: The goal of this code is to keep the VR app on the main display. When the 3674 // stack implementation changes in the future, keep in mind that the use of the fullscreen 3675 // stack is a means to move the activity to the main display and a moveActivityToDisplay() 3676 // option would be a better choice here. 3677 if (r.requestedVrComponent != null && r.getDisplayId() != DEFAULT_DISPLAY) { 3678 Slog.i(TAG, "Moving " + r.shortComponentName + " from stack " + r.getStackId() 3679 + " to main stack for VR"); 3680 final ActivityStack stack = mStackSupervisor.getDefaultDisplay().getOrCreateStack( 3681 WINDOWING_MODE_FULLSCREEN, r.getActivityType(), true /* toTop */); 3682 moveTaskToStack(r.getTask().taskId, stack.mStackId, true /* toTop */); 3683 } 3684 mHandler.sendMessage( 3685 mHandler.obtainMessage(VR_MODE_CHANGE_MSG, 0, 0, r)); 3686 } 3687 3688 final void showAskCompatModeDialogLocked(ActivityRecord r) { 3689 Message msg = Message.obtain(); 3690 msg.what = SHOW_COMPAT_MODE_DIALOG_UI_MSG; 3691 msg.obj = r.getTask().askedCompatMode ? null : r; 3692 mUiHandler.sendMessage(msg); 3693 } 3694 3695 final AppWarnings getAppWarningsLocked() { 3696 return mAppWarnings; 3697 } 3698 3699 /** 3700 * Shows app warning dialogs, if necessary. 3701 * 3702 * @param r activity record for which the warnings may be displayed 3703 */ 3704 final void showAppWarningsIfNeededLocked(ActivityRecord r) { 3705 mAppWarnings.showUnsupportedCompileSdkDialogIfNeeded(r); 3706 mAppWarnings.showUnsupportedDisplaySizeDialogIfNeeded(r); 3707 mAppWarnings.showDeprecatedTargetDialogIfNeeded(r); 3708 } 3709 3710 private int updateLruProcessInternalLocked(ProcessRecord app, long now, int index, 3711 String what, Object obj, ProcessRecord srcApp) { 3712 app.lastActivityTime = now; 3713 3714 if (app.activities.size() > 0 || app.recentTasks.size() > 0) { 3715 // Don't want to touch dependent processes that are hosting activities. 3716 return index; 3717 } 3718 3719 int lrui = mLruProcesses.lastIndexOf(app); 3720 if (lrui < 0) { 3721 Slog.wtf(TAG, "Adding dependent process " + app + " not on LRU list: " 3722 + what + " " + obj + " from " + srcApp); 3723 return index; 3724 } 3725 3726 if (lrui >= index) { 3727 // Don't want to cause this to move dependent processes *back* in the 3728 // list as if they were less frequently used. 3729 return index; 3730 } 3731 3732 if (lrui >= mLruProcessActivityStart) { 3733 // Don't want to touch dependent processes that are hosting activities. 3734 return index; 3735 } 3736 3737 mLruProcesses.remove(lrui); 3738 if (index > 0) { 3739 index--; 3740 } 3741 if (DEBUG_LRU) Slog.d(TAG_LRU, "Moving dep from " + lrui + " to " + index 3742 + " in LRU list: " + app); 3743 mLruProcesses.add(index, app); 3744 return index; 3745 } 3746 3747 static void killProcessGroup(int uid, int pid) { 3748 if (sKillHandler != null) { 3749 sKillHandler.sendMessage( 3750 sKillHandler.obtainMessage(KillHandler.KILL_PROCESS_GROUP_MSG, uid, pid)); 3751 } else { 3752 Slog.w(TAG, "Asked to kill process group before system bringup!"); 3753 Process.killProcessGroup(uid, pid); 3754 } 3755 } 3756 3757 final void removeLruProcessLocked(ProcessRecord app) { 3758 int lrui = mLruProcesses.lastIndexOf(app); 3759 if (lrui >= 0) { 3760 if (!app.killed) { 3761 if (app.persistent) { 3762 Slog.w(TAG, "Removing persistent process that hasn't been killed: " + app); 3763 } else { 3764 Slog.wtfStack(TAG, "Removing process that hasn't been killed: " + app); 3765 if (app.pid > 0) { 3766 killProcessQuiet(app.pid); 3767 killProcessGroup(app.uid, app.pid); 3768 } else { 3769 app.pendingStart = false; 3770 } 3771 } 3772 } 3773 if (lrui <= mLruProcessActivityStart) { 3774 mLruProcessActivityStart--; 3775 } 3776 if (lrui <= mLruProcessServiceStart) { 3777 mLruProcessServiceStart--; 3778 } 3779 mLruProcesses.remove(lrui); 3780 } 3781 } 3782 3783 final void updateLruProcessLocked(ProcessRecord app, boolean activityChange, 3784 ProcessRecord client) { 3785 final boolean hasActivity = app.activities.size() > 0 || app.hasClientActivities 3786 || app.treatLikeActivity || app.recentTasks.size() > 0; 3787 final boolean hasService = false; // not impl yet. app.services.size() > 0; 3788 if (!activityChange && hasActivity) { 3789 // The process has activities, so we are only allowing activity-based adjustments 3790 // to move it. It should be kept in the front of the list with other 3791 // processes that have activities, and we don't want those to change their 3792 // order except due to activity operations. 3793 return; 3794 } 3795 3796 mLruSeq++; 3797 final long now = SystemClock.uptimeMillis(); 3798 app.lastActivityTime = now; 3799 3800 // First a quick reject: if the app is already at the position we will 3801 // put it, then there is nothing to do. 3802 if (hasActivity) { 3803 final int N = mLruProcesses.size(); 3804 if (N > 0 && mLruProcesses.get(N-1) == app) { 3805 if (DEBUG_LRU) Slog.d(TAG_LRU, "Not moving, already top activity: " + app); 3806 return; 3807 } 3808 } else { 3809 if (mLruProcessServiceStart > 0 3810 && mLruProcesses.get(mLruProcessServiceStart-1) == app) { 3811 if (DEBUG_LRU) Slog.d(TAG_LRU, "Not moving, already top other: " + app); 3812 return; 3813 } 3814 } 3815 3816 int lrui = mLruProcesses.lastIndexOf(app); 3817 3818 if (app.persistent && lrui >= 0) { 3819 // We don't care about the position of persistent processes, as long as 3820 // they are in the list. 3821 if (DEBUG_LRU) Slog.d(TAG_LRU, "Not moving, persistent: " + app); 3822 return; 3823 } 3824 3825 /* In progress: compute new position first, so we can avoid doing work 3826 if the process is not actually going to move. Not yet working. 3827 int addIndex; 3828 int nextIndex; 3829 boolean inActivity = false, inService = false; 3830 if (hasActivity) { 3831 // Process has activities, put it at the very tipsy-top. 3832 addIndex = mLruProcesses.size(); 3833 nextIndex = mLruProcessServiceStart; 3834 inActivity = true; 3835 } else if (hasService) { 3836 // Process has services, put it at the top of the service list. 3837 addIndex = mLruProcessActivityStart; 3838 nextIndex = mLruProcessServiceStart; 3839 inActivity = true; 3840 inService = true; 3841 } else { 3842 // Process not otherwise of interest, it goes to the top of the non-service area. 3843 addIndex = mLruProcessServiceStart; 3844 if (client != null) { 3845 int clientIndex = mLruProcesses.lastIndexOf(client); 3846 if (clientIndex < 0) Slog.d(TAG, "Unknown client " + client + " when updating " 3847 + app); 3848 if (clientIndex >= 0 && addIndex > clientIndex) { 3849 addIndex = clientIndex; 3850 } 3851 } 3852 nextIndex = addIndex > 0 ? addIndex-1 : addIndex; 3853 } 3854 3855 Slog.d(TAG, "Update LRU at " + lrui + " to " + addIndex + " (act=" 3856 + mLruProcessActivityStart + "): " + app); 3857 */ 3858 3859 if (lrui >= 0) { 3860 if (lrui < mLruProcessActivityStart) { 3861 mLruProcessActivityStart--; 3862 } 3863 if (lrui < mLruProcessServiceStart) { 3864 mLruProcessServiceStart--; 3865 } 3866 /* 3867 if (addIndex > lrui) { 3868 addIndex--; 3869 } 3870 if (nextIndex > lrui) { 3871 nextIndex--; 3872 } 3873 */ 3874 mLruProcesses.remove(lrui); 3875 } 3876 3877 /* 3878 mLruProcesses.add(addIndex, app); 3879 if (inActivity) { 3880 mLruProcessActivityStart++; 3881 } 3882 if (inService) { 3883 mLruProcessActivityStart++; 3884 } 3885 */ 3886 3887 int nextIndex; 3888 if (hasActivity) { 3889 final int N = mLruProcesses.size(); 3890 if ((app.activities.size() == 0 || app.recentTasks.size() > 0) 3891 && mLruProcessActivityStart < (N - 1)) { 3892 // Process doesn't have activities, but has clients with 3893 // activities... move it up, but one below the top (the top 3894 // should always have a real activity). 3895 if (DEBUG_LRU) Slog.d(TAG_LRU, 3896 "Adding to second-top of LRU activity list: " + app); 3897 mLruProcesses.add(N - 1, app); 3898 // To keep it from spamming the LRU list (by making a bunch of clients), 3899 // we will push down any other entries owned by the app. 3900 final int uid = app.info.uid; 3901 for (int i = N - 2; i > mLruProcessActivityStart; i--) { 3902 ProcessRecord subProc = mLruProcesses.get(i); 3903 if (subProc.info.uid == uid) { 3904 // We want to push this one down the list. If the process after 3905 // it is for the same uid, however, don't do so, because we don't 3906 // want them internally to be re-ordered. 3907 if (mLruProcesses.get(i - 1).info.uid != uid) { 3908 if (DEBUG_LRU) Slog.d(TAG_LRU, 3909 "Pushing uid " + uid + " swapping at " + i + ": " 3910 + mLruProcesses.get(i) + " : " + mLruProcesses.get(i - 1)); 3911 ProcessRecord tmp = mLruProcesses.get(i); 3912 mLruProcesses.set(i, mLruProcesses.get(i - 1)); 3913 mLruProcesses.set(i - 1, tmp); 3914 i--; 3915 } 3916 } else { 3917 // A gap, we can stop here. 3918 break; 3919 } 3920 } 3921 } else { 3922 // Process has activities, put it at the very tipsy-top. 3923 if (DEBUG_LRU) Slog.d(TAG_LRU, "Adding to top of LRU activity list: " + app); 3924 mLruProcesses.add(app); 3925 } 3926 nextIndex = mLruProcessServiceStart; 3927 } else if (hasService) { 3928 // Process has services, put it at the top of the service list. 3929 if (DEBUG_LRU) Slog.d(TAG_LRU, "Adding to top of LRU service list: " + app); 3930 mLruProcesses.add(mLruProcessActivityStart, app); 3931 nextIndex = mLruProcessServiceStart; 3932 mLruProcessActivityStart++; 3933 } else { 3934 // Process not otherwise of interest, it goes to the top of the non-service area. 3935 int index = mLruProcessServiceStart; 3936 if (client != null) { 3937 // If there is a client, don't allow the process to be moved up higher 3938 // in the list than that client. 3939 int clientIndex = mLruProcesses.lastIndexOf(client); 3940 if (DEBUG_LRU && clientIndex < 0) Slog.d(TAG_LRU, "Unknown client " + client 3941 + " when updating " + app); 3942 if (clientIndex <= lrui) { 3943 // Don't allow the client index restriction to push it down farther in the 3944 // list than it already is. 3945 clientIndex = lrui; 3946 } 3947 if (clientIndex >= 0 && index > clientIndex) { 3948 index = clientIndex; 3949 } 3950 } 3951 if (DEBUG_LRU) Slog.d(TAG_LRU, "Adding at " + index + " of LRU list: " + app); 3952 mLruProcesses.add(index, app); 3953 nextIndex = index-1; 3954 mLruProcessActivityStart++; 3955 mLruProcessServiceStart++; 3956 } 3957 3958 // If the app is currently using a content provider or service, 3959 // bump those processes as well. 3960 for (int j=app.connections.size()-1; j>=0; j--) { 3961 ConnectionRecord cr = app.connections.valueAt(j); 3962 if (cr.binding != null && !cr.serviceDead && cr.binding.service != null 3963 && cr.binding.service.app != null 3964 && cr.binding.service.app.lruSeq != mLruSeq 3965 && !cr.binding.service.app.persistent) { 3966 nextIndex = updateLruProcessInternalLocked(cr.binding.service.app, now, nextIndex, 3967 "service connection", cr, app); 3968 } 3969 } 3970 for (int j=app.conProviders.size()-1; j>=0; j--) { 3971 ContentProviderRecord cpr = app.conProviders.get(j).provider; 3972 if (cpr.proc != null && cpr.proc.lruSeq != mLruSeq && !cpr.proc.persistent) { 3973 nextIndex = updateLruProcessInternalLocked(cpr.proc, now, nextIndex, 3974 "provider reference", cpr, app); 3975 } 3976 } 3977 } 3978 3979 final ProcessRecord getProcessRecordLocked(String processName, int uid, boolean keepIfLarge) { 3980 if (uid == SYSTEM_UID) { 3981 // The system gets to run in any process. If there are multiple 3982 // processes with the same uid, just pick the first (this 3983 // should never happen). 3984 SparseArray<ProcessRecord> procs = mProcessNames.getMap().get(processName); 3985 if (procs == null) return null; 3986 final int procCount = procs.size(); 3987 for (int i = 0; i < procCount; i++) { 3988 final int procUid = procs.keyAt(i); 3989 if (UserHandle.isApp(procUid) || !UserHandle.isSameUser(procUid, uid)) { 3990 // Don't use an app process or different user process for system component. 3991 continue; 3992 } 3993 return procs.valueAt(i); 3994 } 3995 } 3996 ProcessRecord proc = mProcessNames.get(processName, uid); 3997 if (false && proc != null && !keepIfLarge 3998 && proc.setProcState >= ActivityManager.PROCESS_STATE_CACHED_EMPTY 3999 && proc.lastCachedPss >= 4000) { 4000 // Turn this condition on to cause killing to happen regularly, for testing. 4001 if (proc.baseProcessTracker != null) { 4002 proc.baseProcessTracker.reportCachedKill(proc.pkgList, proc.lastCachedPss); 4003 } 4004 proc.kill(Long.toString(proc.lastCachedPss) + "k from cached", true); 4005 } else if (proc != null && !keepIfLarge 4006 && mLastMemoryLevel > ProcessStats.ADJ_MEM_FACTOR_NORMAL 4007 && proc.setProcState >= ActivityManager.PROCESS_STATE_CACHED_EMPTY) { 4008 if (DEBUG_PSS) Slog.d(TAG_PSS, "May not keep " + proc + ": pss=" + proc.lastCachedPss); 4009 if (proc.lastCachedPss >= mProcessList.getCachedRestoreThresholdKb()) { 4010 if (proc.baseProcessTracker != null) { 4011 proc.baseProcessTracker.reportCachedKill(proc.pkgList, proc.lastCachedPss); 4012 } 4013 proc.kill(Long.toString(proc.lastCachedPss) + "k from cached", true); 4014 } 4015 } 4016 return proc; 4017 } 4018 4019 void notifyPackageUse(String packageName, int reason) { 4020 synchronized(this) { 4021 getPackageManagerInternalLocked().notifyPackageUse(packageName, reason); 4022 } 4023 } 4024 4025 boolean isNextTransitionForward() { 4026 int transit = mWindowManager.getPendingAppTransition(); 4027 return transit == TRANSIT_ACTIVITY_OPEN 4028 || transit == TRANSIT_TASK_OPEN 4029 || transit == TRANSIT_TASK_TO_FRONT; 4030 } 4031 4032 boolean startIsolatedProcess(String entryPoint, String[] entryPointArgs, 4033 String processName, String abiOverride, int uid, Runnable crashHandler) { 4034 synchronized(this) { 4035 ApplicationInfo info = new ApplicationInfo(); 4036 // In general the ApplicationInfo.uid isn't neccesarily equal to ProcessRecord.uid. 4037 // For isolated processes, the former contains the parent's uid and the latter the 4038 // actual uid of the isolated process. 4039 // In the special case introduced by this method (which is, starting an isolated 4040 // process directly from the SystemServer without an actual parent app process) the 4041 // closest thing to a parent's uid is SYSTEM_UID. 4042 // The only important thing here is to keep AI.uid != PR.uid, in order to trigger 4043 // the |isolated| logic in the ProcessRecord constructor. 4044 info.uid = SYSTEM_UID; 4045 info.processName = processName; 4046 info.className = entryPoint; 4047 info.packageName = "android"; 4048 info.seInfoUser = SELinuxUtil.COMPLETE_STR; 4049 info.targetSdkVersion = Build.VERSION.SDK_INT; 4050 ProcessRecord proc = startProcessLocked(processName, info /* info */, 4051 false /* knownToBeDead */, 0 /* intentFlags */, "" /* hostingType */, 4052 null /* hostingName */, true /* allowWhileBooting */, true /* isolated */, 4053 uid, true /* keepIfLarge */, abiOverride, entryPoint, entryPointArgs, 4054 crashHandler); 4055 return proc != null; 4056 } 4057 } 4058 4059 @GuardedBy("this") 4060 final ProcessRecord startProcessLocked(String processName, 4061 ApplicationInfo info, boolean knownToBeDead, int intentFlags, 4062 String hostingType, ComponentName hostingName, boolean allowWhileBooting, 4063 boolean isolated, boolean keepIfLarge) { 4064 return startProcessLocked(processName, info, knownToBeDead, intentFlags, hostingType, 4065 hostingName, allowWhileBooting, isolated, 0 /* isolatedUid */, keepIfLarge, 4066 null /* ABI override */, null /* entryPoint */, null /* entryPointArgs */, 4067 null /* crashHandler */); 4068 } 4069 4070 @GuardedBy("this") 4071 final ProcessRecord startProcessLocked(String processName, ApplicationInfo info, 4072 boolean knownToBeDead, int intentFlags, String hostingType, ComponentName hostingName, 4073 boolean allowWhileBooting, boolean isolated, int isolatedUid, boolean keepIfLarge, 4074 String abiOverride, String entryPoint, String[] entryPointArgs, Runnable crashHandler) { 4075 long startTime = SystemClock.elapsedRealtime(); 4076 ProcessRecord app; 4077 if (!isolated) { 4078 app = getProcessRecordLocked(processName, info.uid, keepIfLarge); 4079 checkTime(startTime, "startProcess: after getProcessRecord"); 4080 4081 if ((intentFlags & Intent.FLAG_FROM_BACKGROUND) != 0) { 4082 // If we are in the background, then check to see if this process 4083 // is bad. If so, we will just silently fail. 4084 if (mAppErrors.isBadProcessLocked(info)) { 4085 if (DEBUG_PROCESSES) Slog.v(TAG, "Bad process: " + info.uid 4086 + "/" + info.processName); 4087 return null; 4088 } 4089 } else { 4090 // When the user is explicitly starting a process, then clear its 4091 // crash count so that we won't make it bad until they see at 4092 // least one crash dialog again, and make the process good again 4093 // if it had been bad. 4094 if (DEBUG_PROCESSES) Slog.v(TAG, "Clearing bad process: " + info.uid 4095 + "/" + info.processName); 4096 mAppErrors.resetProcessCrashTimeLocked(info); 4097 if (mAppErrors.isBadProcessLocked(info)) { 4098 EventLog.writeEvent(EventLogTags.AM_PROC_GOOD, 4099 UserHandle.getUserId(info.uid), info.uid, 4100 info.processName); 4101 mAppErrors.clearBadProcessLocked(info); 4102 if (app != null) { 4103 app.bad = false; 4104 } 4105 } 4106 } 4107 } else { 4108 // If this is an isolated process, it can't re-use an existing process. 4109 app = null; 4110 } 4111 4112 // We don't have to do anything more if: 4113 // (1) There is an existing application record; and 4114 // (2) The caller doesn't think it is dead, OR there is no thread 4115 // object attached to it so we know it couldn't have crashed; and 4116 // (3) There is a pid assigned to it, so it is either starting or 4117 // already running. 4118 if (DEBUG_PROCESSES) Slog.v(TAG_PROCESSES, "startProcess: name=" + processName 4119 + " app=" + app + " knownToBeDead=" + knownToBeDead 4120 + " thread=" + (app != null ? app.thread : null) 4121 + " pid=" + (app != null ? app.pid : -1)); 4122 if (app != null && app.pid > 0) { 4123 if ((!knownToBeDead && !app.killed) || app.thread == null) { 4124 // We already have the app running, or are waiting for it to 4125 // come up (we have a pid but not yet its thread), so keep it. 4126 if (DEBUG_PROCESSES) Slog.v(TAG_PROCESSES, "App already running: " + app); 4127 // If this is a new package in the process, add the package to the list 4128 app.addPackage(info.packageName, info.versionCode, mProcessStats); 4129 checkTime(startTime, "startProcess: done, added package to proc"); 4130 return app; 4131 } 4132 4133 // An application record is attached to a previous process, 4134 // clean it up now. 4135 if (DEBUG_PROCESSES || DEBUG_CLEANUP) Slog.v(TAG_PROCESSES, "App died: " + app); 4136 checkTime(startTime, "startProcess: bad proc running, killing"); 4137 killProcessGroup(app.uid, app.pid); 4138 handleAppDiedLocked(app, true, true); 4139 checkTime(startTime, "startProcess: done killing old proc"); 4140 } 4141 4142 String hostingNameStr = hostingName != null 4143 ? hostingName.flattenToShortString() : null; 4144 4145 if (app == null) { 4146 checkTime(startTime, "startProcess: creating new process record"); 4147 app = newProcessRecordLocked(info, processName, isolated, isolatedUid); 4148 if (app == null) { 4149 Slog.w(TAG, "Failed making new process record for " 4150 + processName + "/" + info.uid + " isolated=" + isolated); 4151 return null; 4152 } 4153 app.crashHandler = crashHandler; 4154 app.isolatedEntryPoint = entryPoint; 4155 app.isolatedEntryPointArgs = entryPointArgs; 4156 checkTime(startTime, "startProcess: done creating new process record"); 4157 } else { 4158 // If this is a new package in the process, add the package to the list 4159 app.addPackage(info.packageName, info.versionCode, mProcessStats); 4160 checkTime(startTime, "startProcess: added package to existing proc"); 4161 } 4162 4163 // If the system is not ready yet, then hold off on starting this 4164 // process until it is. 4165 if (!mProcessesReady 4166 && !isAllowedWhileBooting(info) 4167 && !allowWhileBooting) { 4168 if (!mProcessesOnHold.contains(app)) { 4169 mProcessesOnHold.add(app); 4170 } 4171 if (DEBUG_PROCESSES) Slog.v(TAG_PROCESSES, 4172 "System not ready, putting on hold: " + app); 4173 checkTime(startTime, "startProcess: returning with proc on hold"); 4174 return app; 4175 } 4176 4177 checkTime(startTime, "startProcess: stepping in to startProcess"); 4178 final boolean success = startProcessLocked(app, hostingType, hostingNameStr, abiOverride); 4179 checkTime(startTime, "startProcess: done starting proc!"); 4180 return success ? app : null; 4181 } 4182 4183 boolean isAllowedWhileBooting(ApplicationInfo ai) { 4184 return (ai.flags&ApplicationInfo.FLAG_PERSISTENT) != 0; 4185 } 4186 4187 @GuardedBy("this") 4188 private final void startProcessLocked(ProcessRecord app, 4189 String hostingType, String hostingNameStr) { 4190 startProcessLocked(app, hostingType, hostingNameStr, null /* abiOverride */); 4191 } 4192 4193 @GuardedBy("this") 4194 private final boolean startProcessLocked(ProcessRecord app, 4195 String hostingType, String hostingNameStr, String abiOverride) { 4196 return startProcessLocked(app, hostingType, hostingNameStr, 4197 false /* disableHiddenApiChecks */, abiOverride); 4198 } 4199 4200 /** 4201 * @return {@code true} if process start is successful, false otherwise. 4202 */ 4203 @GuardedBy("this") 4204 private final boolean startProcessLocked(ProcessRecord app, String hostingType, 4205 String hostingNameStr, boolean disableHiddenApiChecks, String abiOverride) { 4206 if (app.pendingStart) { 4207 return true; 4208 } 4209 long startTime = SystemClock.elapsedRealtime(); 4210 if (app.pid > 0 && app.pid != MY_PID) { 4211 checkTime(startTime, "startProcess: removing from pids map"); 4212 synchronized (mPidsSelfLocked) { 4213 mPidsSelfLocked.remove(app.pid); 4214 mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app); 4215 } 4216 checkTime(startTime, "startProcess: done removing from pids map"); 4217 app.setPid(0); 4218 } 4219 4220 if (DEBUG_PROCESSES && mProcessesOnHold.contains(app)) Slog.v(TAG_PROCESSES, 4221 "startProcessLocked removing on hold: " + app); 4222 mProcessesOnHold.remove(app); 4223 4224 checkTime(startTime, "startProcess: starting to update cpu stats"); 4225 updateCpuStats(); 4226 checkTime(startTime, "startProcess: done updating cpu stats"); 4227 4228 try { 4229 try { 4230 final int userId = UserHandle.getUserId(app.uid); 4231 AppGlobals.getPackageManager().checkPackageStartable(app.info.packageName, userId); 4232 } catch (RemoteException e) { 4233 throw e.rethrowAsRuntimeException(); 4234 } 4235 4236 int uid = app.uid; 4237 int[] gids = null; 4238 int mountExternal = Zygote.MOUNT_EXTERNAL_NONE; 4239 if (!app.isolated) { 4240 int[] permGids = null; 4241 try { 4242 checkTime(startTime, "startProcess: getting gids from package manager"); 4243 final IPackageManager pm = AppGlobals.getPackageManager(); 4244 permGids = pm.getPackageGids(app.info.packageName, 4245 MATCH_DEBUG_TRIAGED_MISSING, app.userId); 4246 StorageManagerInternal storageManagerInternal = LocalServices.getService( 4247 StorageManagerInternal.class); 4248 mountExternal = storageManagerInternal.getExternalStorageMountMode(uid, 4249 app.info.packageName); 4250 } catch (RemoteException e) { 4251 throw e.rethrowAsRuntimeException(); 4252 } 4253 4254 /* 4255 * Add shared application and profile GIDs so applications can share some 4256 * resources like shared libraries and access user-wide resources 4257 */ 4258 if (ArrayUtils.isEmpty(permGids)) { 4259 gids = new int[3]; 4260 } else { 4261 gids = new int[permGids.length + 3]; 4262 System.arraycopy(permGids, 0, gids, 3, permGids.length); 4263 } 4264 gids[0] = UserHandle.getSharedAppGid(UserHandle.getAppId(uid)); 4265 gids[1] = UserHandle.getCacheAppGid(UserHandle.getAppId(uid)); 4266 gids[2] = UserHandle.getUserGid(UserHandle.getUserId(uid)); 4267 4268 // Replace any invalid GIDs 4269 if (gids[0] == UserHandle.ERR_GID) gids[0] = gids[2]; 4270 if (gids[1] == UserHandle.ERR_GID) gids[1] = gids[2]; 4271 } 4272 checkTime(startTime, "startProcess: building args"); 4273 if (mFactoryTest != FactoryTest.FACTORY_TEST_OFF) { 4274 if (mFactoryTest == FactoryTest.FACTORY_TEST_LOW_LEVEL 4275 && mTopComponent != null 4276 && app.processName.equals(mTopComponent.getPackageName())) { 4277 uid = 0; 4278 } 4279 if (mFactoryTest == FactoryTest.FACTORY_TEST_HIGH_LEVEL 4280 && (app.info.flags&ApplicationInfo.FLAG_FACTORY_TEST) != 0) { 4281 uid = 0; 4282 } 4283 } 4284 int runtimeFlags = 0; 4285 if ((app.info.flags & ApplicationInfo.FLAG_DEBUGGABLE) != 0) { 4286 runtimeFlags |= Zygote.DEBUG_ENABLE_JDWP; 4287 runtimeFlags |= Zygote.DEBUG_JAVA_DEBUGGABLE; 4288 // Also turn on CheckJNI for debuggable apps. It's quite 4289 // awkward to turn on otherwise. 4290 runtimeFlags |= Zygote.DEBUG_ENABLE_CHECKJNI; 4291 } 4292 // Run the app in safe mode if its manifest requests so or the 4293 // system is booted in safe mode. 4294 if ((app.info.flags & ApplicationInfo.FLAG_VM_SAFE_MODE) != 0 || 4295 mSafeMode == true) { 4296 runtimeFlags |= Zygote.DEBUG_ENABLE_SAFEMODE; 4297 } 4298 if ("1".equals(SystemProperties.get("debug.checkjni"))) { 4299 runtimeFlags |= Zygote.DEBUG_ENABLE_CHECKJNI; 4300 } 4301 String genDebugInfoProperty = SystemProperties.get("debug.generate-debug-info"); 4302 if ("1".equals(genDebugInfoProperty) || "true".equals(genDebugInfoProperty)) { 4303 runtimeFlags |= Zygote.DEBUG_GENERATE_DEBUG_INFO; 4304 } 4305 String genMiniDebugInfoProperty = SystemProperties.get("dalvik.vm.minidebuginfo"); 4306 if ("1".equals(genMiniDebugInfoProperty) || "true".equals(genMiniDebugInfoProperty)) { 4307 runtimeFlags |= Zygote.DEBUG_GENERATE_MINI_DEBUG_INFO; 4308 } 4309 if ("1".equals(SystemProperties.get("debug.jni.logging"))) { 4310 runtimeFlags |= Zygote.DEBUG_ENABLE_JNI_LOGGING; 4311 } 4312 if ("1".equals(SystemProperties.get("debug.assert"))) { 4313 runtimeFlags |= Zygote.DEBUG_ENABLE_ASSERT; 4314 } 4315 if (mNativeDebuggingApp != null && mNativeDebuggingApp.equals(app.processName)) { 4316 // Enable all debug flags required by the native debugger. 4317 runtimeFlags |= Zygote.DEBUG_ALWAYS_JIT; // Don't interpret anything 4318 runtimeFlags |= Zygote.DEBUG_GENERATE_DEBUG_INFO; // Generate debug info 4319 runtimeFlags |= Zygote.DEBUG_NATIVE_DEBUGGABLE; // Disbale optimizations 4320 mNativeDebuggingApp = null; 4321 } 4322 4323 if (app.info.isPrivilegedApp() && 4324 DexManager.isPackageSelectedToRunOob(app.pkgList.keySet())) { 4325 runtimeFlags |= Zygote.ONLY_USE_SYSTEM_OAT_FILES; 4326 } 4327 4328 if (!disableHiddenApiChecks && !mHiddenApiBlacklist.isDisabled()) { 4329 app.info.maybeUpdateHiddenApiEnforcementPolicy( 4330 mHiddenApiBlacklist.getPolicyForPrePApps(), 4331 mHiddenApiBlacklist.getPolicyForPApps()); 4332 @HiddenApiEnforcementPolicy int policy = 4333 app.info.getHiddenApiEnforcementPolicy(); 4334 int policyBits = (policy << Zygote.API_ENFORCEMENT_POLICY_SHIFT); 4335 if ((policyBits & Zygote.API_ENFORCEMENT_POLICY_MASK) != policyBits) { 4336 throw new IllegalStateException("Invalid API policy: " + policy); 4337 } 4338 runtimeFlags |= policyBits; 4339 } 4340 4341 String invokeWith = null; 4342 if ((app.info.flags & ApplicationInfo.FLAG_DEBUGGABLE) != 0) { 4343 // Debuggable apps may include a wrapper script with their library directory. 4344 String wrapperFileName = app.info.nativeLibraryDir + "/wrap.sh"; 4345 StrictMode.ThreadPolicy oldPolicy = StrictMode.allowThreadDiskReads(); 4346 try { 4347 if (new File(wrapperFileName).exists()) { 4348 invokeWith = "/system/bin/logwrapper " + wrapperFileName; 4349 } 4350 } finally { 4351 StrictMode.setThreadPolicy(oldPolicy); 4352 } 4353 } 4354 4355 String requiredAbi = (abiOverride != null) ? abiOverride : app.info.primaryCpuAbi; 4356 if (requiredAbi == null) { 4357 requiredAbi = Build.SUPPORTED_ABIS[0]; 4358 } 4359 4360 String instructionSet = null; 4361 if (app.info.primaryCpuAbi != null) { 4362 instructionSet = VMRuntime.getInstructionSet(app.info.primaryCpuAbi); 4363 } 4364 4365 app.gids = gids; 4366 app.requiredAbi = requiredAbi; 4367 app.instructionSet = instructionSet; 4368 4369 // the per-user SELinux context must be set 4370 if (TextUtils.isEmpty(app.info.seInfoUser)) { 4371 Slog.wtf(TAG, "SELinux tag not defined", 4372 new IllegalStateException("SELinux tag not defined for " 4373 + app.info.packageName + " (uid " + app.uid + ")")); 4374 } 4375 final String seInfo = app.info.seInfo 4376 + (TextUtils.isEmpty(app.info.seInfoUser) ? "" : app.info.seInfoUser); 4377 // Start the process. It will either succeed and return a result containing 4378 // the PID of the new process, or else throw a RuntimeException. 4379 final String entryPoint = "android.app.ActivityThread"; 4380 4381 return startProcessLocked(hostingType, hostingNameStr, entryPoint, app, uid, gids, 4382 runtimeFlags, mountExternal, seInfo, requiredAbi, instructionSet, invokeWith, 4383 startTime); 4384 } catch (RuntimeException e) { 4385 Slog.e(TAG, "Failure starting process " + app.processName, e); 4386 4387 // Something went very wrong while trying to start this process; one 4388 // common case is when the package is frozen due to an active 4389 // upgrade. To recover, clean up any active bookkeeping related to 4390 // starting this process. (We already invoked this method once when 4391 // the package was initially frozen through KILL_APPLICATION_MSG, so 4392 // it doesn't hurt to use it again.) 4393 forceStopPackageLocked(app.info.packageName, UserHandle.getAppId(app.uid), false, 4394 false, true, false, false, UserHandle.getUserId(app.userId), "start failure"); 4395 return false; 4396 } 4397 } 4398 4399 @GuardedBy("this") 4400 private boolean startProcessLocked(String hostingType, String hostingNameStr, String entryPoint, 4401 ProcessRecord app, int uid, int[] gids, int runtimeFlags, int mountExternal, 4402 String seInfo, String requiredAbi, String instructionSet, String invokeWith, 4403 long startTime) { 4404 app.pendingStart = true; 4405 app.killedByAm = false; 4406 app.removed = false; 4407 app.killed = false; 4408 final long startSeq = app.startSeq = ++mProcStartSeqCounter; 4409 app.setStartParams(uid, hostingType, hostingNameStr, seInfo, startTime); 4410 if (mConstants.FLAG_PROCESS_START_ASYNC) { 4411 if (DEBUG_PROCESSES) Slog.i(TAG_PROCESSES, 4412 "Posting procStart msg for " + app.toShortString()); 4413 mProcStartHandler.post(() -> { 4414 try { 4415 synchronized (ActivityManagerService.this) { 4416 final String reason = isProcStartValidLocked(app, startSeq); 4417 if (reason != null) { 4418 Slog.w(TAG_PROCESSES, app + " not valid anymore," 4419 + " don't start process, " + reason); 4420 app.pendingStart = false; 4421 return; 4422 } 4423 app.usingWrapper = invokeWith != null 4424 || SystemProperties.get("wrap." + app.processName) != null; 4425 mPendingStarts.put(startSeq, app); 4426 } 4427 final ProcessStartResult startResult = startProcess(app.hostingType, entryPoint, 4428 app, app.startUid, gids, runtimeFlags, mountExternal, app.seInfo, 4429 requiredAbi, instructionSet, invokeWith, app.startTime); 4430 synchronized (ActivityManagerService.this) { 4431 handleProcessStartedLocked(app, startResult, startSeq); 4432 } 4433 } catch (RuntimeException e) { 4434 synchronized (ActivityManagerService.this) { 4435 Slog.e(TAG, "Failure starting process " + app.processName, e); 4436 mPendingStarts.remove(startSeq); 4437 app.pendingStart = false; 4438 forceStopPackageLocked(app.info.packageName, UserHandle.getAppId(app.uid), 4439 false, false, true, false, false, 4440 UserHandle.getUserId(app.userId), "start failure"); 4441 } 4442 } 4443 }); 4444 return true; 4445 } else { 4446 try { 4447 final ProcessStartResult startResult = startProcess(hostingType, entryPoint, app, 4448 uid, gids, runtimeFlags, mountExternal, seInfo, requiredAbi, instructionSet, 4449 invokeWith, startTime); 4450 handleProcessStartedLocked(app, startResult.pid, startResult.usingWrapper, 4451 startSeq, false); 4452 } catch (RuntimeException e) { 4453 Slog.e(TAG, "Failure starting process " + app.processName, e); 4454 app.pendingStart = false; 4455 forceStopPackageLocked(app.info.packageName, UserHandle.getAppId(app.uid), 4456 false, false, true, false, false, 4457 UserHandle.getUserId(app.userId), "start failure"); 4458 } 4459 return app.pid > 0; 4460 } 4461 } 4462 4463 private ProcessStartResult startProcess(String hostingType, String entryPoint, 4464 ProcessRecord app, int uid, int[] gids, int runtimeFlags, int mountExternal, 4465 String seInfo, String requiredAbi, String instructionSet, String invokeWith, 4466 long startTime) { 4467 try { 4468 Trace.traceBegin(Trace.TRACE_TAG_ACTIVITY_MANAGER, "Start proc: " + 4469 app.processName); 4470 checkTime(startTime, "startProcess: asking zygote to start proc"); 4471 final ProcessStartResult startResult; 4472 if (hostingType.equals("webview_service")) { 4473 startResult = startWebView(entryPoint, 4474 app.processName, uid, uid, gids, runtimeFlags, mountExternal, 4475 app.info.targetSdkVersion, seInfo, requiredAbi, instructionSet, 4476 app.info.dataDir, null, 4477 new String[] {PROC_START_SEQ_IDENT + app.startSeq}); 4478 } else { 4479 startResult = Process.start(entryPoint, 4480 app.processName, uid, uid, gids, runtimeFlags, mountExternal, 4481 app.info.targetSdkVersion, seInfo, requiredAbi, instructionSet, 4482 app.info.dataDir, invokeWith, 4483 new String[] {PROC_START_SEQ_IDENT + app.startSeq}); 4484 } 4485 checkTime(startTime, "startProcess: returned from zygote!"); 4486 return startResult; 4487 } finally { 4488 Trace.traceEnd(Trace.TRACE_TAG_ACTIVITY_MANAGER); 4489 } 4490 } 4491 4492 @GuardedBy("this") 4493 private String isProcStartValidLocked(ProcessRecord app, long expectedStartSeq) { 4494 StringBuilder sb = null; 4495 if (app.killedByAm) { 4496 if (sb == null) sb = new StringBuilder(); 4497 sb.append("killedByAm=true;"); 4498 } 4499 if (mProcessNames.get(app.processName, app.uid) != app) { 4500 if (sb == null) sb = new StringBuilder(); 4501 sb.append("No entry in mProcessNames;"); 4502 } 4503 if (!app.pendingStart) { 4504 if (sb == null) sb = new StringBuilder(); 4505 sb.append("pendingStart=false;"); 4506 } 4507 if (app.startSeq > expectedStartSeq) { 4508 if (sb == null) sb = new StringBuilder(); 4509 sb.append("seq=" + app.startSeq + ",expected=" + expectedStartSeq + ";"); 4510 } 4511 return sb == null ? null : sb.toString(); 4512 } 4513 4514 @GuardedBy("this") 4515 private boolean handleProcessStartedLocked(ProcessRecord pending, 4516 ProcessStartResult startResult, long expectedStartSeq) { 4517 // Indicates that this process start has been taken care of. 4518 if (mPendingStarts.get(expectedStartSeq) == null) { 4519 if (pending.pid == startResult.pid) { 4520 pending.usingWrapper = startResult.usingWrapper; 4521 // TODO: Update already existing clients of usingWrapper 4522 } 4523 return false; 4524 } 4525 return handleProcessStartedLocked(pending, startResult.pid, startResult.usingWrapper, 4526 expectedStartSeq, false); 4527 } 4528 4529 @GuardedBy("this") 4530 private boolean handleProcessStartedLocked(ProcessRecord app, int pid, boolean usingWrapper, 4531 long expectedStartSeq, boolean procAttached) { 4532 mPendingStarts.remove(expectedStartSeq); 4533 final String reason = isProcStartValidLocked(app, expectedStartSeq); 4534 if (reason != null) { 4535 Slog.w(TAG_PROCESSES, app + " start not valid, killing pid=" + pid 4536 + ", " + reason); 4537 app.pendingStart = false; 4538 Process.killProcessQuiet(pid); 4539 Process.killProcessGroup(app.uid, app.pid); 4540 return false; 4541 } 4542 mBatteryStatsService.noteProcessStart(app.processName, app.info.uid); 4543 checkTime(app.startTime, "startProcess: done updating battery stats"); 4544 4545 EventLog.writeEvent(EventLogTags.AM_PROC_START, 4546 UserHandle.getUserId(app.startUid), pid, app.startUid, 4547 app.processName, app.hostingType, 4548 app.hostingNameStr != null ? app.hostingNameStr : ""); 4549 4550 try { 4551 AppGlobals.getPackageManager().logAppProcessStartIfNeeded(app.processName, app.uid, 4552 app.seInfo, app.info.sourceDir, pid); 4553 } catch (RemoteException ex) { 4554 // Ignore 4555 } 4556 4557 if (app.persistent) { 4558 Watchdog.getInstance().processStarted(app.processName, pid); 4559 } 4560 4561 checkTime(app.startTime, "startProcess: building log message"); 4562 StringBuilder buf = mStringBuilder; 4563 buf.setLength(0); 4564 buf.append("Start proc "); 4565 buf.append(pid); 4566 buf.append(':'); 4567 buf.append(app.processName); 4568 buf.append('/'); 4569 UserHandle.formatUid(buf, app.startUid); 4570 if (app.isolatedEntryPoint != null) { 4571 buf.append(" ["); 4572 buf.append(app.isolatedEntryPoint); 4573 buf.append("]"); 4574 } 4575 buf.append(" for "); 4576 buf.append(app.hostingType); 4577 if (app.hostingNameStr != null) { 4578 buf.append(" "); 4579 buf.append(app.hostingNameStr); 4580 } 4581 reportUidInfoMessageLocked(TAG, buf.toString(), app.startUid); 4582 app.setPid(pid); 4583 app.usingWrapper = usingWrapper; 4584 app.pendingStart = false; 4585 checkTime(app.startTime, "startProcess: starting to update pids map"); 4586 ProcessRecord oldApp; 4587 synchronized (mPidsSelfLocked) { 4588 oldApp = mPidsSelfLocked.get(pid); 4589 } 4590 // If there is already an app occupying that pid that hasn't been cleaned up 4591 if (oldApp != null && !app.isolated) { 4592 // Clean up anything relating to this pid first 4593 Slog.w(TAG, "Reusing pid " + pid 4594 + " while app is still mapped to it"); 4595 cleanUpApplicationRecordLocked(oldApp, false, false, -1, 4596 true /*replacingPid*/); 4597 } 4598 synchronized (mPidsSelfLocked) { 4599 this.mPidsSelfLocked.put(pid, app); 4600 if (!procAttached) { 4601 Message msg = mHandler.obtainMessage(PROC_START_TIMEOUT_MSG); 4602 msg.obj = app; 4603 mHandler.sendMessageDelayed(msg, usingWrapper 4604 ? PROC_START_TIMEOUT_WITH_WRAPPER : PROC_START_TIMEOUT); 4605 } 4606 } 4607 checkTime(app.startTime, "startProcess: done updating pids map"); 4608 return true; 4609 } 4610 4611 void updateUsageStats(ActivityRecord component, boolean resumed) { 4612 if (DEBUG_SWITCH) Slog.d(TAG_SWITCH, 4613 "updateUsageStats: comp=" + component + "res=" + resumed); 4614 final BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 4615 StatsLog.write(StatsLog.ACTIVITY_FOREGROUND_STATE_CHANGED, 4616 component.app.uid, component.realActivity.getPackageName(), 4617 component.realActivity.getShortClassName(), resumed ? 4618 StatsLog.ACTIVITY_FOREGROUND_STATE_CHANGED__STATE__FOREGROUND : 4619 StatsLog.ACTIVITY_FOREGROUND_STATE_CHANGED__STATE__BACKGROUND); 4620 if (resumed) { 4621 if (mUsageStatsService != null) { 4622 mUsageStatsService.reportEvent(component.realActivity, component.userId, 4623 UsageEvents.Event.MOVE_TO_FOREGROUND); 4624 4625 } 4626 synchronized (stats) { 4627 stats.noteActivityResumedLocked(component.app.uid); 4628 } 4629 } else { 4630 if (mUsageStatsService != null) { 4631 mUsageStatsService.reportEvent(component.realActivity, component.userId, 4632 UsageEvents.Event.MOVE_TO_BACKGROUND); 4633 } 4634 synchronized (stats) { 4635 stats.noteActivityPausedLocked(component.app.uid); 4636 } 4637 } 4638 } 4639 4640 Intent getHomeIntent() { 4641 Intent intent = new Intent(mTopAction, mTopData != null ? Uri.parse(mTopData) : null); 4642 intent.setComponent(mTopComponent); 4643 intent.addFlags(Intent.FLAG_DEBUG_TRIAGED_MISSING); 4644 if (mFactoryTest != FactoryTest.FACTORY_TEST_LOW_LEVEL) { 4645 intent.addCategory(Intent.CATEGORY_HOME); 4646 } 4647 return intent; 4648 } 4649 4650 boolean startHomeActivityLocked(int userId, String reason) { 4651 if (mFactoryTest == FactoryTest.FACTORY_TEST_LOW_LEVEL 4652 && mTopAction == null) { 4653 // We are running in factory test mode, but unable to find 4654 // the factory test app, so just sit around displaying the 4655 // error message and don't try to start anything. 4656 return false; 4657 } 4658 Intent intent = getHomeIntent(); 4659 ActivityInfo aInfo = resolveActivityInfo(intent, STOCK_PM_FLAGS, userId); 4660 if (aInfo != null) { 4661 intent.setComponent(new ComponentName(aInfo.applicationInfo.packageName, aInfo.name)); 4662 // Don't do this if the home app is currently being 4663 // instrumented. 4664 aInfo = new ActivityInfo(aInfo); 4665 aInfo.applicationInfo = getAppInfoForUser(aInfo.applicationInfo, userId); 4666 ProcessRecord app = getProcessRecordLocked(aInfo.processName, 4667 aInfo.applicationInfo.uid, true); 4668 if (app == null || app.instr == null) { 4669 intent.setFlags(intent.getFlags() | FLAG_ACTIVITY_NEW_TASK); 4670 final int resolvedUserId = UserHandle.getUserId(aInfo.applicationInfo.uid); 4671 // For ANR debugging to verify if the user activity is the one that actually 4672 // launched. 4673 final String myReason = reason + ":" + userId + ":" + resolvedUserId; 4674 mActivityStartController.startHomeActivity(intent, aInfo, myReason); 4675 } 4676 } else { 4677 Slog.wtf(TAG, "No home screen found for " + intent, new Throwable()); 4678 } 4679 4680 return true; 4681 } 4682 4683 private ActivityInfo resolveActivityInfo(Intent intent, int flags, int userId) { 4684 ActivityInfo ai = null; 4685 ComponentName comp = intent.getComponent(); 4686 try { 4687 if (comp != null) { 4688 // Factory test. 4689 ai = AppGlobals.getPackageManager().getActivityInfo(comp, flags, userId); 4690 } else { 4691 ResolveInfo info = AppGlobals.getPackageManager().resolveIntent( 4692 intent, 4693 intent.resolveTypeIfNeeded(mContext.getContentResolver()), 4694 flags, userId); 4695 4696 if (info != null) { 4697 ai = info.activityInfo; 4698 } 4699 } 4700 } catch (RemoteException e) { 4701 // ignore 4702 } 4703 4704 return ai; 4705 } 4706 4707 boolean getCheckedForSetup() { 4708 return mCheckedForSetup; 4709 } 4710 4711 void setCheckedForSetup(boolean checked) { 4712 mCheckedForSetup = checked; 4713 } 4714 4715 CompatibilityInfo compatibilityInfoForPackageLocked(ApplicationInfo ai) { 4716 return mCompatModePackages.compatibilityInfoForPackageLocked(ai); 4717 } 4718 4719 void enforceNotIsolatedCaller(String caller) { 4720 if (UserHandle.isIsolated(Binder.getCallingUid())) { 4721 throw new SecurityException("Isolated process not allowed to call " + caller); 4722 } 4723 } 4724 4725 @Override 4726 public int getFrontActivityScreenCompatMode() { 4727 enforceNotIsolatedCaller("getFrontActivityScreenCompatMode"); 4728 synchronized (this) { 4729 return mCompatModePackages.getFrontActivityScreenCompatModeLocked(); 4730 } 4731 } 4732 4733 @Override 4734 public void setFrontActivityScreenCompatMode(int mode) { 4735 enforceCallingPermission(android.Manifest.permission.SET_SCREEN_COMPATIBILITY, 4736 "setFrontActivityScreenCompatMode"); 4737 synchronized (this) { 4738 mCompatModePackages.setFrontActivityScreenCompatModeLocked(mode); 4739 } 4740 } 4741 4742 @Override 4743 public int getPackageScreenCompatMode(String packageName) { 4744 enforceNotIsolatedCaller("getPackageScreenCompatMode"); 4745 synchronized (this) { 4746 return mCompatModePackages.getPackageScreenCompatModeLocked(packageName); 4747 } 4748 } 4749 4750 @Override 4751 public void setPackageScreenCompatMode(String packageName, int mode) { 4752 enforceCallingPermission(android.Manifest.permission.SET_SCREEN_COMPATIBILITY, 4753 "setPackageScreenCompatMode"); 4754 synchronized (this) { 4755 mCompatModePackages.setPackageScreenCompatModeLocked(packageName, mode); 4756 } 4757 } 4758 4759 @Override 4760 public boolean getPackageAskScreenCompat(String packageName) { 4761 enforceNotIsolatedCaller("getPackageAskScreenCompat"); 4762 synchronized (this) { 4763 return mCompatModePackages.getPackageAskCompatModeLocked(packageName); 4764 } 4765 } 4766 4767 @Override 4768 public void setPackageAskScreenCompat(String packageName, boolean ask) { 4769 enforceCallingPermission(android.Manifest.permission.SET_SCREEN_COMPATIBILITY, 4770 "setPackageAskScreenCompat"); 4771 synchronized (this) { 4772 mCompatModePackages.setPackageAskCompatModeLocked(packageName, ask); 4773 } 4774 } 4775 4776 private boolean hasUsageStatsPermission(String callingPackage) { 4777 final int mode = mAppOpsService.noteOperation(AppOpsManager.OP_GET_USAGE_STATS, 4778 Binder.getCallingUid(), callingPackage); 4779 if (mode == AppOpsManager.MODE_DEFAULT) { 4780 return checkCallingPermission(Manifest.permission.PACKAGE_USAGE_STATS) 4781 == PackageManager.PERMISSION_GRANTED; 4782 } 4783 return mode == AppOpsManager.MODE_ALLOWED; 4784 } 4785 4786 @Override 4787 public int getPackageProcessState(String packageName, String callingPackage) { 4788 if (!hasUsageStatsPermission(callingPackage)) { 4789 enforceCallingPermission(android.Manifest.permission.PACKAGE_USAGE_STATS, 4790 "getPackageProcessState"); 4791 } 4792 4793 int procState = ActivityManager.PROCESS_STATE_NONEXISTENT; 4794 synchronized (this) { 4795 for (int i=mLruProcesses.size()-1; i>=0; i--) { 4796 final ProcessRecord proc = mLruProcesses.get(i); 4797 if (procState > proc.setProcState) { 4798 if (proc.pkgList.containsKey(packageName) || 4799 (proc.pkgDeps != null && proc.pkgDeps.contains(packageName))) { 4800 procState = proc.setProcState; 4801 } 4802 } 4803 } 4804 } 4805 return procState; 4806 } 4807 4808 @Override 4809 public boolean setProcessMemoryTrimLevel(String process, int userId, int level) 4810 throws RemoteException { 4811 synchronized (this) { 4812 final ProcessRecord app = findProcessLocked(process, userId, "setProcessMemoryTrimLevel"); 4813 if (app == null) { 4814 throw new IllegalArgumentException("Unknown process: " + process); 4815 } 4816 if (app.thread == null) { 4817 throw new IllegalArgumentException("Process has no app thread"); 4818 } 4819 if (app.trimMemoryLevel >= level) { 4820 throw new IllegalArgumentException( 4821 "Unable to set a higher trim level than current level"); 4822 } 4823 if (!(level < ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN || 4824 app.curProcState > ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND)) { 4825 throw new IllegalArgumentException("Unable to set a background trim level " 4826 + "on a foreground process"); 4827 } 4828 app.thread.scheduleTrimMemory(level); 4829 app.trimMemoryLevel = level; 4830 return true; 4831 } 4832 } 4833 4834 private void dispatchProcessesChanged() { 4835 int N; 4836 synchronized (this) { 4837 N = mPendingProcessChanges.size(); 4838 if (mActiveProcessChanges.length < N) { 4839 mActiveProcessChanges = new ProcessChangeItem[N]; 4840 } 4841 mPendingProcessChanges.toArray(mActiveProcessChanges); 4842 mPendingProcessChanges.clear(); 4843 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG_PROCESS_OBSERVERS, 4844 "*** Delivering " + N + " process changes"); 4845 } 4846 4847 int i = mProcessObservers.beginBroadcast(); 4848 while (i > 0) { 4849 i--; 4850 final IProcessObserver observer = mProcessObservers.getBroadcastItem(i); 4851 if (observer != null) { 4852 try { 4853 for (int j=0; j<N; j++) { 4854 ProcessChangeItem item = mActiveProcessChanges[j]; 4855 if ((item.changes&ProcessChangeItem.CHANGE_ACTIVITIES) != 0) { 4856 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG_PROCESS_OBSERVERS, 4857 "ACTIVITIES CHANGED pid=" + item.pid + " uid=" 4858 + item.uid + ": " + item.foregroundActivities); 4859 observer.onForegroundActivitiesChanged(item.pid, item.uid, 4860 item.foregroundActivities); 4861 } 4862 } 4863 } catch (RemoteException e) { 4864 } 4865 } 4866 } 4867 mProcessObservers.finishBroadcast(); 4868 4869 synchronized (this) { 4870 for (int j=0; j<N; j++) { 4871 mAvailProcessChanges.add(mActiveProcessChanges[j]); 4872 } 4873 } 4874 } 4875 4876 private void dispatchProcessDied(int pid, int uid) { 4877 int i = mProcessObservers.beginBroadcast(); 4878 while (i > 0) { 4879 i--; 4880 final IProcessObserver observer = mProcessObservers.getBroadcastItem(i); 4881 if (observer != null) { 4882 try { 4883 observer.onProcessDied(pid, uid); 4884 } catch (RemoteException e) { 4885 } 4886 } 4887 } 4888 mProcessObservers.finishBroadcast(); 4889 } 4890 4891 @VisibleForTesting 4892 void dispatchUidsChanged() { 4893 int N; 4894 synchronized (this) { 4895 N = mPendingUidChanges.size(); 4896 if (mActiveUidChanges.length < N) { 4897 mActiveUidChanges = new UidRecord.ChangeItem[N]; 4898 } 4899 for (int i=0; i<N; i++) { 4900 final UidRecord.ChangeItem change = mPendingUidChanges.get(i); 4901 mActiveUidChanges[i] = change; 4902 if (change.uidRecord != null) { 4903 change.uidRecord.pendingChange = null; 4904 change.uidRecord = null; 4905 } 4906 } 4907 mPendingUidChanges.clear(); 4908 if (DEBUG_UID_OBSERVERS) Slog.i(TAG_UID_OBSERVERS, 4909 "*** Delivering " + N + " uid changes"); 4910 } 4911 4912 mUidChangeDispatchCount += N; 4913 int i = mUidObservers.beginBroadcast(); 4914 while (i > 0) { 4915 i--; 4916 dispatchUidsChangedForObserver(mUidObservers.getBroadcastItem(i), 4917 (UidObserverRegistration) mUidObservers.getBroadcastCookie(i), N); 4918 } 4919 mUidObservers.finishBroadcast(); 4920 4921 if (VALIDATE_UID_STATES && mUidObservers.getRegisteredCallbackCount() > 0) { 4922 for (int j = 0; j < N; ++j) { 4923 final UidRecord.ChangeItem item = mActiveUidChanges[j]; 4924 if ((item.change & UidRecord.CHANGE_GONE) != 0) { 4925 mValidateUids.remove(item.uid); 4926 } else { 4927 UidRecord validateUid = mValidateUids.get(item.uid); 4928 if (validateUid == null) { 4929 validateUid = new UidRecord(item.uid); 4930 mValidateUids.put(item.uid, validateUid); 4931 } 4932 if ((item.change & UidRecord.CHANGE_IDLE) != 0) { 4933 validateUid.idle = true; 4934 } else if ((item.change & UidRecord.CHANGE_ACTIVE) != 0) { 4935 validateUid.idle = false; 4936 } 4937 validateUid.curProcState = validateUid.setProcState = item.processState; 4938 validateUid.lastDispatchedProcStateSeq = item.procStateSeq; 4939 } 4940 } 4941 } 4942 4943 synchronized (this) { 4944 for (int j = 0; j < N; j++) { 4945 mAvailUidChanges.add(mActiveUidChanges[j]); 4946 } 4947 } 4948 } 4949 4950 private void dispatchUidsChangedForObserver(IUidObserver observer, 4951 UidObserverRegistration reg, int changesSize) { 4952 if (observer == null) { 4953 return; 4954 } 4955 try { 4956 for (int j = 0; j < changesSize; j++) { 4957 UidRecord.ChangeItem item = mActiveUidChanges[j]; 4958 final int change = item.change; 4959 if (change == UidRecord.CHANGE_PROCSTATE && 4960 (reg.which & ActivityManager.UID_OBSERVER_PROCSTATE) == 0) { 4961 // No-op common case: no significant change, the observer is not 4962 // interested in all proc state changes. 4963 continue; 4964 } 4965 final long start = SystemClock.uptimeMillis(); 4966 if ((change & UidRecord.CHANGE_IDLE) != 0) { 4967 if ((reg.which & ActivityManager.UID_OBSERVER_IDLE) != 0) { 4968 if (DEBUG_UID_OBSERVERS) Slog.i(TAG_UID_OBSERVERS, 4969 "UID idle uid=" + item.uid); 4970 observer.onUidIdle(item.uid, item.ephemeral); 4971 } 4972 } else if ((change & UidRecord.CHANGE_ACTIVE) != 0) { 4973 if ((reg.which & ActivityManager.UID_OBSERVER_ACTIVE) != 0) { 4974 if (DEBUG_UID_OBSERVERS) Slog.i(TAG_UID_OBSERVERS, 4975 "UID active uid=" + item.uid); 4976 observer.onUidActive(item.uid); 4977 } 4978 } 4979 if ((reg.which & ActivityManager.UID_OBSERVER_CACHED) != 0) { 4980 if ((change & UidRecord.CHANGE_CACHED) != 0) { 4981 if (DEBUG_UID_OBSERVERS) Slog.i(TAG_UID_OBSERVERS, 4982 "UID cached uid=" + item.uid); 4983 observer.onUidCachedChanged(item.uid, true); 4984 } else if ((change & UidRecord.CHANGE_UNCACHED) != 0) { 4985 if (DEBUG_UID_OBSERVERS) Slog.i(TAG_UID_OBSERVERS, 4986 "UID active uid=" + item.uid); 4987 observer.onUidCachedChanged(item.uid, false); 4988 } 4989 } 4990 if ((change & UidRecord.CHANGE_GONE) != 0) { 4991 if ((reg.which & ActivityManager.UID_OBSERVER_GONE) != 0) { 4992 if (DEBUG_UID_OBSERVERS) Slog.i(TAG_UID_OBSERVERS, 4993 "UID gone uid=" + item.uid); 4994 observer.onUidGone(item.uid, item.ephemeral); 4995 } 4996 if (reg.lastProcStates != null) { 4997 reg.lastProcStates.delete(item.uid); 4998 } 4999 } else { 5000 if ((reg.which & ActivityManager.UID_OBSERVER_PROCSTATE) != 0) { 5001 if (DEBUG_UID_OBSERVERS) Slog.i(TAG_UID_OBSERVERS, 5002 "UID CHANGED uid=" + item.uid 5003 + ": " + item.processState); 5004 boolean doReport = true; 5005 if (reg.cutpoint >= ActivityManager.MIN_PROCESS_STATE) { 5006 final int lastState = reg.lastProcStates.get(item.uid, 5007 ActivityManager.PROCESS_STATE_UNKNOWN); 5008 if (lastState != ActivityManager.PROCESS_STATE_UNKNOWN) { 5009 final boolean lastAboveCut = lastState <= reg.cutpoint; 5010 final boolean newAboveCut = item.processState <= reg.cutpoint; 5011 doReport = lastAboveCut != newAboveCut; 5012 } else { 5013 doReport = item.processState 5014 != ActivityManager.PROCESS_STATE_NONEXISTENT; 5015 } 5016 } 5017 if (doReport) { 5018 if (reg.lastProcStates != null) { 5019 reg.lastProcStates.put(item.uid, item.processState); 5020 } 5021 observer.onUidStateChanged(item.uid, item.processState, 5022 item.procStateSeq); 5023 } 5024 } 5025 } 5026 final int duration = (int) (SystemClock.uptimeMillis() - start); 5027 if (reg.mMaxDispatchTime < duration) { 5028 reg.mMaxDispatchTime = duration; 5029 } 5030 if (duration >= SLOW_UID_OBSERVER_THRESHOLD_MS) { 5031 reg.mSlowDispatchCount++; 5032 } 5033 } 5034 } catch (RemoteException e) { 5035 } 5036 } 5037 5038 void dispatchOomAdjObserver(String msg) { 5039 OomAdjObserver observer; 5040 synchronized (this) { 5041 observer = mCurOomAdjObserver; 5042 } 5043 5044 if (observer != null) { 5045 observer.onOomAdjMessage(msg); 5046 } 5047 } 5048 5049 void setOomAdjObserver(int uid, OomAdjObserver observer) { 5050 synchronized (this) { 5051 mCurOomAdjUid = uid; 5052 mCurOomAdjObserver = observer; 5053 } 5054 } 5055 5056 void clearOomAdjObserver() { 5057 synchronized (this) { 5058 mCurOomAdjUid = -1; 5059 mCurOomAdjObserver = null; 5060 } 5061 } 5062 5063 void reportOomAdjMessageLocked(String tag, String msg) { 5064 Slog.d(tag, msg); 5065 if (mCurOomAdjObserver != null) { 5066 mUiHandler.obtainMessage(DISPATCH_OOM_ADJ_OBSERVER_MSG, msg).sendToTarget(); 5067 } 5068 } 5069 5070 void reportUidInfoMessageLocked(String tag, String msg, int uid) { 5071 Slog.i(TAG, msg); 5072 if (mCurOomAdjObserver != null && uid == mCurOomAdjUid) { 5073 mUiHandler.obtainMessage(DISPATCH_OOM_ADJ_OBSERVER_MSG, msg).sendToTarget(); 5074 } 5075 5076 } 5077 5078 @Override 5079 public final int startActivity(IApplicationThread caller, String callingPackage, 5080 Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode, 5081 int startFlags, ProfilerInfo profilerInfo, Bundle bOptions) { 5082 return startActivityAsUser(caller, callingPackage, intent, resolvedType, resultTo, 5083 resultWho, requestCode, startFlags, profilerInfo, bOptions, 5084 UserHandle.getCallingUserId()); 5085 } 5086 5087 @Override 5088 public final int startActivityAsUser(IApplicationThread caller, String callingPackage, 5089 Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode, 5090 int startFlags, ProfilerInfo profilerInfo, Bundle bOptions, int userId) { 5091 return startActivityAsUser(caller, callingPackage, intent, resolvedType, resultTo, 5092 resultWho, requestCode, startFlags, profilerInfo, bOptions, userId, 5093 true /*validateIncomingUser*/); 5094 } 5095 5096 public final int startActivityAsUser(IApplicationThread caller, String callingPackage, 5097 Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode, 5098 int startFlags, ProfilerInfo profilerInfo, Bundle bOptions, int userId, 5099 boolean validateIncomingUser) { 5100 enforceNotIsolatedCaller("startActivity"); 5101 5102 userId = mActivityStartController.checkTargetUser(userId, validateIncomingUser, 5103 Binder.getCallingPid(), Binder.getCallingUid(), "startActivityAsUser"); 5104 5105 // TODO: Switch to user app stacks here. 5106 return mActivityStartController.obtainStarter(intent, "startActivityAsUser") 5107 .setCaller(caller) 5108 .setCallingPackage(callingPackage) 5109 .setResolvedType(resolvedType) 5110 .setResultTo(resultTo) 5111 .setResultWho(resultWho) 5112 .setRequestCode(requestCode) 5113 .setStartFlags(startFlags) 5114 .setProfilerInfo(profilerInfo) 5115 .setActivityOptions(bOptions) 5116 .setMayWait(userId) 5117 .execute(); 5118 5119 } 5120 5121 @Override 5122 public final int startActivityAsCaller(IApplicationThread caller, String callingPackage, 5123 Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode, 5124 int startFlags, ProfilerInfo profilerInfo, Bundle bOptions, boolean ignoreTargetSecurity, 5125 int userId) { 5126 5127 // This is very dangerous -- it allows you to perform a start activity (including 5128 // permission grants) as any app that may launch one of your own activities. So 5129 // we will only allow this to be done from activities that are part of the core framework, 5130 // and then only when they are running as the system. 5131 final ActivityRecord sourceRecord; 5132 final int targetUid; 5133 final String targetPackage; 5134 final boolean isResolver; 5135 synchronized (this) { 5136 if (resultTo == null) { 5137 throw new SecurityException("Must be called from an activity"); 5138 } 5139 sourceRecord = mStackSupervisor.isInAnyStackLocked(resultTo); 5140 if (sourceRecord == null) { 5141 throw new SecurityException("Called with bad activity token: " + resultTo); 5142 } 5143 if (!sourceRecord.info.packageName.equals("android")) { 5144 throw new SecurityException( 5145 "Must be called from an activity that is declared in the android package"); 5146 } 5147 if (sourceRecord.app == null) { 5148 throw new SecurityException("Called without a process attached to activity"); 5149 } 5150 if (UserHandle.getAppId(sourceRecord.app.uid) != SYSTEM_UID) { 5151 // This is still okay, as long as this activity is running under the 5152 // uid of the original calling activity. 5153 if (sourceRecord.app.uid != sourceRecord.launchedFromUid) { 5154 throw new SecurityException( 5155 "Calling activity in uid " + sourceRecord.app.uid 5156 + " must be system uid or original calling uid " 5157 + sourceRecord.launchedFromUid); 5158 } 5159 } 5160 if (ignoreTargetSecurity) { 5161 if (intent.getComponent() == null) { 5162 throw new SecurityException( 5163 "Component must be specified with ignoreTargetSecurity"); 5164 } 5165 if (intent.getSelector() != null) { 5166 throw new SecurityException( 5167 "Selector not allowed with ignoreTargetSecurity"); 5168 } 5169 } 5170 targetUid = sourceRecord.launchedFromUid; 5171 targetPackage = sourceRecord.launchedFromPackage; 5172 isResolver = sourceRecord.isResolverOrChildActivity(); 5173 } 5174 5175 if (userId == UserHandle.USER_NULL) { 5176 userId = UserHandle.getUserId(sourceRecord.app.uid); 5177 } 5178 5179 // TODO: Switch to user app stacks here. 5180 try { 5181 return mActivityStartController.obtainStarter(intent, "startActivityAsCaller") 5182 .setCallingUid(targetUid) 5183 .setCallingPackage(targetPackage) 5184 .setResolvedType(resolvedType) 5185 .setResultTo(resultTo) 5186 .setResultWho(resultWho) 5187 .setRequestCode(requestCode) 5188 .setStartFlags(startFlags) 5189 .setActivityOptions(bOptions) 5190 .setMayWait(userId) 5191 .setIgnoreTargetSecurity(ignoreTargetSecurity) 5192 .setFilterCallingUid(isResolver ? 0 /* system */ : targetUid) 5193 .execute(); 5194 } catch (SecurityException e) { 5195 // XXX need to figure out how to propagate to original app. 5196 // A SecurityException here is generally actually a fault of the original 5197 // calling activity (such as a fairly granting permissions), so propagate it 5198 // back to them. 5199 /* 5200 StringBuilder msg = new StringBuilder(); 5201 msg.append("While launching"); 5202 msg.append(intent.toString()); 5203 msg.append(": "); 5204 msg.append(e.getMessage()); 5205 */ 5206 throw e; 5207 } 5208 } 5209 5210 @Override 5211 public final WaitResult startActivityAndWait(IApplicationThread caller, String callingPackage, 5212 Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode, 5213 int startFlags, ProfilerInfo profilerInfo, Bundle bOptions, int userId) { 5214 enforceNotIsolatedCaller("startActivityAndWait"); 5215 userId = mUserController.handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 5216 userId, false, ALLOW_FULL_ONLY, "startActivityAndWait", null); 5217 WaitResult res = new WaitResult(); 5218 // TODO: Switch to user app stacks here. 5219 mActivityStartController.obtainStarter(intent, "startActivityAndWait") 5220 .setCaller(caller) 5221 .setCallingPackage(callingPackage) 5222 .setResolvedType(resolvedType) 5223 .setResultTo(resultTo) 5224 .setResultWho(resultWho) 5225 .setRequestCode(requestCode) 5226 .setStartFlags(startFlags) 5227 .setActivityOptions(bOptions) 5228 .setMayWait(userId) 5229 .setProfilerInfo(profilerInfo) 5230 .setWaitResult(res) 5231 .execute(); 5232 return res; 5233 } 5234 5235 @Override 5236 public final int startActivityWithConfig(IApplicationThread caller, String callingPackage, 5237 Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode, 5238 int startFlags, Configuration config, Bundle bOptions, int userId) { 5239 enforceNotIsolatedCaller("startActivityWithConfig"); 5240 userId = mUserController.handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 5241 userId, false, ALLOW_FULL_ONLY, "startActivityWithConfig", null); 5242 // TODO: Switch to user app stacks here. 5243 return mActivityStartController.obtainStarter(intent, "startActivityWithConfig") 5244 .setCaller(caller) 5245 .setCallingPackage(callingPackage) 5246 .setResolvedType(resolvedType) 5247 .setResultTo(resultTo) 5248 .setResultWho(resultWho) 5249 .setRequestCode(requestCode) 5250 .setStartFlags(startFlags) 5251 .setGlobalConfiguration(config) 5252 .setActivityOptions(bOptions) 5253 .setMayWait(userId) 5254 .execute(); 5255 } 5256 5257 @Override 5258 public int startActivityIntentSender(IApplicationThread caller, IIntentSender target, 5259 IBinder whitelistToken, Intent fillInIntent, String resolvedType, IBinder resultTo, 5260 String resultWho, int requestCode, int flagsMask, int flagsValues, Bundle bOptions) 5261 throws TransactionTooLargeException { 5262 enforceNotIsolatedCaller("startActivityIntentSender"); 5263 // Refuse possible leaked file descriptors 5264 if (fillInIntent != null && fillInIntent.hasFileDescriptors()) { 5265 throw new IllegalArgumentException("File descriptors passed in Intent"); 5266 } 5267 5268 if (!(target instanceof PendingIntentRecord)) { 5269 throw new IllegalArgumentException("Bad PendingIntent object"); 5270 } 5271 5272 PendingIntentRecord pir = (PendingIntentRecord)target; 5273 5274 synchronized (this) { 5275 // If this is coming from the currently resumed activity, it is 5276 // effectively saying that app switches are allowed at this point. 5277 final ActivityStack stack = getFocusedStack(); 5278 if (stack.mResumedActivity != null && 5279 stack.mResumedActivity.info.applicationInfo.uid == Binder.getCallingUid()) { 5280 mAppSwitchesAllowedTime = 0; 5281 } 5282 } 5283 int ret = pir.sendInner(0, fillInIntent, resolvedType, whitelistToken, null, null, 5284 resultTo, resultWho, requestCode, flagsMask, flagsValues, bOptions); 5285 return ret; 5286 } 5287 5288 @Override 5289 public int startVoiceActivity(String callingPackage, int callingPid, int callingUid, 5290 Intent intent, String resolvedType, IVoiceInteractionSession session, 5291 IVoiceInteractor interactor, int startFlags, ProfilerInfo profilerInfo, 5292 Bundle bOptions, int userId) { 5293 enforceCallingPermission(BIND_VOICE_INTERACTION, "startVoiceActivity()"); 5294 if (session == null || interactor == null) { 5295 throw new NullPointerException("null session or interactor"); 5296 } 5297 userId = mUserController.handleIncomingUser(callingPid, callingUid, userId, false, 5298 ALLOW_FULL_ONLY, "startVoiceActivity", null); 5299 // TODO: Switch to user app stacks here. 5300 return mActivityStartController.obtainStarter(intent, "startVoiceActivity") 5301 .setCallingUid(callingUid) 5302 .setCallingPackage(callingPackage) 5303 .setResolvedType(resolvedType) 5304 .setVoiceSession(session) 5305 .setVoiceInteractor(interactor) 5306 .setStartFlags(startFlags) 5307 .setProfilerInfo(profilerInfo) 5308 .setActivityOptions(bOptions) 5309 .setMayWait(userId) 5310 .execute(); 5311 } 5312 5313 @Override 5314 public int startAssistantActivity(String callingPackage, int callingPid, int callingUid, 5315 Intent intent, String resolvedType, Bundle bOptions, int userId) { 5316 enforceCallingPermission(BIND_VOICE_INTERACTION, "startAssistantActivity()"); 5317 userId = mUserController.handleIncomingUser(callingPid, callingUid, userId, false, 5318 ALLOW_FULL_ONLY, "startAssistantActivity", null); 5319 5320 return mActivityStartController.obtainStarter(intent, "startAssistantActivity") 5321 .setCallingUid(callingUid) 5322 .setCallingPackage(callingPackage) 5323 .setResolvedType(resolvedType) 5324 .setActivityOptions(bOptions) 5325 .setMayWait(userId) 5326 .execute(); 5327 } 5328 5329 @Override 5330 public void startRecentsActivity(Intent intent, IAssistDataReceiver assistDataReceiver, 5331 IRecentsAnimationRunner recentsAnimationRunner) { 5332 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS, "startRecentsActivity()"); 5333 final int callingPid = Binder.getCallingPid(); 5334 final long origId = Binder.clearCallingIdentity(); 5335 try { 5336 synchronized (this) { 5337 final ComponentName recentsComponent = mRecentTasks.getRecentsComponent(); 5338 final int recentsUid = mRecentTasks.getRecentsComponentUid(); 5339 5340 // Start a new recents animation 5341 final RecentsAnimation anim = new RecentsAnimation(this, mStackSupervisor, 5342 mActivityStartController, mWindowManager, mUserController, callingPid); 5343 anim.startRecentsActivity(intent, recentsAnimationRunner, recentsComponent, 5344 recentsUid, assistDataReceiver); 5345 } 5346 } finally { 5347 Binder.restoreCallingIdentity(origId); 5348 } 5349 } 5350 5351 @Override 5352 public void cancelRecentsAnimation(boolean restoreHomeStackPosition) { 5353 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS, "cancelRecentsAnimation()"); 5354 final long callingUid = Binder.getCallingUid(); 5355 final long origId = Binder.clearCallingIdentity(); 5356 try { 5357 synchronized (this) { 5358 // Cancel the recents animation synchronously (do not hold the WM lock) 5359 mWindowManager.cancelRecentsAnimationSynchronously(restoreHomeStackPosition 5360 ? REORDER_MOVE_TO_ORIGINAL_POSITION 5361 : REORDER_KEEP_IN_PLACE, "cancelRecentsAnimation/uid=" + callingUid); 5362 } 5363 } finally { 5364 Binder.restoreCallingIdentity(origId); 5365 } 5366 } 5367 5368 @Override 5369 public void startLocalVoiceInteraction(IBinder callingActivity, Bundle options) 5370 throws RemoteException { 5371 Slog.i(TAG, "Activity tried to startVoiceInteraction"); 5372 synchronized (this) { 5373 ActivityRecord activity = getFocusedStack().getTopActivity(); 5374 if (ActivityRecord.forTokenLocked(callingActivity) != activity) { 5375 throw new SecurityException("Only focused activity can call startVoiceInteraction"); 5376 } 5377 if (mRunningVoice != null || activity.getTask().voiceSession != null 5378 || activity.voiceSession != null) { 5379 Slog.w(TAG, "Already in a voice interaction, cannot start new voice interaction"); 5380 return; 5381 } 5382 if (activity.pendingVoiceInteractionStart) { 5383 Slog.w(TAG, "Pending start of voice interaction already."); 5384 return; 5385 } 5386 activity.pendingVoiceInteractionStart = true; 5387 } 5388 LocalServices.getService(VoiceInteractionManagerInternal.class) 5389 .startLocalVoiceInteraction(callingActivity, options); 5390 } 5391 5392 @Override 5393 public void stopLocalVoiceInteraction(IBinder callingActivity) throws RemoteException { 5394 LocalServices.getService(VoiceInteractionManagerInternal.class) 5395 .stopLocalVoiceInteraction(callingActivity); 5396 } 5397 5398 @Override 5399 public boolean supportsLocalVoiceInteraction() throws RemoteException { 5400 return LocalServices.getService(VoiceInteractionManagerInternal.class) 5401 .supportsLocalVoiceInteraction(); 5402 } 5403 5404 @GuardedBy("this") 5405 void onLocalVoiceInteractionStartedLocked(IBinder activity, 5406 IVoiceInteractionSession voiceSession, IVoiceInteractor voiceInteractor) { 5407 ActivityRecord activityToCallback = ActivityRecord.forTokenLocked(activity); 5408 if (activityToCallback == null) return; 5409 activityToCallback.setVoiceSessionLocked(voiceSession); 5410 5411 // Inform the activity 5412 try { 5413 activityToCallback.app.thread.scheduleLocalVoiceInteractionStarted(activity, 5414 voiceInteractor); 5415 long token = Binder.clearCallingIdentity(); 5416 try { 5417 startRunningVoiceLocked(voiceSession, activityToCallback.appInfo.uid); 5418 } finally { 5419 Binder.restoreCallingIdentity(token); 5420 } 5421 // TODO: VI Should we cache the activity so that it's easier to find later 5422 // rather than scan through all the stacks and activities? 5423 } catch (RemoteException re) { 5424 activityToCallback.clearVoiceSessionLocked(); 5425 // TODO: VI Should this terminate the voice session? 5426 } 5427 } 5428 5429 @Override 5430 public void setVoiceKeepAwake(IVoiceInteractionSession session, boolean keepAwake) { 5431 synchronized (this) { 5432 if (mRunningVoice != null && mRunningVoice.asBinder() == session.asBinder()) { 5433 if (keepAwake) { 5434 mVoiceWakeLock.acquire(); 5435 } else { 5436 mVoiceWakeLock.release(); 5437 } 5438 } 5439 } 5440 } 5441 5442 @Override 5443 public boolean startNextMatchingActivity(IBinder callingActivity, 5444 Intent intent, Bundle bOptions) { 5445 // Refuse possible leaked file descriptors 5446 if (intent != null && intent.hasFileDescriptors() == true) { 5447 throw new IllegalArgumentException("File descriptors passed in Intent"); 5448 } 5449 SafeActivityOptions options = SafeActivityOptions.fromBundle(bOptions); 5450 5451 synchronized (this) { 5452 final ActivityRecord r = ActivityRecord.isInStackLocked(callingActivity); 5453 if (r == null) { 5454 SafeActivityOptions.abort(options); 5455 return false; 5456 } 5457 if (r.app == null || r.app.thread == null) { 5458 // The caller is not running... d'oh! 5459 SafeActivityOptions.abort(options); 5460 return false; 5461 } 5462 intent = new Intent(intent); 5463 // The caller is not allowed to change the data. 5464 intent.setDataAndType(r.intent.getData(), r.intent.getType()); 5465 // And we are resetting to find the next component... 5466 intent.setComponent(null); 5467 5468 final boolean debug = ((intent.getFlags() & Intent.FLAG_DEBUG_LOG_RESOLUTION) != 0); 5469 5470 ActivityInfo aInfo = null; 5471 try { 5472 List<ResolveInfo> resolves = 5473 AppGlobals.getPackageManager().queryIntentActivities( 5474 intent, r.resolvedType, 5475 PackageManager.MATCH_DEFAULT_ONLY | STOCK_PM_FLAGS, 5476 UserHandle.getCallingUserId()).getList(); 5477 5478 // Look for the original activity in the list... 5479 final int N = resolves != null ? resolves.size() : 0; 5480 for (int i=0; i<N; i++) { 5481 ResolveInfo rInfo = resolves.get(i); 5482 if (rInfo.activityInfo.packageName.equals(r.packageName) 5483 && rInfo.activityInfo.name.equals(r.info.name)) { 5484 // We found the current one... the next matching is 5485 // after it. 5486 i++; 5487 if (i<N) { 5488 aInfo = resolves.get(i).activityInfo; 5489 } 5490 if (debug) { 5491 Slog.v(TAG, "Next matching activity: found current " + r.packageName 5492 + "/" + r.info.name); 5493 Slog.v(TAG, "Next matching activity: next is " + ((aInfo == null) 5494 ? "null" : aInfo.packageName + "/" + aInfo.name)); 5495 } 5496 break; 5497 } 5498 } 5499 } catch (RemoteException e) { 5500 } 5501 5502 if (aInfo == null) { 5503 // Nobody who is next! 5504 SafeActivityOptions.abort(options); 5505 if (debug) Slog.d(TAG, "Next matching activity: nothing found"); 5506 return false; 5507 } 5508 5509 intent.setComponent(new ComponentName( 5510 aInfo.applicationInfo.packageName, aInfo.name)); 5511 intent.setFlags(intent.getFlags()&~( 5512 Intent.FLAG_ACTIVITY_FORWARD_RESULT| 5513 Intent.FLAG_ACTIVITY_CLEAR_TOP| 5514 Intent.FLAG_ACTIVITY_MULTIPLE_TASK| 5515 FLAG_ACTIVITY_NEW_TASK)); 5516 5517 // Okay now we need to start the new activity, replacing the 5518 // currently running activity. This is a little tricky because 5519 // we want to start the new one as if the current one is finished, 5520 // but not finish the current one first so that there is no flicker. 5521 // And thus... 5522 final boolean wasFinishing = r.finishing; 5523 r.finishing = true; 5524 5525 // Propagate reply information over to the new activity. 5526 final ActivityRecord resultTo = r.resultTo; 5527 final String resultWho = r.resultWho; 5528 final int requestCode = r.requestCode; 5529 r.resultTo = null; 5530 if (resultTo != null) { 5531 resultTo.removeResultsLocked(r, resultWho, requestCode); 5532 } 5533 5534 final long origId = Binder.clearCallingIdentity(); 5535 // TODO(b/64750076): Check if calling pid should really be -1. 5536 final int res = mActivityStartController 5537 .obtainStarter(intent, "startNextMatchingActivity") 5538 .setCaller(r.app.thread) 5539 .setResolvedType(r.resolvedType) 5540 .setActivityInfo(aInfo) 5541 .setResultTo(resultTo != null ? resultTo.appToken : null) 5542 .setResultWho(resultWho) 5543 .setRequestCode(requestCode) 5544 .setCallingPid(-1) 5545 .setCallingUid(r.launchedFromUid) 5546 .setCallingPackage(r.launchedFromPackage) 5547 .setRealCallingPid(-1) 5548 .setRealCallingUid(r.launchedFromUid) 5549 .setActivityOptions(options) 5550 .execute(); 5551 Binder.restoreCallingIdentity(origId); 5552 5553 r.finishing = wasFinishing; 5554 if (res != ActivityManager.START_SUCCESS) { 5555 return false; 5556 } 5557 return true; 5558 } 5559 } 5560 5561 @Override 5562 public final int startActivityFromRecents(int taskId, Bundle bOptions) { 5563 enforceCallerIsRecentsOrHasPermission(START_TASKS_FROM_RECENTS, 5564 "startActivityFromRecents()"); 5565 5566 final int callingPid = Binder.getCallingPid(); 5567 final int callingUid = Binder.getCallingUid(); 5568 final SafeActivityOptions safeOptions = SafeActivityOptions.fromBundle(bOptions); 5569 final long origId = Binder.clearCallingIdentity(); 5570 try { 5571 synchronized (this) { 5572 return mStackSupervisor.startActivityFromRecents(callingPid, callingUid, taskId, 5573 safeOptions); 5574 } 5575 } finally { 5576 Binder.restoreCallingIdentity(origId); 5577 } 5578 } 5579 5580 @Override 5581 public final int startActivities(IApplicationThread caller, String callingPackage, 5582 Intent[] intents, String[] resolvedTypes, IBinder resultTo, Bundle bOptions, 5583 int userId) { 5584 final String reason = "startActivities"; 5585 enforceNotIsolatedCaller(reason); 5586 userId = mUserController.handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 5587 userId, false, ALLOW_FULL_ONLY, reason, null); 5588 // TODO: Switch to user app stacks here. 5589 int ret = mActivityStartController.startActivities(caller, -1, callingPackage, 5590 intents, resolvedTypes, resultTo, SafeActivityOptions.fromBundle(bOptions), userId, 5591 reason); 5592 return ret; 5593 } 5594 5595 @Override 5596 public void reportActivityFullyDrawn(IBinder token, boolean restoredFromBundle) { 5597 synchronized (this) { 5598 ActivityRecord r = ActivityRecord.isInStackLocked(token); 5599 if (r == null) { 5600 return; 5601 } 5602 r.reportFullyDrawnLocked(restoredFromBundle); 5603 } 5604 } 5605 5606 @Override 5607 public void setRequestedOrientation(IBinder token, int requestedOrientation) { 5608 synchronized (this) { 5609 ActivityRecord r = ActivityRecord.isInStackLocked(token); 5610 if (r == null) { 5611 return; 5612 } 5613 final long origId = Binder.clearCallingIdentity(); 5614 try { 5615 r.setRequestedOrientation(requestedOrientation); 5616 } finally { 5617 Binder.restoreCallingIdentity(origId); 5618 } 5619 } 5620 } 5621 5622 @Override 5623 public int getRequestedOrientation(IBinder token) { 5624 synchronized (this) { 5625 ActivityRecord r = ActivityRecord.isInStackLocked(token); 5626 if (r == null) { 5627 return ActivityInfo.SCREEN_ORIENTATION_UNSPECIFIED; 5628 } 5629 return r.getRequestedOrientation(); 5630 } 5631 } 5632 5633 /** 5634 * This is the internal entry point for handling Activity.finish(). 5635 * 5636 * @param token The Binder token referencing the Activity we want to finish. 5637 * @param resultCode Result code, if any, from this Activity. 5638 * @param resultData Result data (Intent), if any, from this Activity. 5639 * @param finishTask Whether to finish the task associated with this Activity. 5640 * 5641 * @return Returns true if the activity successfully finished, or false if it is still running. 5642 */ 5643 @Override 5644 public final boolean finishActivity(IBinder token, int resultCode, Intent resultData, 5645 int finishTask) { 5646 // Refuse possible leaked file descriptors 5647 if (resultData != null && resultData.hasFileDescriptors() == true) { 5648 throw new IllegalArgumentException("File descriptors passed in Intent"); 5649 } 5650 5651 synchronized(this) { 5652 ActivityRecord r = ActivityRecord.isInStackLocked(token); 5653 if (r == null) { 5654 return true; 5655 } 5656 // Keep track of the root activity of the task before we finish it 5657 TaskRecord tr = r.getTask(); 5658 ActivityRecord rootR = tr.getRootActivity(); 5659 if (rootR == null) { 5660 Slog.w(TAG, "Finishing task with all activities already finished"); 5661 } 5662 // Do not allow task to finish if last task in lockTask mode. Launchable priv-apps can 5663 // finish. 5664 if (mLockTaskController.activityBlockedFromFinish(r)) { 5665 return false; 5666 } 5667 5668 if (mController != null) { 5669 // Find the first activity that is not finishing. 5670 ActivityRecord next = r.getStack().topRunningActivityLocked(token, 0); 5671 if (next != null) { 5672 // ask watcher if this is allowed 5673 boolean resumeOK = true; 5674 try { 5675 resumeOK = mController.activityResuming(next.packageName); 5676 } catch (RemoteException e) { 5677 mController = null; 5678 Watchdog.getInstance().setActivityController(null); 5679 } 5680 5681 if (!resumeOK) { 5682 Slog.i(TAG, "Not finishing activity because controller resumed"); 5683 return false; 5684 } 5685 } 5686 } 5687 final long origId = Binder.clearCallingIdentity(); 5688 try { 5689 boolean res; 5690 final boolean finishWithRootActivity = 5691 finishTask == Activity.FINISH_TASK_WITH_ROOT_ACTIVITY; 5692 if (finishTask == Activity.FINISH_TASK_WITH_ACTIVITY 5693 || (finishWithRootActivity && r == rootR)) { 5694 // If requested, remove the task that is associated to this activity only if it 5695 // was the root activity in the task. The result code and data is ignored 5696 // because we don't support returning them across task boundaries. Also, to 5697 // keep backwards compatibility we remove the task from recents when finishing 5698 // task with root activity. 5699 res = mStackSupervisor.removeTaskByIdLocked(tr.taskId, false, 5700 finishWithRootActivity, "finish-activity"); 5701 if (!res) { 5702 Slog.i(TAG, "Removing task failed to finish activity"); 5703 } 5704 } else { 5705 res = tr.getStack().requestFinishActivityLocked(token, resultCode, 5706 resultData, "app-request", true); 5707 if (!res) { 5708 Slog.i(TAG, "Failed to finish by app-request"); 5709 } 5710 } 5711 return res; 5712 } finally { 5713 Binder.restoreCallingIdentity(origId); 5714 } 5715 } 5716 } 5717 5718 @Override 5719 public final void finishHeavyWeightApp() { 5720 if (checkCallingPermission(android.Manifest.permission.FORCE_STOP_PACKAGES) 5721 != PackageManager.PERMISSION_GRANTED) { 5722 String msg = "Permission Denial: finishHeavyWeightApp() from pid=" 5723 + Binder.getCallingPid() 5724 + ", uid=" + Binder.getCallingUid() 5725 + " requires " + android.Manifest.permission.FORCE_STOP_PACKAGES; 5726 Slog.w(TAG, msg); 5727 throw new SecurityException(msg); 5728 } 5729 5730 synchronized(this) { 5731 final ProcessRecord proc = mHeavyWeightProcess; 5732 if (proc == null) { 5733 return; 5734 } 5735 5736 ArrayList<ActivityRecord> activities = new ArrayList<>(proc.activities); 5737 for (int i = 0; i < activities.size(); i++) { 5738 ActivityRecord r = activities.get(i); 5739 if (!r.finishing && r.isInStackLocked()) { 5740 r.getStack().finishActivityLocked(r, Activity.RESULT_CANCELED, 5741 null, "finish-heavy", true); 5742 } 5743 } 5744 5745 mHandler.sendMessage(mHandler.obtainMessage(CANCEL_HEAVY_NOTIFICATION_MSG, 5746 proc.userId, 0)); 5747 mHeavyWeightProcess = null; 5748 } 5749 } 5750 5751 @Override 5752 public void crashApplication(int uid, int initialPid, String packageName, int userId, 5753 String message) { 5754 if (checkCallingPermission(android.Manifest.permission.FORCE_STOP_PACKAGES) 5755 != PackageManager.PERMISSION_GRANTED) { 5756 String msg = "Permission Denial: crashApplication() from pid=" 5757 + Binder.getCallingPid() 5758 + ", uid=" + Binder.getCallingUid() 5759 + " requires " + android.Manifest.permission.FORCE_STOP_PACKAGES; 5760 Slog.w(TAG, msg); 5761 throw new SecurityException(msg); 5762 } 5763 5764 synchronized(this) { 5765 mAppErrors.scheduleAppCrashLocked(uid, initialPid, packageName, userId, message); 5766 } 5767 } 5768 5769 @Override 5770 public final void finishSubActivity(IBinder token, String resultWho, 5771 int requestCode) { 5772 synchronized(this) { 5773 final long origId = Binder.clearCallingIdentity(); 5774 ActivityRecord r = ActivityRecord.isInStackLocked(token); 5775 if (r != null) { 5776 r.getStack().finishSubActivityLocked(r, resultWho, requestCode); 5777 } 5778 Binder.restoreCallingIdentity(origId); 5779 } 5780 } 5781 5782 @Override 5783 public boolean finishActivityAffinity(IBinder token) { 5784 synchronized(this) { 5785 final long origId = Binder.clearCallingIdentity(); 5786 try { 5787 ActivityRecord r = ActivityRecord.isInStackLocked(token); 5788 if (r == null) { 5789 return false; 5790 } 5791 5792 // Do not allow task to finish if last task in lockTask mode. Launchable priv-apps 5793 // can finish. 5794 final TaskRecord task = r.getTask(); 5795 if (mLockTaskController.activityBlockedFromFinish(r)) { 5796 return false; 5797 } 5798 return task.getStack().finishActivityAffinityLocked(r); 5799 } finally { 5800 Binder.restoreCallingIdentity(origId); 5801 } 5802 } 5803 } 5804 5805 @Override 5806 public void finishVoiceTask(IVoiceInteractionSession session) { 5807 synchronized (this) { 5808 final long origId = Binder.clearCallingIdentity(); 5809 try { 5810 // TODO: VI Consider treating local voice interactions and voice tasks 5811 // differently here 5812 mStackSupervisor.finishVoiceTask(session); 5813 } finally { 5814 Binder.restoreCallingIdentity(origId); 5815 } 5816 } 5817 5818 } 5819 5820 @Override 5821 public boolean releaseActivityInstance(IBinder token) { 5822 synchronized(this) { 5823 final long origId = Binder.clearCallingIdentity(); 5824 try { 5825 ActivityRecord r = ActivityRecord.isInStackLocked(token); 5826 if (r == null) { 5827 return false; 5828 } 5829 return r.getStack().safelyDestroyActivityLocked(r, "app-req"); 5830 } finally { 5831 Binder.restoreCallingIdentity(origId); 5832 } 5833 } 5834 } 5835 5836 @Override 5837 public void releaseSomeActivities(IApplicationThread appInt) { 5838 synchronized(this) { 5839 final long origId = Binder.clearCallingIdentity(); 5840 try { 5841 ProcessRecord app = getRecordForAppLocked(appInt); 5842 mStackSupervisor.releaseSomeActivitiesLocked(app, "low-mem"); 5843 } finally { 5844 Binder.restoreCallingIdentity(origId); 5845 } 5846 } 5847 } 5848 5849 @Override 5850 public boolean willActivityBeVisible(IBinder token) { 5851 synchronized(this) { 5852 ActivityStack stack = ActivityRecord.getStackLocked(token); 5853 if (stack != null) { 5854 return stack.willActivityBeVisibleLocked(token); 5855 } 5856 return false; 5857 } 5858 } 5859 5860 @Override 5861 public void overridePendingTransition(IBinder token, String packageName, 5862 int enterAnim, int exitAnim) { 5863 synchronized(this) { 5864 ActivityRecord self = ActivityRecord.isInStackLocked(token); 5865 if (self == null) { 5866 return; 5867 } 5868 5869 final long origId = Binder.clearCallingIdentity(); 5870 5871 if (self.isState(ActivityState.RESUMED, ActivityState.PAUSING)) { 5872 mWindowManager.overridePendingAppTransition(packageName, 5873 enterAnim, exitAnim, null); 5874 } 5875 5876 Binder.restoreCallingIdentity(origId); 5877 } 5878 } 5879 5880 /** 5881 * Main function for removing an existing process from the activity manager 5882 * as a result of that process going away. Clears out all connections 5883 * to the process. 5884 */ 5885 @GuardedBy("this") 5886 private final void handleAppDiedLocked(ProcessRecord app, 5887 boolean restarting, boolean allowRestart) { 5888 int pid = app.pid; 5889 boolean kept = cleanUpApplicationRecordLocked(app, restarting, allowRestart, -1, 5890 false /*replacingPid*/); 5891 if (!kept && !restarting) { 5892 removeLruProcessLocked(app); 5893 if (pid > 0) { 5894 ProcessList.remove(pid); 5895 } 5896 } 5897 5898 if (mProfileProc == app) { 5899 clearProfilerLocked(); 5900 } 5901 5902 // Remove this application's activities from active lists. 5903 boolean hasVisibleActivities = mStackSupervisor.handleAppDiedLocked(app); 5904 5905 app.clearRecentTasks(); 5906 5907 app.activities.clear(); 5908 5909 if (app.instr != null) { 5910 Slog.w(TAG, "Crash of app " + app.processName 5911 + " running instrumentation " + app.instr.mClass); 5912 Bundle info = new Bundle(); 5913 info.putString("shortMsg", "Process crashed."); 5914 finishInstrumentationLocked(app, Activity.RESULT_CANCELED, info); 5915 } 5916 5917 mWindowManager.deferSurfaceLayout(); 5918 try { 5919 if (!restarting && hasVisibleActivities 5920 && !mStackSupervisor.resumeFocusedStackTopActivityLocked()) { 5921 // If there was nothing to resume, and we are not already restarting this process, but 5922 // there is a visible activity that is hosted by the process... then make sure all 5923 // visible activities are running, taking care of restarting this process. 5924 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0, !PRESERVE_WINDOWS); 5925 } 5926 } finally { 5927 mWindowManager.continueSurfaceLayout(); 5928 } 5929 } 5930 5931 private final int getLRURecordIndexForAppLocked(IApplicationThread thread) { 5932 final IBinder threadBinder = thread.asBinder(); 5933 // Find the application record. 5934 for (int i=mLruProcesses.size()-1; i>=0; i--) { 5935 final ProcessRecord rec = mLruProcesses.get(i); 5936 if (rec.thread != null && rec.thread.asBinder() == threadBinder) { 5937 return i; 5938 } 5939 } 5940 return -1; 5941 } 5942 5943 ProcessRecord getRecordForAppLocked(IApplicationThread thread) { 5944 if (thread == null) { 5945 return null; 5946 } 5947 5948 int appIndex = getLRURecordIndexForAppLocked(thread); 5949 if (appIndex >= 0) { 5950 return mLruProcesses.get(appIndex); 5951 } 5952 5953 // Validation: if it isn't in the LRU list, it shouldn't exist, but let's 5954 // double-check that. 5955 final IBinder threadBinder = thread.asBinder(); 5956 final ArrayMap<String, SparseArray<ProcessRecord>> pmap = mProcessNames.getMap(); 5957 for (int i = pmap.size()-1; i >= 0; i--) { 5958 final SparseArray<ProcessRecord> procs = pmap.valueAt(i); 5959 for (int j = procs.size()-1; j >= 0; j--) { 5960 final ProcessRecord proc = procs.valueAt(j); 5961 if (proc.thread != null && proc.thread.asBinder() == threadBinder) { 5962 Slog.wtf(TAG, "getRecordForApp: exists in name list but not in LRU list: " 5963 + proc); 5964 return proc; 5965 } 5966 } 5967 } 5968 5969 return null; 5970 } 5971 5972 final void doLowMemReportIfNeededLocked(ProcessRecord dyingProc) { 5973 // If there are no longer any background processes running, 5974 // and the app that died was not running instrumentation, 5975 // then tell everyone we are now low on memory. 5976 boolean haveBg = false; 5977 for (int i=mLruProcesses.size()-1; i>=0; i--) { 5978 ProcessRecord rec = mLruProcesses.get(i); 5979 if (rec.thread != null 5980 && rec.setProcState >= ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 5981 haveBg = true; 5982 break; 5983 } 5984 } 5985 5986 if (!haveBg) { 5987 boolean doReport = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 5988 if (doReport) { 5989 long now = SystemClock.uptimeMillis(); 5990 if (now < (mLastMemUsageReportTime+5*60*1000)) { 5991 doReport = false; 5992 } else { 5993 mLastMemUsageReportTime = now; 5994 } 5995 } 5996 final ArrayList<ProcessMemInfo> memInfos 5997 = doReport ? new ArrayList<ProcessMemInfo>(mLruProcesses.size()) : null; 5998 EventLog.writeEvent(EventLogTags.AM_LOW_MEMORY, mLruProcesses.size()); 5999 long now = SystemClock.uptimeMillis(); 6000 for (int i=mLruProcesses.size()-1; i>=0; i--) { 6001 ProcessRecord rec = mLruProcesses.get(i); 6002 if (rec == dyingProc || rec.thread == null) { 6003 continue; 6004 } 6005 if (doReport) { 6006 memInfos.add(new ProcessMemInfo(rec.processName, rec.pid, rec.setAdj, 6007 rec.setProcState, rec.adjType, rec.makeAdjReason())); 6008 } 6009 if ((rec.lastLowMemory+mConstants.GC_MIN_INTERVAL) <= now) { 6010 // The low memory report is overriding any current 6011 // state for a GC request. Make sure to do 6012 // heavy/important/visible/foreground processes first. 6013 if (rec.setAdj <= ProcessList.HEAVY_WEIGHT_APP_ADJ) { 6014 rec.lastRequestedGc = 0; 6015 } else { 6016 rec.lastRequestedGc = rec.lastLowMemory; 6017 } 6018 rec.reportLowMemory = true; 6019 rec.lastLowMemory = now; 6020 mProcessesToGc.remove(rec); 6021 addProcessToGcListLocked(rec); 6022 } 6023 } 6024 if (doReport) { 6025 Message msg = mHandler.obtainMessage(REPORT_MEM_USAGE_MSG, memInfos); 6026 mHandler.sendMessage(msg); 6027 } 6028 scheduleAppGcsLocked(); 6029 } 6030 } 6031 6032 @GuardedBy("this") 6033 final void appDiedLocked(ProcessRecord app) { 6034 appDiedLocked(app, app.pid, app.thread, false); 6035 } 6036 6037 @GuardedBy("this") 6038 final void appDiedLocked(ProcessRecord app, int pid, IApplicationThread thread, 6039 boolean fromBinderDied) { 6040 // First check if this ProcessRecord is actually active for the pid. 6041 synchronized (mPidsSelfLocked) { 6042 ProcessRecord curProc = mPidsSelfLocked.get(pid); 6043 if (curProc != app) { 6044 Slog.w(TAG, "Spurious death for " + app + ", curProc for " + pid + ": " + curProc); 6045 return; 6046 } 6047 } 6048 6049 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 6050 synchronized (stats) { 6051 stats.noteProcessDiedLocked(app.info.uid, pid); 6052 } 6053 6054 if (!app.killed) { 6055 if (!fromBinderDied) { 6056 killProcessQuiet(pid); 6057 } 6058 killProcessGroup(app.uid, pid); 6059 app.killed = true; 6060 } 6061 6062 // Clean up already done if the process has been re-started. 6063 if (app.pid == pid && app.thread != null && 6064 app.thread.asBinder() == thread.asBinder()) { 6065 boolean doLowMem = app.instr == null; 6066 boolean doOomAdj = doLowMem; 6067 if (!app.killedByAm) { 6068 reportUidInfoMessageLocked(TAG, 6069 "Process " + app.processName + " (pid " + pid + ") has died: " 6070 + ProcessList.makeOomAdjString(app.setAdj) 6071 + ProcessList.makeProcStateString(app.setProcState), app.info.uid); 6072 mAllowLowerMemLevel = true; 6073 } else { 6074 // Note that we always want to do oom adj to update our state with the 6075 // new number of procs. 6076 mAllowLowerMemLevel = false; 6077 doLowMem = false; 6078 } 6079 EventLog.writeEvent(EventLogTags.AM_PROC_DIED, app.userId, app.pid, app.processName, 6080 app.setAdj, app.setProcState); 6081 if (DEBUG_CLEANUP) Slog.v(TAG_CLEANUP, 6082 "Dying app: " + app + ", pid: " + pid + ", thread: " + thread.asBinder()); 6083 handleAppDiedLocked(app, false, true); 6084 6085 if (doOomAdj) { 6086 updateOomAdjLocked(); 6087 } 6088 if (doLowMem) { 6089 doLowMemReportIfNeededLocked(app); 6090 } 6091 } else if (app.pid != pid) { 6092 // A new process has already been started. 6093 reportUidInfoMessageLocked(TAG, 6094 "Process " + app.processName + " (pid " + pid 6095 + ") has died and restarted (pid " + app.pid + ").", app.info.uid); 6096 EventLog.writeEvent(EventLogTags.AM_PROC_DIED, app.userId, app.pid, app.processName); 6097 } else if (DEBUG_PROCESSES) { 6098 Slog.d(TAG_PROCESSES, "Received spurious death notification for thread " 6099 + thread.asBinder()); 6100 } 6101 6102 // On the device which doesn't have Cgroup, log LmkStateChanged which is used as a signal 6103 // for pulling memory stats of other running processes when this process died. 6104 if (!hasMemcg()) { 6105 StatsLog.write(StatsLog.APP_DIED, SystemClock.elapsedRealtime()); 6106 } 6107 } 6108 6109 /** 6110 * If a stack trace dump file is configured, dump process stack traces. 6111 * @param clearTraces causes the dump file to be erased prior to the new 6112 * traces being written, if true; when false, the new traces will be 6113 * appended to any existing file content. 6114 * @param firstPids of dalvik VM processes to dump stack traces for first 6115 * @param lastPids of dalvik VM processes to dump stack traces for last 6116 * @param nativePids optional list of native pids to dump stack crawls 6117 */ 6118 public static File dumpStackTraces(boolean clearTraces, ArrayList<Integer> firstPids, 6119 ProcessCpuTracker processCpuTracker, SparseArray<Boolean> lastPids, 6120 ArrayList<Integer> nativePids) { 6121 ArrayList<Integer> extraPids = null; 6122 6123 // Measure CPU usage as soon as we're called in order to get a realistic sampling 6124 // of the top users at the time of the request. 6125 if (processCpuTracker != null) { 6126 processCpuTracker.init(); 6127 try { 6128 Thread.sleep(200); 6129 } catch (InterruptedException ignored) { 6130 } 6131 6132 processCpuTracker.update(); 6133 6134 // We'll take the stack crawls of just the top apps using CPU. 6135 final int N = processCpuTracker.countWorkingStats(); 6136 extraPids = new ArrayList<>(); 6137 for (int i = 0; i < N && extraPids.size() < 5; i++) { 6138 ProcessCpuTracker.Stats stats = processCpuTracker.getWorkingStats(i); 6139 if (lastPids.indexOfKey(stats.pid) >= 0) { 6140 if (DEBUG_ANR) Slog.d(TAG, "Collecting stacks for extra pid " + stats.pid); 6141 6142 extraPids.add(stats.pid); 6143 } else if (DEBUG_ANR) { 6144 Slog.d(TAG, "Skipping next CPU consuming process, not a java proc: " 6145 + stats.pid); 6146 } 6147 } 6148 } 6149 6150 boolean useTombstonedForJavaTraces = false; 6151 File tracesFile; 6152 6153 final String tracesDirProp = SystemProperties.get("dalvik.vm.stack-trace-dir", ""); 6154 if (tracesDirProp.isEmpty()) { 6155 // When dalvik.vm.stack-trace-dir is not set, we are using the "old" trace 6156 // dumping scheme. All traces are written to a global trace file (usually 6157 // "/data/anr/traces.txt") so the code below must take care to unlink and recreate 6158 // the file if requested. 6159 // 6160 // This mode of operation will be removed in the near future. 6161 6162 6163 String globalTracesPath = SystemProperties.get("dalvik.vm.stack-trace-file", null); 6164 if (globalTracesPath.isEmpty()) { 6165 Slog.w(TAG, "dumpStackTraces: no trace path configured"); 6166 return null; 6167 } 6168 6169 tracesFile = new File(globalTracesPath); 6170 try { 6171 if (clearTraces && tracesFile.exists()) { 6172 tracesFile.delete(); 6173 } 6174 6175 tracesFile.createNewFile(); 6176 FileUtils.setPermissions(globalTracesPath, 0666, -1, -1); // -rw-rw-rw- 6177 } catch (IOException e) { 6178 Slog.w(TAG, "Unable to prepare ANR traces file: " + tracesFile, e); 6179 return null; 6180 } 6181 } else { 6182 File tracesDir = new File(tracesDirProp); 6183 // When dalvik.vm.stack-trace-dir is set, we use the "new" trace dumping scheme. 6184 // Each set of ANR traces is written to a separate file and dumpstate will process 6185 // all such files and add them to a captured bug report if they're recent enough. 6186 maybePruneOldTraces(tracesDir); 6187 6188 // NOTE: We should consider creating the file in native code atomically once we've 6189 // gotten rid of the old scheme of dumping and lot of the code that deals with paths 6190 // can be removed. 6191 tracesFile = createAnrDumpFile(tracesDir); 6192 if (tracesFile == null) { 6193 return null; 6194 } 6195 6196 useTombstonedForJavaTraces = true; 6197 } 6198 6199 dumpStackTraces(tracesFile.getAbsolutePath(), firstPids, nativePids, extraPids, 6200 useTombstonedForJavaTraces); 6201 return tracesFile; 6202 } 6203 6204 @GuardedBy("ActivityManagerService.class") 6205 private static SimpleDateFormat sAnrFileDateFormat; 6206 6207 private static synchronized File createAnrDumpFile(File tracesDir) { 6208 if (sAnrFileDateFormat == null) { 6209 sAnrFileDateFormat = new SimpleDateFormat("yyyy-MM-dd-HH-mm-ss-SSS"); 6210 } 6211 6212 final String formattedDate = sAnrFileDateFormat.format(new Date()); 6213 final File anrFile = new File(tracesDir, "anr_" + formattedDate); 6214 6215 try { 6216 if (anrFile.createNewFile()) { 6217 FileUtils.setPermissions(anrFile.getAbsolutePath(), 0600, -1, -1); // -rw------- 6218 return anrFile; 6219 } else { 6220 Slog.w(TAG, "Unable to create ANR dump file: createNewFile failed"); 6221 } 6222 } catch (IOException ioe) { 6223 Slog.w(TAG, "Exception creating ANR dump file:", ioe); 6224 } 6225 6226 return null; 6227 } 6228 6229 /** 6230 * Prune all trace files that are more than a day old. 6231 * 6232 * NOTE: It might make sense to move this functionality to tombstoned eventually, along with a 6233 * shift away from anr_XX and tombstone_XX to a more descriptive name. We do it here for now 6234 * since it's the system_server that creates trace files for most ANRs. 6235 */ 6236 private static void maybePruneOldTraces(File tracesDir) { 6237 final long now = System.currentTimeMillis(); 6238 final File[] traceFiles = tracesDir.listFiles(); 6239 6240 if (traceFiles != null) { 6241 for (File file : traceFiles) { 6242 if ((now - file.lastModified()) > DAY_IN_MILLIS) { 6243 if (!file.delete()) { 6244 Slog.w(TAG, "Unable to prune stale trace file: " + file); 6245 } 6246 } 6247 } 6248 } 6249 } 6250 6251 /** 6252 * Legacy code, do not use. Existing users will be deleted. 6253 * 6254 * @deprecated 6255 */ 6256 @Deprecated 6257 public static class DumpStackFileObserver extends FileObserver { 6258 // Keep in sync with frameworks/native/cmds/dumpstate/utils.cpp 6259 private static final int TRACE_DUMP_TIMEOUT_MS = 10000; // 10 seconds 6260 6261 private final String mTracesPath; 6262 private boolean mClosed; 6263 6264 public DumpStackFileObserver(String tracesPath) { 6265 super(tracesPath, FileObserver.CLOSE_WRITE); 6266 mTracesPath = tracesPath; 6267 } 6268 6269 @Override 6270 public synchronized void onEvent(int event, String path) { 6271 mClosed = true; 6272 notify(); 6273 } 6274 6275 public long dumpWithTimeout(int pid, long timeout) { 6276 sendSignal(pid, SIGNAL_QUIT); 6277 final long start = SystemClock.elapsedRealtime(); 6278 6279 final long waitTime = Math.min(timeout, TRACE_DUMP_TIMEOUT_MS); 6280 synchronized (this) { 6281 try { 6282 wait(waitTime); // Wait for traces file to be closed. 6283 } catch (InterruptedException e) { 6284 Slog.wtf(TAG, e); 6285 } 6286 } 6287 6288 // This avoids a corner case of passing a negative time to the native 6289 // trace in case we've already hit the overall timeout. 6290 final long timeWaited = SystemClock.elapsedRealtime() - start; 6291 if (timeWaited >= timeout) { 6292 return timeWaited; 6293 } 6294 6295 if (!mClosed) { 6296 Slog.w(TAG, "Didn't see close of " + mTracesPath + " for pid " + pid + 6297 ". Attempting native stack collection."); 6298 6299 final long nativeDumpTimeoutMs = Math.min( 6300 NATIVE_DUMP_TIMEOUT_MS, timeout - timeWaited); 6301 6302 Debug.dumpNativeBacktraceToFileTimeout(pid, mTracesPath, 6303 (int) (nativeDumpTimeoutMs / 1000)); 6304 } 6305 6306 final long end = SystemClock.elapsedRealtime(); 6307 mClosed = false; 6308 6309 return (end - start); 6310 } 6311 } 6312 6313 /** 6314 * Dump java traces for process {@code pid} to the specified file. If java trace dumping 6315 * fails, a native backtrace is attempted. Note that the timeout {@code timeoutMs} only applies 6316 * to the java section of the trace, a further {@code NATIVE_DUMP_TIMEOUT_MS} might be spent 6317 * attempting to obtain native traces in the case of a failure. Returns the total time spent 6318 * capturing traces. 6319 */ 6320 private static long dumpJavaTracesTombstoned(int pid, String fileName, long timeoutMs) { 6321 final long timeStart = SystemClock.elapsedRealtime(); 6322 if (!Debug.dumpJavaBacktraceToFileTimeout(pid, fileName, (int) (timeoutMs / 1000))) { 6323 Debug.dumpNativeBacktraceToFileTimeout(pid, fileName, 6324 (NATIVE_DUMP_TIMEOUT_MS / 1000)); 6325 } 6326 6327 return SystemClock.elapsedRealtime() - timeStart; 6328 } 6329 6330 private static void dumpStackTraces(String tracesFile, ArrayList<Integer> firstPids, 6331 ArrayList<Integer> nativePids, ArrayList<Integer> extraPids, 6332 boolean useTombstonedForJavaTraces) { 6333 6334 // We don't need any sort of inotify based monitoring when we're dumping traces via 6335 // tombstoned. Data is piped to an "intercept" FD installed in tombstoned so we're in full 6336 // control of all writes to the file in question. 6337 final DumpStackFileObserver observer; 6338 if (useTombstonedForJavaTraces) { 6339 observer = null; 6340 } else { 6341 // Use a FileObserver to detect when traces finish writing. 6342 // The order of traces is considered important to maintain for legibility. 6343 observer = new DumpStackFileObserver(tracesFile); 6344 } 6345 6346 // We must complete all stack dumps within 20 seconds. 6347 long remainingTime = 20 * 1000; 6348 try { 6349 if (observer != null) { 6350 observer.startWatching(); 6351 } 6352 6353 // First collect all of the stacks of the most important pids. 6354 if (firstPids != null) { 6355 int num = firstPids.size(); 6356 for (int i = 0; i < num; i++) { 6357 if (DEBUG_ANR) Slog.d(TAG, "Collecting stacks for pid " 6358 + firstPids.get(i)); 6359 final long timeTaken; 6360 if (useTombstonedForJavaTraces) { 6361 timeTaken = dumpJavaTracesTombstoned(firstPids.get(i), tracesFile, remainingTime); 6362 } else { 6363 timeTaken = observer.dumpWithTimeout(firstPids.get(i), remainingTime); 6364 } 6365 6366 remainingTime -= timeTaken; 6367 if (remainingTime <= 0) { 6368 Slog.e(TAG, "Aborting stack trace dump (current firstPid=" + firstPids.get(i) + 6369 "); deadline exceeded."); 6370 return; 6371 } 6372 6373 if (DEBUG_ANR) { 6374 Slog.d(TAG, "Done with pid " + firstPids.get(i) + " in " + timeTaken + "ms"); 6375 } 6376 } 6377 } 6378 6379 // Next collect the stacks of the native pids 6380 if (nativePids != null) { 6381 for (int pid : nativePids) { 6382 if (DEBUG_ANR) Slog.d(TAG, "Collecting stacks for native pid " + pid); 6383 final long nativeDumpTimeoutMs = Math.min(NATIVE_DUMP_TIMEOUT_MS, remainingTime); 6384 6385 final long start = SystemClock.elapsedRealtime(); 6386 Debug.dumpNativeBacktraceToFileTimeout( 6387 pid, tracesFile, (int) (nativeDumpTimeoutMs / 1000)); 6388 final long timeTaken = SystemClock.elapsedRealtime() - start; 6389 6390 remainingTime -= timeTaken; 6391 if (remainingTime <= 0) { 6392 Slog.e(TAG, "Aborting stack trace dump (current native pid=" + pid + 6393 "); deadline exceeded."); 6394 return; 6395 } 6396 6397 if (DEBUG_ANR) { 6398 Slog.d(TAG, "Done with native pid " + pid + " in " + timeTaken + "ms"); 6399 } 6400 } 6401 } 6402 6403 // Lastly, dump stacks for all extra PIDs from the CPU tracker. 6404 if (extraPids != null) { 6405 for (int pid : extraPids) { 6406 if (DEBUG_ANR) Slog.d(TAG, "Collecting stacks for extra pid " + pid); 6407 6408 final long timeTaken; 6409 if (useTombstonedForJavaTraces) { 6410 timeTaken = dumpJavaTracesTombstoned(pid, tracesFile, remainingTime); 6411 } else { 6412 timeTaken = observer.dumpWithTimeout(pid, remainingTime); 6413 } 6414 6415 remainingTime -= timeTaken; 6416 if (remainingTime <= 0) { 6417 Slog.e(TAG, "Aborting stack trace dump (current extra pid=" + pid + 6418 "); deadline exceeded."); 6419 return; 6420 } 6421 6422 if (DEBUG_ANR) { 6423 Slog.d(TAG, "Done with extra pid " + pid + " in " + timeTaken + "ms"); 6424 } 6425 } 6426 } 6427 } finally { 6428 if (observer != null) { 6429 observer.stopWatching(); 6430 } 6431 } 6432 } 6433 6434 final void logAppTooSlow(ProcessRecord app, long startTime, String msg) { 6435 if (true || Build.IS_USER) { 6436 return; 6437 } 6438 String tracesPath = SystemProperties.get("dalvik.vm.stack-trace-file", null); 6439 if (tracesPath == null || tracesPath.length() == 0) { 6440 return; 6441 } 6442 6443 StrictMode.ThreadPolicy oldPolicy = StrictMode.allowThreadDiskReads(); 6444 StrictMode.allowThreadDiskWrites(); 6445 try { 6446 final File tracesFile = new File(tracesPath); 6447 final File tracesDir = tracesFile.getParentFile(); 6448 final File tracesTmp = new File(tracesDir, "__tmp__"); 6449 try { 6450 if (tracesFile.exists()) { 6451 tracesTmp.delete(); 6452 tracesFile.renameTo(tracesTmp); 6453 } 6454 StringBuilder sb = new StringBuilder(); 6455 Time tobj = new Time(); 6456 tobj.set(System.currentTimeMillis()); 6457 sb.append(tobj.format("%Y-%m-%d %H:%M:%S")); 6458 sb.append(": "); 6459 TimeUtils.formatDuration(SystemClock.uptimeMillis()-startTime, sb); 6460 sb.append(" since "); 6461 sb.append(msg); 6462 FileOutputStream fos = new FileOutputStream(tracesFile); 6463 fos.write(sb.toString().getBytes()); 6464 if (app == null) { 6465 fos.write("\n*** No application process!".getBytes()); 6466 } 6467 fos.close(); 6468 FileUtils.setPermissions(tracesFile.getPath(), 0666, -1, -1); // -rw-rw-rw- 6469 } catch (IOException e) { 6470 Slog.w(TAG, "Unable to prepare slow app traces file: " + tracesPath, e); 6471 return; 6472 } 6473 6474 if (app != null && app.pid > 0) { 6475 ArrayList<Integer> firstPids = new ArrayList<Integer>(); 6476 firstPids.add(app.pid); 6477 dumpStackTraces(tracesPath, firstPids, null, null, true /* useTombstoned */); 6478 } 6479 6480 File lastTracesFile = null; 6481 File curTracesFile = null; 6482 for (int i=9; i>=0; i--) { 6483 String name = String.format(Locale.US, "slow%02d.txt", i); 6484 curTracesFile = new File(tracesDir, name); 6485 if (curTracesFile.exists()) { 6486 if (lastTracesFile != null) { 6487 curTracesFile.renameTo(lastTracesFile); 6488 } else { 6489 curTracesFile.delete(); 6490 } 6491 } 6492 lastTracesFile = curTracesFile; 6493 } 6494 tracesFile.renameTo(curTracesFile); 6495 if (tracesTmp.exists()) { 6496 tracesTmp.renameTo(tracesFile); 6497 } 6498 } finally { 6499 StrictMode.setThreadPolicy(oldPolicy); 6500 } 6501 } 6502 6503 @GuardedBy("this") 6504 final void showLaunchWarningLocked(final ActivityRecord cur, final ActivityRecord next) { 6505 if (!mLaunchWarningShown) { 6506 mLaunchWarningShown = true; 6507 mUiHandler.post(new Runnable() { 6508 @Override 6509 public void run() { 6510 synchronized (ActivityManagerService.this) { 6511 final Dialog d = new LaunchWarningWindow(mContext, cur, next); 6512 d.show(); 6513 mUiHandler.postDelayed(new Runnable() { 6514 @Override 6515 public void run() { 6516 synchronized (ActivityManagerService.this) { 6517 d.dismiss(); 6518 mLaunchWarningShown = false; 6519 } 6520 } 6521 }, 4000); 6522 } 6523 } 6524 }); 6525 } 6526 } 6527 6528 @Override 6529 public boolean clearApplicationUserData(final String packageName, boolean keepState, 6530 final IPackageDataObserver observer, int userId) { 6531 enforceNotIsolatedCaller("clearApplicationUserData"); 6532 int uid = Binder.getCallingUid(); 6533 int pid = Binder.getCallingPid(); 6534 final int resolvedUserId = mUserController.handleIncomingUser(pid, uid, userId, false, 6535 ALLOW_FULL_ONLY, "clearApplicationUserData", null); 6536 6537 final ApplicationInfo appInfo; 6538 final boolean isInstantApp; 6539 6540 long callingId = Binder.clearCallingIdentity(); 6541 try { 6542 IPackageManager pm = AppGlobals.getPackageManager(); 6543 synchronized(this) { 6544 // Instant packages are not protected 6545 if (getPackageManagerInternalLocked().isPackageDataProtected( 6546 resolvedUserId, packageName)) { 6547 throw new SecurityException( 6548 "Cannot clear data for a protected package: " + packageName); 6549 } 6550 6551 ApplicationInfo applicationInfo = null; 6552 try { 6553 applicationInfo = pm.getApplicationInfo(packageName, 6554 MATCH_UNINSTALLED_PACKAGES, resolvedUserId); 6555 } catch (RemoteException e) { 6556 /* ignore */ 6557 } 6558 appInfo = applicationInfo; 6559 6560 final boolean clearingOwnUidData = appInfo != null && appInfo.uid == uid; 6561 6562 if (!clearingOwnUidData && checkComponentPermission(permission.CLEAR_APP_USER_DATA, 6563 pid, uid, -1, true) != PackageManager.PERMISSION_GRANTED) { 6564 throw new SecurityException("PID " + pid + " does not have permission " 6565 + android.Manifest.permission.CLEAR_APP_USER_DATA + " to clear data" 6566 + " of package " + packageName); 6567 } 6568 6569 final boolean hasInstantMetadata = getPackageManagerInternalLocked() 6570 .hasInstantApplicationMetadata(packageName, resolvedUserId); 6571 final boolean isUninstalledAppWithoutInstantMetadata = 6572 (appInfo == null && !hasInstantMetadata); 6573 isInstantApp = (appInfo != null && appInfo.isInstantApp()) 6574 || hasInstantMetadata; 6575 final boolean canAccessInstantApps = checkComponentPermission( 6576 permission.ACCESS_INSTANT_APPS, pid, uid, -1, true) 6577 == PackageManager.PERMISSION_GRANTED; 6578 6579 if (isUninstalledAppWithoutInstantMetadata || (isInstantApp 6580 && !canAccessInstantApps)) { 6581 Slog.w(TAG, "Invalid packageName: " + packageName); 6582 if (observer != null) { 6583 try { 6584 observer.onRemoveCompleted(packageName, false); 6585 } catch (RemoteException e) { 6586 Slog.i(TAG, "Observer no longer exists."); 6587 } 6588 } 6589 return false; 6590 } 6591 6592 if (appInfo != null) { 6593 forceStopPackageLocked(packageName, appInfo.uid, "clear data"); 6594 mRecentTasks.removeTasksByPackageName(packageName, resolvedUserId); 6595 } 6596 } 6597 6598 final IPackageDataObserver localObserver = new IPackageDataObserver.Stub() { 6599 @Override 6600 public void onRemoveCompleted(String packageName, boolean succeeded) 6601 throws RemoteException { 6602 if (appInfo != null) { 6603 synchronized (ActivityManagerService.this) { 6604 finishForceStopPackageLocked(packageName, appInfo.uid); 6605 } 6606 } 6607 final Intent intent = new Intent(Intent.ACTION_PACKAGE_DATA_CLEARED, 6608 Uri.fromParts("package", packageName, null)); 6609 intent.addFlags(Intent.FLAG_RECEIVER_INCLUDE_BACKGROUND); 6610 intent.putExtra(Intent.EXTRA_UID, (appInfo != null) ? appInfo.uid : -1); 6611 intent.putExtra(Intent.EXTRA_USER_HANDLE, resolvedUserId); 6612 if (isInstantApp) { 6613 intent.putExtra(Intent.EXTRA_PACKAGE_NAME, packageName); 6614 broadcastIntentInPackage("android", SYSTEM_UID, intent, null, null, 0, 6615 null, null, permission.ACCESS_INSTANT_APPS, null, false, false, 6616 resolvedUserId); 6617 } else { 6618 broadcastIntentInPackage("android", SYSTEM_UID, intent, null, null, 0, 6619 null, null, null, null, false, false, resolvedUserId); 6620 } 6621 6622 if (observer != null) { 6623 observer.onRemoveCompleted(packageName, succeeded); 6624 } 6625 } 6626 }; 6627 6628 try { 6629 // Clear application user data 6630 pm.clearApplicationUserData(packageName, localObserver, resolvedUserId); 6631 6632 if (appInfo != null) { 6633 // Restore already established notification state and permission grants, 6634 // so it told us to keep those intact -- it's about to emplace app data 6635 // that is appropriate for those bits of system state. 6636 if (!keepState) { 6637 synchronized (this) { 6638 // Remove all permissions granted from/to this package 6639 removeUriPermissionsForPackageLocked(packageName, resolvedUserId, true, 6640 false); 6641 } 6642 6643 // Reset notification state 6644 INotificationManager inm = NotificationManager.getService(); 6645 inm.clearData(packageName, appInfo.uid, uid == appInfo.uid); 6646 } 6647 6648 // Clear its scheduled jobs 6649 JobSchedulerInternal js = LocalServices.getService(JobSchedulerInternal.class); 6650 js.cancelJobsForUid(appInfo.uid, "clear data"); 6651 6652 // Clear its pending alarms 6653 AlarmManagerInternal ami = LocalServices.getService(AlarmManagerInternal.class); 6654 ami.removeAlarmsForUid(appInfo.uid); 6655 } 6656 } catch (RemoteException e) { 6657 } 6658 } finally { 6659 Binder.restoreCallingIdentity(callingId); 6660 } 6661 return true; 6662 } 6663 6664 @Override 6665 public void killBackgroundProcesses(final String packageName, int userId) { 6666 if (checkCallingPermission(android.Manifest.permission.KILL_BACKGROUND_PROCESSES) 6667 != PackageManager.PERMISSION_GRANTED && 6668 checkCallingPermission(android.Manifest.permission.RESTART_PACKAGES) 6669 != PackageManager.PERMISSION_GRANTED) { 6670 String msg = "Permission Denial: killBackgroundProcesses() from pid=" 6671 + Binder.getCallingPid() 6672 + ", uid=" + Binder.getCallingUid() 6673 + " requires " + android.Manifest.permission.KILL_BACKGROUND_PROCESSES; 6674 Slog.w(TAG, msg); 6675 throw new SecurityException(msg); 6676 } 6677 6678 userId = mUserController.handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 6679 userId, true, ALLOW_FULL_ONLY, "killBackgroundProcesses", null); 6680 final int[] userIds = mUserController.expandUserId(userId); 6681 6682 long callingId = Binder.clearCallingIdentity(); 6683 try { 6684 IPackageManager pm = AppGlobals.getPackageManager(); 6685 for (int targetUserId : userIds) { 6686 int appId = -1; 6687 try { 6688 appId = UserHandle.getAppId( 6689 pm.getPackageUid(packageName, MATCH_DEBUG_TRIAGED_MISSING, 6690 targetUserId)); 6691 } catch (RemoteException e) { 6692 } 6693 if (appId == -1) { 6694 Slog.w(TAG, "Invalid packageName: " + packageName); 6695 return; 6696 } 6697 synchronized (this) { 6698 killPackageProcessesLocked(packageName, appId, targetUserId, 6699 ProcessList.SERVICE_ADJ, false, true, true, false, "kill background"); 6700 } 6701 } 6702 } finally { 6703 Binder.restoreCallingIdentity(callingId); 6704 } 6705 } 6706 6707 @Override 6708 public void killAllBackgroundProcesses() { 6709 if (checkCallingPermission(android.Manifest.permission.KILL_BACKGROUND_PROCESSES) 6710 != PackageManager.PERMISSION_GRANTED) { 6711 final String msg = "Permission Denial: killAllBackgroundProcesses() from pid=" 6712 + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid() 6713 + " requires " + android.Manifest.permission.KILL_BACKGROUND_PROCESSES; 6714 Slog.w(TAG, msg); 6715 throw new SecurityException(msg); 6716 } 6717 6718 final long callingId = Binder.clearCallingIdentity(); 6719 try { 6720 synchronized (this) { 6721 final ArrayList<ProcessRecord> procs = new ArrayList<>(); 6722 final int NP = mProcessNames.getMap().size(); 6723 for (int ip = 0; ip < NP; ip++) { 6724 final SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 6725 final int NA = apps.size(); 6726 for (int ia = 0; ia < NA; ia++) { 6727 final ProcessRecord app = apps.valueAt(ia); 6728 if (app.persistent) { 6729 // We don't kill persistent processes. 6730 continue; 6731 } 6732 if (app.removed) { 6733 procs.add(app); 6734 } else if (app.setAdj >= ProcessList.CACHED_APP_MIN_ADJ) { 6735 app.removed = true; 6736 procs.add(app); 6737 } 6738 } 6739 } 6740 6741 final int N = procs.size(); 6742 for (int i = 0; i < N; i++) { 6743 removeProcessLocked(procs.get(i), false, true, "kill all background"); 6744 } 6745 6746 mAllowLowerMemLevel = true; 6747 6748 updateOomAdjLocked(); 6749 doLowMemReportIfNeededLocked(null); 6750 } 6751 } finally { 6752 Binder.restoreCallingIdentity(callingId); 6753 } 6754 } 6755 6756 /** 6757 * Kills all background processes, except those matching any of the 6758 * specified properties. 6759 * 6760 * @param minTargetSdk the target SDK version at or above which to preserve 6761 * processes, or {@code -1} to ignore the target SDK 6762 * @param maxProcState the process state at or below which to preserve 6763 * processes, or {@code -1} to ignore the process state 6764 */ 6765 private void killAllBackgroundProcessesExcept(int minTargetSdk, int maxProcState) { 6766 if (checkCallingPermission(android.Manifest.permission.KILL_BACKGROUND_PROCESSES) 6767 != PackageManager.PERMISSION_GRANTED) { 6768 final String msg = "Permission Denial: killAllBackgroundProcessesExcept() from pid=" 6769 + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid() 6770 + " requires " + android.Manifest.permission.KILL_BACKGROUND_PROCESSES; 6771 Slog.w(TAG, msg); 6772 throw new SecurityException(msg); 6773 } 6774 6775 final long callingId = Binder.clearCallingIdentity(); 6776 try { 6777 synchronized (this) { 6778 final ArrayList<ProcessRecord> procs = new ArrayList<>(); 6779 final int NP = mProcessNames.getMap().size(); 6780 for (int ip = 0; ip < NP; ip++) { 6781 final SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 6782 final int NA = apps.size(); 6783 for (int ia = 0; ia < NA; ia++) { 6784 final ProcessRecord app = apps.valueAt(ia); 6785 if (app.removed) { 6786 procs.add(app); 6787 } else if ((minTargetSdk < 0 || app.info.targetSdkVersion < minTargetSdk) 6788 && (maxProcState < 0 || app.setProcState > maxProcState)) { 6789 app.removed = true; 6790 procs.add(app); 6791 } 6792 } 6793 } 6794 6795 final int N = procs.size(); 6796 for (int i = 0; i < N; i++) { 6797 removeProcessLocked(procs.get(i), false, true, "kill all background except"); 6798 } 6799 } 6800 } finally { 6801 Binder.restoreCallingIdentity(callingId); 6802 } 6803 } 6804 6805 @Override 6806 public void forceStopPackage(final String packageName, int userId) { 6807 if (checkCallingPermission(android.Manifest.permission.FORCE_STOP_PACKAGES) 6808 != PackageManager.PERMISSION_GRANTED) { 6809 String msg = "Permission Denial: forceStopPackage() from pid=" 6810 + Binder.getCallingPid() 6811 + ", uid=" + Binder.getCallingUid() 6812 + " requires " + android.Manifest.permission.FORCE_STOP_PACKAGES; 6813 Slog.w(TAG, msg); 6814 throw new SecurityException(msg); 6815 } 6816 final int callingPid = Binder.getCallingPid(); 6817 userId = mUserController.handleIncomingUser(callingPid, Binder.getCallingUid(), 6818 userId, true, ALLOW_FULL_ONLY, "forceStopPackage", null); 6819 long callingId = Binder.clearCallingIdentity(); 6820 try { 6821 IPackageManager pm = AppGlobals.getPackageManager(); 6822 synchronized(this) { 6823 int[] users = userId == UserHandle.USER_ALL 6824 ? mUserController.getUsers() : new int[] { userId }; 6825 for (int user : users) { 6826 if (getPackageManagerInternalLocked().isPackageStateProtected( 6827 packageName, user)) { 6828 Slog.w(TAG, "Ignoring request to force stop protected package " 6829 + packageName + " u" + user); 6830 return; 6831 } 6832 6833 int pkgUid = -1; 6834 try { 6835 pkgUid = pm.getPackageUid(packageName, MATCH_DEBUG_TRIAGED_MISSING, 6836 user); 6837 } catch (RemoteException e) { 6838 } 6839 if (pkgUid == -1) { 6840 Slog.w(TAG, "Invalid packageName: " + packageName); 6841 continue; 6842 } 6843 try { 6844 pm.setPackageStoppedState(packageName, true, user); 6845 } catch (RemoteException e) { 6846 } catch (IllegalArgumentException e) { 6847 Slog.w(TAG, "Failed trying to unstop package " 6848 + packageName + ": " + e); 6849 } 6850 if (mUserController.isUserRunning(user, 0)) { 6851 forceStopPackageLocked(packageName, pkgUid, "from pid " + callingPid); 6852 finishForceStopPackageLocked(packageName, pkgUid); 6853 } 6854 } 6855 } 6856 } finally { 6857 Binder.restoreCallingIdentity(callingId); 6858 } 6859 } 6860 6861 @Override 6862 public void addPackageDependency(String packageName) { 6863 synchronized (this) { 6864 int callingPid = Binder.getCallingPid(); 6865 if (callingPid == myPid()) { 6866 // Yeah, um, no. 6867 return; 6868 } 6869 ProcessRecord proc; 6870 synchronized (mPidsSelfLocked) { 6871 proc = mPidsSelfLocked.get(Binder.getCallingPid()); 6872 } 6873 if (proc != null) { 6874 if (proc.pkgDeps == null) { 6875 proc.pkgDeps = new ArraySet<String>(1); 6876 } 6877 proc.pkgDeps.add(packageName); 6878 } 6879 } 6880 } 6881 6882 /* 6883 * The pkg name and app id have to be specified. 6884 */ 6885 @Override 6886 public void killApplication(String pkg, int appId, int userId, String reason) { 6887 if (pkg == null) { 6888 return; 6889 } 6890 // Make sure the uid is valid. 6891 if (appId < 0) { 6892 Slog.w(TAG, "Invalid appid specified for pkg : " + pkg); 6893 return; 6894 } 6895 int callerUid = Binder.getCallingUid(); 6896 // Only the system server can kill an application 6897 if (UserHandle.getAppId(callerUid) == SYSTEM_UID) { 6898 // Post an aysnc message to kill the application 6899 Message msg = mHandler.obtainMessage(KILL_APPLICATION_MSG); 6900 msg.arg1 = appId; 6901 msg.arg2 = userId; 6902 Bundle bundle = new Bundle(); 6903 bundle.putString("pkg", pkg); 6904 bundle.putString("reason", reason); 6905 msg.obj = bundle; 6906 mHandler.sendMessage(msg); 6907 } else { 6908 throw new SecurityException(callerUid + " cannot kill pkg: " + 6909 pkg); 6910 } 6911 } 6912 6913 @Override 6914 public void closeSystemDialogs(String reason) { 6915 enforceNotIsolatedCaller("closeSystemDialogs"); 6916 6917 final int pid = Binder.getCallingPid(); 6918 final int uid = Binder.getCallingUid(); 6919 final long origId = Binder.clearCallingIdentity(); 6920 try { 6921 synchronized (this) { 6922 // Only allow this from foreground processes, so that background 6923 // applications can't abuse it to prevent system UI from being shown. 6924 if (uid >= FIRST_APPLICATION_UID) { 6925 ProcessRecord proc; 6926 synchronized (mPidsSelfLocked) { 6927 proc = mPidsSelfLocked.get(pid); 6928 } 6929 if (proc.curRawAdj > ProcessList.PERCEPTIBLE_APP_ADJ) { 6930 Slog.w(TAG, "Ignoring closeSystemDialogs " + reason 6931 + " from background process " + proc); 6932 return; 6933 } 6934 } 6935 closeSystemDialogsLocked(reason); 6936 } 6937 } finally { 6938 Binder.restoreCallingIdentity(origId); 6939 } 6940 } 6941 6942 @GuardedBy("this") 6943 void closeSystemDialogsLocked(String reason) { 6944 Intent intent = new Intent(Intent.ACTION_CLOSE_SYSTEM_DIALOGS); 6945 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 6946 | Intent.FLAG_RECEIVER_FOREGROUND); 6947 if (reason != null) { 6948 intent.putExtra("reason", reason); 6949 } 6950 mWindowManager.closeSystemDialogs(reason); 6951 6952 mStackSupervisor.closeSystemDialogsLocked(); 6953 6954 broadcastIntentLocked(null, null, intent, null, null, 0, null, null, null, 6955 OP_NONE, null, false, false, 6956 -1, SYSTEM_UID, UserHandle.USER_ALL); 6957 } 6958 6959 @Override 6960 public Debug.MemoryInfo[] getProcessMemoryInfo(int[] pids) { 6961 enforceNotIsolatedCaller("getProcessMemoryInfo"); 6962 Debug.MemoryInfo[] infos = new Debug.MemoryInfo[pids.length]; 6963 for (int i=pids.length-1; i>=0; i--) { 6964 ProcessRecord proc; 6965 int oomAdj; 6966 synchronized (this) { 6967 synchronized (mPidsSelfLocked) { 6968 proc = mPidsSelfLocked.get(pids[i]); 6969 oomAdj = proc != null ? proc.setAdj : 0; 6970 } 6971 } 6972 infos[i] = new Debug.MemoryInfo(); 6973 long startTime = SystemClock.currentThreadTimeMillis(); 6974 Debug.getMemoryInfo(pids[i], infos[i]); 6975 long endTime = SystemClock.currentThreadTimeMillis(); 6976 if (proc != null) { 6977 synchronized (this) { 6978 if (proc.thread != null && proc.setAdj == oomAdj) { 6979 // Record this for posterity if the process has been stable. 6980 proc.baseProcessTracker.addPss(infos[i].getTotalPss(), 6981 infos[i].getTotalUss(), infos[i].getTotalRss(), false, 6982 ProcessStats.ADD_PSS_EXTERNAL_SLOW, endTime-startTime, 6983 proc.pkgList); 6984 } 6985 } 6986 } 6987 } 6988 return infos; 6989 } 6990 6991 @Override 6992 public long[] getProcessPss(int[] pids) { 6993 enforceNotIsolatedCaller("getProcessPss"); 6994 long[] pss = new long[pids.length]; 6995 for (int i=pids.length-1; i>=0; i--) { 6996 ProcessRecord proc; 6997 int oomAdj; 6998 synchronized (this) { 6999 synchronized (mPidsSelfLocked) { 7000 proc = mPidsSelfLocked.get(pids[i]); 7001 oomAdj = proc != null ? proc.setAdj : 0; 7002 } 7003 } 7004 long[] tmpUss = new long[3]; 7005 long startTime = SystemClock.currentThreadTimeMillis(); 7006 pss[i] = Debug.getPss(pids[i], tmpUss, null); 7007 long endTime = SystemClock.currentThreadTimeMillis(); 7008 if (proc != null) { 7009 synchronized (this) { 7010 if (proc.thread != null && proc.setAdj == oomAdj) { 7011 // Record this for posterity if the process has been stable. 7012 proc.baseProcessTracker.addPss(pss[i], tmpUss[0], tmpUss[2], false, 7013 ProcessStats.ADD_PSS_EXTERNAL, endTime-startTime, proc.pkgList); 7014 } 7015 } 7016 } 7017 } 7018 return pss; 7019 } 7020 7021 @Override 7022 public void killApplicationProcess(String processName, int uid) { 7023 if (processName == null) { 7024 return; 7025 } 7026 7027 int callerUid = Binder.getCallingUid(); 7028 // Only the system server can kill an application 7029 if (callerUid == SYSTEM_UID) { 7030 synchronized (this) { 7031 ProcessRecord app = getProcessRecordLocked(processName, uid, true); 7032 if (app != null && app.thread != null) { 7033 try { 7034 app.thread.scheduleSuicide(); 7035 } catch (RemoteException e) { 7036 // If the other end already died, then our work here is done. 7037 } 7038 } else { 7039 Slog.w(TAG, "Process/uid not found attempting kill of " 7040 + processName + " / " + uid); 7041 } 7042 } 7043 } else { 7044 throw new SecurityException(callerUid + " cannot kill app process: " + 7045 processName); 7046 } 7047 } 7048 7049 @GuardedBy("this") 7050 private void forceStopPackageLocked(final String packageName, int uid, String reason) { 7051 forceStopPackageLocked(packageName, UserHandle.getAppId(uid), false, 7052 false, true, false, false, UserHandle.getUserId(uid), reason); 7053 } 7054 7055 @GuardedBy("this") 7056 private void finishForceStopPackageLocked(final String packageName, int uid) { 7057 Intent intent = new Intent(Intent.ACTION_PACKAGE_RESTARTED, 7058 Uri.fromParts("package", packageName, null)); 7059 if (!mProcessesReady) { 7060 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 7061 | Intent.FLAG_RECEIVER_FOREGROUND); 7062 } 7063 intent.putExtra(Intent.EXTRA_UID, uid); 7064 intent.putExtra(Intent.EXTRA_USER_HANDLE, UserHandle.getUserId(uid)); 7065 broadcastIntentLocked(null, null, intent, 7066 null, null, 0, null, null, null, OP_NONE, 7067 null, false, false, MY_PID, SYSTEM_UID, UserHandle.getUserId(uid)); 7068 } 7069 7070 7071 @GuardedBy("this") 7072 private final boolean killPackageProcessesLocked(String packageName, int appId, 7073 int userId, int minOomAdj, boolean callerWillRestart, boolean allowRestart, 7074 boolean doit, boolean evenPersistent, String reason) { 7075 ArrayList<ProcessRecord> procs = new ArrayList<>(); 7076 7077 // Remove all processes this package may have touched: all with the 7078 // same UID (except for the system or root user), and all whose name 7079 // matches the package name. 7080 final int NP = mProcessNames.getMap().size(); 7081 for (int ip=0; ip<NP; ip++) { 7082 SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 7083 final int NA = apps.size(); 7084 for (int ia=0; ia<NA; ia++) { 7085 ProcessRecord app = apps.valueAt(ia); 7086 if (app.persistent && !evenPersistent) { 7087 // we don't kill persistent processes 7088 continue; 7089 } 7090 if (app.removed) { 7091 if (doit) { 7092 procs.add(app); 7093 } 7094 continue; 7095 } 7096 7097 // Skip process if it doesn't meet our oom adj requirement. 7098 if (app.setAdj < minOomAdj) { 7099 continue; 7100 } 7101 7102 // If no package is specified, we call all processes under the 7103 // give user id. 7104 if (packageName == null) { 7105 if (userId != UserHandle.USER_ALL && app.userId != userId) { 7106 continue; 7107 } 7108 if (appId >= 0 && UserHandle.getAppId(app.uid) != appId) { 7109 continue; 7110 } 7111 // Package has been specified, we want to hit all processes 7112 // that match it. We need to qualify this by the processes 7113 // that are running under the specified app and user ID. 7114 } else { 7115 final boolean isDep = app.pkgDeps != null 7116 && app.pkgDeps.contains(packageName); 7117 if (!isDep && UserHandle.getAppId(app.uid) != appId) { 7118 continue; 7119 } 7120 if (userId != UserHandle.USER_ALL && app.userId != userId) { 7121 continue; 7122 } 7123 if (!app.pkgList.containsKey(packageName) && !isDep) { 7124 continue; 7125 } 7126 } 7127 7128 // Process has passed all conditions, kill it! 7129 if (!doit) { 7130 return true; 7131 } 7132 app.removed = true; 7133 procs.add(app); 7134 } 7135 } 7136 7137 int N = procs.size(); 7138 for (int i=0; i<N; i++) { 7139 removeProcessLocked(procs.get(i), callerWillRestart, allowRestart, reason); 7140 } 7141 updateOomAdjLocked(); 7142 return N > 0; 7143 } 7144 7145 private void cleanupDisabledPackageComponentsLocked( 7146 String packageName, int userId, boolean killProcess, String[] changedClasses) { 7147 7148 Set<String> disabledClasses = null; 7149 boolean packageDisabled = false; 7150 IPackageManager pm = AppGlobals.getPackageManager(); 7151 7152 if (changedClasses == null) { 7153 // Nothing changed... 7154 return; 7155 } 7156 7157 // Determine enable/disable state of the package and its components. 7158 int enabled = PackageManager.COMPONENT_ENABLED_STATE_DEFAULT; 7159 for (int i = changedClasses.length - 1; i >= 0; i--) { 7160 final String changedClass = changedClasses[i]; 7161 7162 if (changedClass.equals(packageName)) { 7163 try { 7164 // Entire package setting changed 7165 enabled = pm.getApplicationEnabledSetting(packageName, 7166 (userId != UserHandle.USER_ALL) ? userId : UserHandle.USER_SYSTEM); 7167 } catch (Exception e) { 7168 // No such package/component; probably racing with uninstall. In any 7169 // event it means we have nothing further to do here. 7170 return; 7171 } 7172 packageDisabled = enabled != PackageManager.COMPONENT_ENABLED_STATE_ENABLED 7173 && enabled != PackageManager.COMPONENT_ENABLED_STATE_DEFAULT; 7174 if (packageDisabled) { 7175 // Entire package is disabled. 7176 // No need to continue to check component states. 7177 disabledClasses = null; 7178 break; 7179 } 7180 } else { 7181 try { 7182 enabled = pm.getComponentEnabledSetting( 7183 new ComponentName(packageName, changedClass), 7184 (userId != UserHandle.USER_ALL) ? userId : UserHandle.USER_SYSTEM); 7185 } catch (Exception e) { 7186 // As above, probably racing with uninstall. 7187 return; 7188 } 7189 if (enabled != PackageManager.COMPONENT_ENABLED_STATE_ENABLED 7190 && enabled != PackageManager.COMPONENT_ENABLED_STATE_DEFAULT) { 7191 if (disabledClasses == null) { 7192 disabledClasses = new ArraySet<>(changedClasses.length); 7193 } 7194 disabledClasses.add(changedClass); 7195 } 7196 } 7197 } 7198 7199 if (!packageDisabled && disabledClasses == null) { 7200 // Nothing to do here... 7201 return; 7202 } 7203 7204 // Clean-up disabled activities. 7205 if (mStackSupervisor.finishDisabledPackageActivitiesLocked( 7206 packageName, disabledClasses, true, false, userId) && mBooted) { 7207 mStackSupervisor.resumeFocusedStackTopActivityLocked(); 7208 mStackSupervisor.scheduleIdleLocked(); 7209 } 7210 7211 // Clean-up disabled tasks 7212 mRecentTasks.cleanupDisabledPackageTasksLocked(packageName, disabledClasses, userId); 7213 7214 // Clean-up disabled services. 7215 mServices.bringDownDisabledPackageServicesLocked( 7216 packageName, disabledClasses, userId, false, killProcess, true); 7217 7218 // Clean-up disabled providers. 7219 ArrayList<ContentProviderRecord> providers = new ArrayList<>(); 7220 mProviderMap.collectPackageProvidersLocked( 7221 packageName, disabledClasses, true, false, userId, providers); 7222 for (int i = providers.size() - 1; i >= 0; i--) { 7223 removeDyingProviderLocked(null, providers.get(i), true); 7224 } 7225 7226 // Clean-up disabled broadcast receivers. 7227 for (int i = mBroadcastQueues.length - 1; i >= 0; i--) { 7228 mBroadcastQueues[i].cleanupDisabledPackageReceiversLocked( 7229 packageName, disabledClasses, userId, true); 7230 } 7231 7232 } 7233 7234 final boolean clearBroadcastQueueForUserLocked(int userId) { 7235 boolean didSomething = false; 7236 for (int i = mBroadcastQueues.length - 1; i >= 0; i--) { 7237 didSomething |= mBroadcastQueues[i].cleanupDisabledPackageReceiversLocked( 7238 null, null, userId, true); 7239 } 7240 return didSomething; 7241 } 7242 7243 @GuardedBy("this") 7244 final boolean forceStopPackageLocked(String packageName, int appId, 7245 boolean callerWillRestart, boolean purgeCache, boolean doit, 7246 boolean evenPersistent, boolean uninstalling, int userId, String reason) { 7247 int i; 7248 7249 if (userId == UserHandle.USER_ALL && packageName == null) { 7250 Slog.w(TAG, "Can't force stop all processes of all users, that is insane!"); 7251 } 7252 7253 if (appId < 0 && packageName != null) { 7254 try { 7255 appId = UserHandle.getAppId(AppGlobals.getPackageManager() 7256 .getPackageUid(packageName, MATCH_DEBUG_TRIAGED_MISSING, 0)); 7257 } catch (RemoteException e) { 7258 } 7259 } 7260 7261 if (doit) { 7262 if (packageName != null) { 7263 Slog.i(TAG, "Force stopping " + packageName + " appid=" + appId 7264 + " user=" + userId + ": " + reason); 7265 } else { 7266 Slog.i(TAG, "Force stopping u" + userId + ": " + reason); 7267 } 7268 7269 mAppErrors.resetProcessCrashTimeLocked(packageName == null, appId, userId); 7270 } 7271 7272 boolean didSomething = killPackageProcessesLocked(packageName, appId, userId, 7273 ProcessList.INVALID_ADJ, callerWillRestart, true, doit, evenPersistent, 7274 packageName == null ? ("stop user " + userId) : ("stop " + packageName)); 7275 7276 didSomething |= mActivityStartController.clearPendingActivityLaunches(packageName); 7277 7278 if (mStackSupervisor.finishDisabledPackageActivitiesLocked( 7279 packageName, null, doit, evenPersistent, userId)) { 7280 if (!doit) { 7281 return true; 7282 } 7283 didSomething = true; 7284 } 7285 7286 if (mServices.bringDownDisabledPackageServicesLocked( 7287 packageName, null, userId, evenPersistent, true, doit)) { 7288 if (!doit) { 7289 return true; 7290 } 7291 didSomething = true; 7292 } 7293 7294 if (packageName == null) { 7295 // Remove all sticky broadcasts from this user. 7296 mStickyBroadcasts.remove(userId); 7297 } 7298 7299 ArrayList<ContentProviderRecord> providers = new ArrayList<>(); 7300 if (mProviderMap.collectPackageProvidersLocked(packageName, null, doit, evenPersistent, 7301 userId, providers)) { 7302 if (!doit) { 7303 return true; 7304 } 7305 didSomething = true; 7306 } 7307 for (i = providers.size() - 1; i >= 0; i--) { 7308 removeDyingProviderLocked(null, providers.get(i), true); 7309 } 7310 7311 // Remove transient permissions granted from/to this package/user 7312 removeUriPermissionsForPackageLocked(packageName, userId, false, false); 7313 7314 if (doit) { 7315 for (i = mBroadcastQueues.length - 1; i >= 0; i--) { 7316 didSomething |= mBroadcastQueues[i].cleanupDisabledPackageReceiversLocked( 7317 packageName, null, userId, doit); 7318 } 7319 } 7320 7321 if (packageName == null || uninstalling) { 7322 // Remove pending intents. For now we only do this when force 7323 // stopping users, because we have some problems when doing this 7324 // for packages -- app widgets are not currently cleaned up for 7325 // such packages, so they can be left with bad pending intents. 7326 if (mIntentSenderRecords.size() > 0) { 7327 Iterator<WeakReference<PendingIntentRecord>> it 7328 = mIntentSenderRecords.values().iterator(); 7329 while (it.hasNext()) { 7330 WeakReference<PendingIntentRecord> wpir = it.next(); 7331 if (wpir == null) { 7332 it.remove(); 7333 continue; 7334 } 7335 PendingIntentRecord pir = wpir.get(); 7336 if (pir == null) { 7337 it.remove(); 7338 continue; 7339 } 7340 if (packageName == null) { 7341 // Stopping user, remove all objects for the user. 7342 if (pir.key.userId != userId) { 7343 // Not the same user, skip it. 7344 continue; 7345 } 7346 } else { 7347 if (UserHandle.getAppId(pir.uid) != appId) { 7348 // Different app id, skip it. 7349 continue; 7350 } 7351 if (userId != UserHandle.USER_ALL && pir.key.userId != userId) { 7352 // Different user, skip it. 7353 continue; 7354 } 7355 if (!pir.key.packageName.equals(packageName)) { 7356 // Different package, skip it. 7357 continue; 7358 } 7359 } 7360 if (!doit) { 7361 return true; 7362 } 7363 didSomething = true; 7364 it.remove(); 7365 makeIntentSenderCanceledLocked(pir); 7366 if (pir.key.activity != null && pir.key.activity.pendingResults != null) { 7367 pir.key.activity.pendingResults.remove(pir.ref); 7368 } 7369 } 7370 } 7371 } 7372 7373 if (doit) { 7374 if (purgeCache && packageName != null) { 7375 AttributeCache ac = AttributeCache.instance(); 7376 if (ac != null) { 7377 ac.removePackage(packageName); 7378 } 7379 } 7380 if (mBooted) { 7381 mStackSupervisor.resumeFocusedStackTopActivityLocked(); 7382 mStackSupervisor.scheduleIdleLocked(); 7383 } 7384 } 7385 7386 return didSomething; 7387 } 7388 7389 private final ProcessRecord removeProcessNameLocked(final String name, final int uid) { 7390 return removeProcessNameLocked(name, uid, null); 7391 } 7392 7393 private final ProcessRecord removeProcessNameLocked(final String name, final int uid, 7394 final ProcessRecord expecting) { 7395 ProcessRecord old = mProcessNames.get(name, uid); 7396 // Only actually remove when the currently recorded value matches the 7397 // record that we expected; if it doesn't match then we raced with a 7398 // newly created process and we don't want to destroy the new one. 7399 if ((expecting == null) || (old == expecting)) { 7400 mProcessNames.remove(name, uid); 7401 } 7402 if (old != null && old.uidRecord != null) { 7403 old.uidRecord.numProcs--; 7404 if (old.uidRecord.numProcs == 0) { 7405 // No more processes using this uid, tell clients it is gone. 7406 if (DEBUG_UID_OBSERVERS) Slog.i(TAG_UID_OBSERVERS, 7407 "No more processes in " + old.uidRecord); 7408 enqueueUidChangeLocked(old.uidRecord, -1, UidRecord.CHANGE_GONE); 7409 EventLogTags.writeAmUidStopped(uid); 7410 mActiveUids.remove(uid); 7411 noteUidProcessState(uid, ActivityManager.PROCESS_STATE_NONEXISTENT); 7412 } 7413 old.uidRecord = null; 7414 } 7415 mIsolatedProcesses.remove(uid); 7416 return old; 7417 } 7418 7419 private final void addProcessNameLocked(ProcessRecord proc) { 7420 // We shouldn't already have a process under this name, but just in case we 7421 // need to clean up whatever may be there now. 7422 ProcessRecord old = removeProcessNameLocked(proc.processName, proc.uid); 7423 if (old == proc && proc.persistent) { 7424 // We are re-adding a persistent process. Whatevs! Just leave it there. 7425 Slog.w(TAG, "Re-adding persistent process " + proc); 7426 } else if (old != null) { 7427 Slog.wtf(TAG, "Already have existing proc " + old + " when adding " + proc); 7428 } 7429 UidRecord uidRec = mActiveUids.get(proc.uid); 7430 if (uidRec == null) { 7431 uidRec = new UidRecord(proc.uid); 7432 // This is the first appearance of the uid, report it now! 7433 if (DEBUG_UID_OBSERVERS) Slog.i(TAG_UID_OBSERVERS, 7434 "Creating new process uid: " + uidRec); 7435 if (Arrays.binarySearch(mDeviceIdleTempWhitelist, UserHandle.getAppId(proc.uid)) >= 0 7436 || mPendingTempWhitelist.indexOfKey(proc.uid) >= 0) { 7437 uidRec.setWhitelist = uidRec.curWhitelist = true; 7438 } 7439 uidRec.updateHasInternetPermission(); 7440 mActiveUids.put(proc.uid, uidRec); 7441 EventLogTags.writeAmUidRunning(uidRec.uid); 7442 noteUidProcessState(uidRec.uid, uidRec.curProcState); 7443 } 7444 proc.uidRecord = uidRec; 7445 7446 // Reset render thread tid if it was already set, so new process can set it again. 7447 proc.renderThreadTid = 0; 7448 uidRec.numProcs++; 7449 mProcessNames.put(proc.processName, proc.uid, proc); 7450 if (proc.isolated) { 7451 mIsolatedProcesses.put(proc.uid, proc); 7452 } 7453 } 7454 7455 @GuardedBy("this") 7456 boolean removeProcessLocked(ProcessRecord app, 7457 boolean callerWillRestart, boolean allowRestart, String reason) { 7458 final String name = app.processName; 7459 final int uid = app.uid; 7460 if (DEBUG_PROCESSES) Slog.d(TAG_PROCESSES, 7461 "Force removing proc " + app.toShortString() + " (" + name + "/" + uid + ")"); 7462 7463 ProcessRecord old = mProcessNames.get(name, uid); 7464 if (old != app) { 7465 // This process is no longer active, so nothing to do. 7466 Slog.w(TAG, "Ignoring remove of inactive process: " + app); 7467 return false; 7468 } 7469 removeProcessNameLocked(name, uid); 7470 if (mHeavyWeightProcess == app) { 7471 mHandler.sendMessage(mHandler.obtainMessage(CANCEL_HEAVY_NOTIFICATION_MSG, 7472 mHeavyWeightProcess.userId, 0)); 7473 mHeavyWeightProcess = null; 7474 } 7475 boolean needRestart = false; 7476 if ((app.pid > 0 && app.pid != MY_PID) || (app.pid == 0 && app.pendingStart)) { 7477 int pid = app.pid; 7478 if (pid > 0) { 7479 synchronized (mPidsSelfLocked) { 7480 mPidsSelfLocked.remove(pid); 7481 mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app); 7482 } 7483 mBatteryStatsService.noteProcessFinish(app.processName, app.info.uid); 7484 if (app.isolated) { 7485 mBatteryStatsService.removeIsolatedUid(app.uid, app.info.uid); 7486 getPackageManagerInternalLocked().removeIsolatedUid(app.uid); 7487 } 7488 } 7489 boolean willRestart = false; 7490 if (app.persistent && !app.isolated) { 7491 if (!callerWillRestart) { 7492 willRestart = true; 7493 } else { 7494 needRestart = true; 7495 } 7496 } 7497 app.kill(reason, true); 7498 handleAppDiedLocked(app, willRestart, allowRestart); 7499 if (willRestart) { 7500 removeLruProcessLocked(app); 7501 addAppLocked(app.info, null, false, null /* ABI override */); 7502 } 7503 } else { 7504 mRemovedProcesses.add(app); 7505 } 7506 7507 return needRestart; 7508 } 7509 7510 @GuardedBy("this") 7511 private final void processContentProviderPublishTimedOutLocked(ProcessRecord app) { 7512 cleanupAppInLaunchingProvidersLocked(app, true); 7513 removeProcessLocked(app, false, true, "timeout publishing content providers"); 7514 } 7515 7516 private final void processStartTimedOutLocked(ProcessRecord app) { 7517 final int pid = app.pid; 7518 boolean gone = false; 7519 synchronized (mPidsSelfLocked) { 7520 ProcessRecord knownApp = mPidsSelfLocked.get(pid); 7521 if (knownApp != null && knownApp.thread == null) { 7522 mPidsSelfLocked.remove(pid); 7523 gone = true; 7524 } 7525 } 7526 7527 if (gone) { 7528 Slog.w(TAG, "Process " + app + " failed to attach"); 7529 EventLog.writeEvent(EventLogTags.AM_PROCESS_START_TIMEOUT, app.userId, 7530 pid, app.uid, app.processName); 7531 removeProcessNameLocked(app.processName, app.uid); 7532 if (mHeavyWeightProcess == app) { 7533 mHandler.sendMessage(mHandler.obtainMessage(CANCEL_HEAVY_NOTIFICATION_MSG, 7534 mHeavyWeightProcess.userId, 0)); 7535 mHeavyWeightProcess = null; 7536 } 7537 mBatteryStatsService.noteProcessFinish(app.processName, app.info.uid); 7538 // Take care of any launching providers waiting for this process. 7539 cleanupAppInLaunchingProvidersLocked(app, true); 7540 // Take care of any services that are waiting for the process. 7541 mServices.processStartTimedOutLocked(app); 7542 app.kill("start timeout", true); 7543 if (app.isolated) { 7544 mBatteryStatsService.removeIsolatedUid(app.uid, app.info.uid); 7545 } 7546 removeLruProcessLocked(app); 7547 if (mBackupTarget != null && mBackupTarget.app.pid == pid) { 7548 Slog.w(TAG, "Unattached app died before backup, skipping"); 7549 mHandler.post(new Runnable() { 7550 @Override 7551 public void run(){ 7552 try { 7553 IBackupManager bm = IBackupManager.Stub.asInterface( 7554 ServiceManager.getService(Context.BACKUP_SERVICE)); 7555 bm.agentDisconnected(app.info.packageName); 7556 } catch (RemoteException e) { 7557 // Can't happen; the backup manager is local 7558 } 7559 } 7560 }); 7561 } 7562 if (isPendingBroadcastProcessLocked(pid)) { 7563 Slog.w(TAG, "Unattached app died before broadcast acknowledged, skipping"); 7564 skipPendingBroadcastLocked(pid); 7565 } 7566 } else { 7567 Slog.w(TAG, "Spurious process start timeout - pid not known for " + app); 7568 } 7569 } 7570 7571 @GuardedBy("this") 7572 private final boolean attachApplicationLocked(IApplicationThread thread, 7573 int pid, int callingUid, long startSeq) { 7574 7575 // Find the application record that is being attached... either via 7576 // the pid if we are running in multiple processes, or just pull the 7577 // next app record if we are emulating process with anonymous threads. 7578 ProcessRecord app; 7579 long startTime = SystemClock.uptimeMillis(); 7580 if (pid != MY_PID && pid >= 0) { 7581 synchronized (mPidsSelfLocked) { 7582 app = mPidsSelfLocked.get(pid); 7583 } 7584 } else { 7585 app = null; 7586 } 7587 7588 // It's possible that process called attachApplication before we got a chance to 7589 // update the internal state. 7590 if (app == null && startSeq > 0) { 7591 final ProcessRecord pending = mPendingStarts.get(startSeq); 7592 if (pending != null && pending.startUid == callingUid 7593 && handleProcessStartedLocked(pending, pid, pending.usingWrapper, 7594 startSeq, true)) { 7595 app = pending; 7596 } 7597 } 7598 7599 if (app == null) { 7600 Slog.w(TAG, "No pending application record for pid " + pid 7601 + " (IApplicationThread " + thread + "); dropping process"); 7602 EventLog.writeEvent(EventLogTags.AM_DROP_PROCESS, pid); 7603 if (pid > 0 && pid != MY_PID) { 7604 killProcessQuiet(pid); 7605 //TODO: killProcessGroup(app.info.uid, pid); 7606 } else { 7607 try { 7608 thread.scheduleExit(); 7609 } catch (Exception e) { 7610 // Ignore exceptions. 7611 } 7612 } 7613 return false; 7614 } 7615 7616 // If this application record is still attached to a previous 7617 // process, clean it up now. 7618 if (app.thread != null) { 7619 handleAppDiedLocked(app, true, true); 7620 } 7621 7622 // Tell the process all about itself. 7623 7624 if (DEBUG_ALL) Slog.v( 7625 TAG, "Binding process pid " + pid + " to record " + app); 7626 7627 final String processName = app.processName; 7628 try { 7629 AppDeathRecipient adr = new AppDeathRecipient( 7630 app, pid, thread); 7631 thread.asBinder().linkToDeath(adr, 0); 7632 app.deathRecipient = adr; 7633 } catch (RemoteException e) { 7634 app.resetPackageList(mProcessStats); 7635 startProcessLocked(app, "link fail", processName); 7636 return false; 7637 } 7638 7639 EventLog.writeEvent(EventLogTags.AM_PROC_BOUND, app.userId, app.pid, app.processName); 7640 7641 app.makeActive(thread, mProcessStats); 7642 app.curAdj = app.setAdj = app.verifiedAdj = ProcessList.INVALID_ADJ; 7643 app.curSchedGroup = app.setSchedGroup = ProcessList.SCHED_GROUP_DEFAULT; 7644 app.forcingToImportant = null; 7645 updateProcessForegroundLocked(app, false, false); 7646 app.hasShownUi = false; 7647 app.debugging = false; 7648 app.cached = false; 7649 app.killedByAm = false; 7650 app.killed = false; 7651 7652 7653 // We carefully use the same state that PackageManager uses for 7654 // filtering, since we use this flag to decide if we need to install 7655 // providers when user is unlocked later 7656 app.unlocked = StorageManager.isUserKeyUnlocked(app.userId); 7657 7658 mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app); 7659 7660 boolean normalMode = mProcessesReady || isAllowedWhileBooting(app.info); 7661 List<ProviderInfo> providers = normalMode ? generateApplicationProvidersLocked(app) : null; 7662 7663 if (providers != null && checkAppInLaunchingProvidersLocked(app)) { 7664 Message msg = mHandler.obtainMessage(CONTENT_PROVIDER_PUBLISH_TIMEOUT_MSG); 7665 msg.obj = app; 7666 mHandler.sendMessageDelayed(msg, CONTENT_PROVIDER_PUBLISH_TIMEOUT); 7667 } 7668 7669 checkTime(startTime, "attachApplicationLocked: before bindApplication"); 7670 7671 if (!normalMode) { 7672 Slog.i(TAG, "Launching preboot mode app: " + app); 7673 } 7674 7675 if (DEBUG_ALL) Slog.v( 7676 TAG, "New app record " + app 7677 + " thread=" + thread.asBinder() + " pid=" + pid); 7678 try { 7679 int testMode = ApplicationThreadConstants.DEBUG_OFF; 7680 if (mDebugApp != null && mDebugApp.equals(processName)) { 7681 testMode = mWaitForDebugger 7682 ? ApplicationThreadConstants.DEBUG_WAIT 7683 : ApplicationThreadConstants.DEBUG_ON; 7684 app.debugging = true; 7685 if (mDebugTransient) { 7686 mDebugApp = mOrigDebugApp; 7687 mWaitForDebugger = mOrigWaitForDebugger; 7688 } 7689 } 7690 7691 boolean enableTrackAllocation = false; 7692 if (mTrackAllocationApp != null && mTrackAllocationApp.equals(processName)) { 7693 enableTrackAllocation = true; 7694 mTrackAllocationApp = null; 7695 } 7696 7697 // If the app is being launched for restore or full backup, set it up specially 7698 boolean isRestrictedBackupMode = false; 7699 if (mBackupTarget != null && mBackupAppName.equals(processName)) { 7700 isRestrictedBackupMode = mBackupTarget.appInfo.uid >= FIRST_APPLICATION_UID 7701 && ((mBackupTarget.backupMode == BackupRecord.RESTORE) 7702 || (mBackupTarget.backupMode == BackupRecord.RESTORE_FULL) 7703 || (mBackupTarget.backupMode == BackupRecord.BACKUP_FULL)); 7704 } 7705 7706 if (app.instr != null) { 7707 notifyPackageUse(app.instr.mClass.getPackageName(), 7708 PackageManager.NOTIFY_PACKAGE_USE_INSTRUMENTATION); 7709 } 7710 if (DEBUG_CONFIGURATION) Slog.v(TAG_CONFIGURATION, "Binding proc " 7711 + processName + " with config " + getGlobalConfiguration()); 7712 ApplicationInfo appInfo = app.instr != null ? app.instr.mTargetInfo : app.info; 7713 app.compat = compatibilityInfoForPackageLocked(appInfo); 7714 7715 ProfilerInfo profilerInfo = null; 7716 String preBindAgent = null; 7717 if (mProfileApp != null && mProfileApp.equals(processName)) { 7718 mProfileProc = app; 7719 if (mProfilerInfo != null) { 7720 // Send a profiler info object to the app if either a file is given, or 7721 // an agent should be loaded at bind-time. 7722 boolean needsInfo = mProfilerInfo.profileFile != null 7723 || mProfilerInfo.attachAgentDuringBind; 7724 profilerInfo = needsInfo ? new ProfilerInfo(mProfilerInfo) : null; 7725 if (mProfilerInfo.agent != null) { 7726 preBindAgent = mProfilerInfo.agent; 7727 } 7728 } 7729 } else if (app.instr != null && app.instr.mProfileFile != null) { 7730 profilerInfo = new ProfilerInfo(app.instr.mProfileFile, null, 0, false, false, 7731 null, false); 7732 } 7733 if (mAppAgentMap != null && mAppAgentMap.containsKey(processName)) { 7734 // We need to do a debuggable check here. See setAgentApp for why the check is 7735 // postponed to here. 7736 if ((app.info.flags & ApplicationInfo.FLAG_DEBUGGABLE) != 0) { 7737 String agent = mAppAgentMap.get(processName); 7738 // Do not overwrite already requested agent. 7739 if (profilerInfo == null) { 7740 profilerInfo = new ProfilerInfo(null, null, 0, false, false, 7741 mAppAgentMap.get(processName), true); 7742 } else if (profilerInfo.agent == null) { 7743 profilerInfo = profilerInfo.setAgent(mAppAgentMap.get(processName), true); 7744 } 7745 } 7746 } 7747 7748 if (profilerInfo != null && profilerInfo.profileFd != null) { 7749 profilerInfo.profileFd = profilerInfo.profileFd.dup(); 7750 if (TextUtils.equals(mProfileApp, processName) && mProfilerInfo != null) { 7751 clearProfilerLocked(); 7752 } 7753 } 7754 7755 // We deprecated Build.SERIAL and it is not accessible to 7756 // apps that target the v2 security sandbox and to apps that 7757 // target APIs higher than O MR1. Since access to the serial 7758 // is now behind a permission we push down the value. 7759 final String buildSerial = (appInfo.targetSandboxVersion < 2 7760 && appInfo.targetSdkVersion < Build.VERSION_CODES.P) 7761 ? sTheRealBuildSerial : Build.UNKNOWN; 7762 7763 // Check if this is a secondary process that should be incorporated into some 7764 // currently active instrumentation. (Note we do this AFTER all of the profiling 7765 // stuff above because profiling can currently happen only in the primary 7766 // instrumentation process.) 7767 if (mActiveInstrumentation.size() > 0 && app.instr == null) { 7768 for (int i = mActiveInstrumentation.size() - 1; i >= 0 && app.instr == null; i--) { 7769 ActiveInstrumentation aInstr = mActiveInstrumentation.get(i); 7770 if (!aInstr.mFinished && aInstr.mTargetInfo.uid == app.uid) { 7771 if (aInstr.mTargetProcesses.length == 0) { 7772 // This is the wildcard mode, where every process brought up for 7773 // the target instrumentation should be included. 7774 if (aInstr.mTargetInfo.packageName.equals(app.info.packageName)) { 7775 app.instr = aInstr; 7776 aInstr.mRunningProcesses.add(app); 7777 } 7778 } else { 7779 for (String proc : aInstr.mTargetProcesses) { 7780 if (proc.equals(app.processName)) { 7781 app.instr = aInstr; 7782 aInstr.mRunningProcesses.add(app); 7783 break; 7784 } 7785 } 7786 } 7787 } 7788 } 7789 } 7790 7791 // If we were asked to attach an agent on startup, do so now, before we're binding 7792 // application code. 7793 if (preBindAgent != null) { 7794 thread.attachAgent(preBindAgent); 7795 } 7796 7797 7798 // Figure out whether the app needs to run in autofill compat mode. 7799 boolean isAutofillCompatEnabled = false; 7800 if (UserHandle.getAppId(app.info.uid) >= Process.FIRST_APPLICATION_UID) { 7801 final AutofillManagerInternal afm = LocalServices.getService( 7802 AutofillManagerInternal.class); 7803 if (afm != null) { 7804 isAutofillCompatEnabled = afm.isCompatibilityModeRequested( 7805 app.info.packageName, app.info.versionCode, app.userId); 7806 } 7807 } 7808 7809 checkTime(startTime, "attachApplicationLocked: immediately before bindApplication"); 7810 mStackSupervisor.getActivityMetricsLogger().notifyBindApplication(app); 7811 if (app.isolatedEntryPoint != null) { 7812 // This is an isolated process which should just call an entry point instead of 7813 // being bound to an application. 7814 thread.runIsolatedEntryPoint(app.isolatedEntryPoint, app.isolatedEntryPointArgs); 7815 } else if (app.instr != null) { 7816 thread.bindApplication(processName, appInfo, providers, 7817 app.instr.mClass, 7818 profilerInfo, app.instr.mArguments, 7819 app.instr.mWatcher, 7820 app.instr.mUiAutomationConnection, testMode, 7821 mBinderTransactionTrackingEnabled, enableTrackAllocation, 7822 isRestrictedBackupMode || !normalMode, app.persistent, 7823 new Configuration(getGlobalConfiguration()), app.compat, 7824 getCommonServicesLocked(app.isolated), 7825 mCoreSettingsObserver.getCoreSettingsLocked(), 7826 buildSerial, isAutofillCompatEnabled); 7827 } else { 7828 thread.bindApplication(processName, appInfo, providers, null, profilerInfo, 7829 null, null, null, testMode, 7830 mBinderTransactionTrackingEnabled, enableTrackAllocation, 7831 isRestrictedBackupMode || !normalMode, app.persistent, 7832 new Configuration(getGlobalConfiguration()), app.compat, 7833 getCommonServicesLocked(app.isolated), 7834 mCoreSettingsObserver.getCoreSettingsLocked(), 7835 buildSerial, isAutofillCompatEnabled); 7836 } 7837 if (profilerInfo != null) { 7838 profilerInfo.closeFd(); 7839 profilerInfo = null; 7840 } 7841 checkTime(startTime, "attachApplicationLocked: immediately after bindApplication"); 7842 updateLruProcessLocked(app, false, null); 7843 checkTime(startTime, "attachApplicationLocked: after updateLruProcessLocked"); 7844 app.lastRequestedGc = app.lastLowMemory = SystemClock.uptimeMillis(); 7845 } catch (Exception e) { 7846 // todo: Yikes! What should we do? For now we will try to 7847 // start another process, but that could easily get us in 7848 // an infinite loop of restarting processes... 7849 Slog.wtf(TAG, "Exception thrown during bind of " + app, e); 7850 7851 app.resetPackageList(mProcessStats); 7852 app.unlinkDeathRecipient(); 7853 startProcessLocked(app, "bind fail", processName); 7854 return false; 7855 } 7856 7857 // Remove this record from the list of starting applications. 7858 mPersistentStartingProcesses.remove(app); 7859 if (DEBUG_PROCESSES && mProcessesOnHold.contains(app)) Slog.v(TAG_PROCESSES, 7860 "Attach application locked removing on hold: " + app); 7861 mProcessesOnHold.remove(app); 7862 7863 boolean badApp = false; 7864 boolean didSomething = false; 7865 7866 // See if the top visible activity is waiting to run in this process... 7867 if (normalMode) { 7868 try { 7869 if (mStackSupervisor.attachApplicationLocked(app)) { 7870 didSomething = true; 7871 } 7872 } catch (Exception e) { 7873 Slog.wtf(TAG, "Exception thrown launching activities in " + app, e); 7874 badApp = true; 7875 } 7876 } 7877 7878 // Find any services that should be running in this process... 7879 if (!badApp) { 7880 try { 7881 didSomething |= mServices.attachApplicationLocked(app, processName); 7882 checkTime(startTime, "attachApplicationLocked: after mServices.attachApplicationLocked"); 7883 } catch (Exception e) { 7884 Slog.wtf(TAG, "Exception thrown starting services in " + app, e); 7885 badApp = true; 7886 } 7887 } 7888 7889 // Check if a next-broadcast receiver is in this process... 7890 if (!badApp && isPendingBroadcastProcessLocked(pid)) { 7891 try { 7892 didSomething |= sendPendingBroadcastsLocked(app); 7893 checkTime(startTime, "attachApplicationLocked: after sendPendingBroadcastsLocked"); 7894 } catch (Exception e) { 7895 // If the app died trying to launch the receiver we declare it 'bad' 7896 Slog.wtf(TAG, "Exception thrown dispatching broadcasts in " + app, e); 7897 badApp = true; 7898 } 7899 } 7900 7901 // Check whether the next backup agent is in this process... 7902 if (!badApp && mBackupTarget != null && mBackupTarget.app == app) { 7903 if (DEBUG_BACKUP) Slog.v(TAG_BACKUP, 7904 "New app is backup target, launching agent for " + app); 7905 notifyPackageUse(mBackupTarget.appInfo.packageName, 7906 PackageManager.NOTIFY_PACKAGE_USE_BACKUP); 7907 try { 7908 thread.scheduleCreateBackupAgent(mBackupTarget.appInfo, 7909 compatibilityInfoForPackageLocked(mBackupTarget.appInfo), 7910 mBackupTarget.backupMode); 7911 } catch (Exception e) { 7912 Slog.wtf(TAG, "Exception thrown creating backup agent in " + app, e); 7913 badApp = true; 7914 } 7915 } 7916 7917 if (badApp) { 7918 app.kill("error during init", true); 7919 handleAppDiedLocked(app, false, true); 7920 return false; 7921 } 7922 7923 if (!didSomething) { 7924 updateOomAdjLocked(); 7925 checkTime(startTime, "attachApplicationLocked: after updateOomAdjLocked"); 7926 } 7927 7928 return true; 7929 } 7930 7931 @Override 7932 public final void attachApplication(IApplicationThread thread, long startSeq) { 7933 synchronized (this) { 7934 int callingPid = Binder.getCallingPid(); 7935 final int callingUid = Binder.getCallingUid(); 7936 final long origId = Binder.clearCallingIdentity(); 7937 attachApplicationLocked(thread, callingPid, callingUid, startSeq); 7938 Binder.restoreCallingIdentity(origId); 7939 } 7940 } 7941 7942 @Override 7943 public final void activityIdle(IBinder token, Configuration config, boolean stopProfiling) { 7944 final long origId = Binder.clearCallingIdentity(); 7945 synchronized (this) { 7946 ActivityStack stack = ActivityRecord.getStackLocked(token); 7947 if (stack != null) { 7948 ActivityRecord r = 7949 mStackSupervisor.activityIdleInternalLocked(token, false /* fromTimeout */, 7950 false /* processPausingActivities */, config); 7951 if (stopProfiling) { 7952 if ((mProfileProc == r.app) && mProfilerInfo != null) { 7953 clearProfilerLocked(); 7954 } 7955 } 7956 } 7957 } 7958 Binder.restoreCallingIdentity(origId); 7959 } 7960 7961 void postFinishBooting(boolean finishBooting, boolean enableScreen) { 7962 mHandler.sendMessage(mHandler.obtainMessage(FINISH_BOOTING_MSG, 7963 finishBooting ? 1 : 0, enableScreen ? 1 : 0)); 7964 } 7965 7966 void enableScreenAfterBoot() { 7967 EventLog.writeEvent(EventLogTags.BOOT_PROGRESS_ENABLE_SCREEN, 7968 SystemClock.uptimeMillis()); 7969 mWindowManager.enableScreenAfterBoot(); 7970 7971 synchronized (this) { 7972 updateEventDispatchingLocked(); 7973 } 7974 } 7975 7976 @Override 7977 public void showBootMessage(final CharSequence msg, final boolean always) { 7978 if (Binder.getCallingUid() != myUid()) { 7979 throw new SecurityException(); 7980 } 7981 mWindowManager.showBootMessage(msg, always); 7982 } 7983 7984 @Override 7985 public void keyguardGoingAway(int flags) { 7986 enforceNotIsolatedCaller("keyguardGoingAway"); 7987 final long token = Binder.clearCallingIdentity(); 7988 try { 7989 synchronized (this) { 7990 mKeyguardController.keyguardGoingAway(flags); 7991 } 7992 } finally { 7993 Binder.restoreCallingIdentity(token); 7994 } 7995 } 7996 7997 /** 7998 * @return whther the keyguard is currently locked. 7999 */ 8000 boolean isKeyguardLocked() { 8001 return mKeyguardController.isKeyguardLocked(); 8002 } 8003 8004 final void finishBooting() { 8005 synchronized (this) { 8006 if (!mBootAnimationComplete) { 8007 mCallFinishBooting = true; 8008 return; 8009 } 8010 mCallFinishBooting = false; 8011 } 8012 8013 ArraySet<String> completedIsas = new ArraySet<String>(); 8014 for (String abi : Build.SUPPORTED_ABIS) { 8015 zygoteProcess.establishZygoteConnectionForAbi(abi); 8016 final String instructionSet = VMRuntime.getInstructionSet(abi); 8017 if (!completedIsas.contains(instructionSet)) { 8018 try { 8019 mInstaller.markBootComplete(VMRuntime.getInstructionSet(abi)); 8020 } catch (InstallerException e) { 8021 Slog.w(TAG, "Unable to mark boot complete for abi: " + abi + " (" + 8022 e.getMessage() +")"); 8023 } 8024 completedIsas.add(instructionSet); 8025 } 8026 } 8027 8028 IntentFilter pkgFilter = new IntentFilter(); 8029 pkgFilter.addAction(Intent.ACTION_QUERY_PACKAGE_RESTART); 8030 pkgFilter.addDataScheme("package"); 8031 mContext.registerReceiver(new BroadcastReceiver() { 8032 @Override 8033 public void onReceive(Context context, Intent intent) { 8034 String[] pkgs = intent.getStringArrayExtra(Intent.EXTRA_PACKAGES); 8035 if (pkgs != null) { 8036 for (String pkg : pkgs) { 8037 synchronized (ActivityManagerService.this) { 8038 if (forceStopPackageLocked(pkg, -1, false, false, false, false, false, 8039 0, "query restart")) { 8040 setResultCode(Activity.RESULT_OK); 8041 return; 8042 } 8043 } 8044 } 8045 } 8046 } 8047 }, pkgFilter); 8048 8049 IntentFilter dumpheapFilter = new IntentFilter(); 8050 dumpheapFilter.addAction(DumpHeapActivity.ACTION_DELETE_DUMPHEAP); 8051 mContext.registerReceiver(new BroadcastReceiver() { 8052 @Override 8053 public void onReceive(Context context, Intent intent) { 8054 if (intent.getBooleanExtra(DumpHeapActivity.EXTRA_DELAY_DELETE, false)) { 8055 mHandler.sendEmptyMessageDelayed(POST_DUMP_HEAP_NOTIFICATION_MSG, 5*60*1000); 8056 } else { 8057 mHandler.sendEmptyMessage(POST_DUMP_HEAP_NOTIFICATION_MSG); 8058 } 8059 } 8060 }, dumpheapFilter); 8061 8062 // Let system services know. 8063 mSystemServiceManager.startBootPhase(SystemService.PHASE_BOOT_COMPLETED); 8064 8065 synchronized (this) { 8066 // Ensure that any processes we had put on hold are now started 8067 // up. 8068 final int NP = mProcessesOnHold.size(); 8069 if (NP > 0) { 8070 ArrayList<ProcessRecord> procs = 8071 new ArrayList<ProcessRecord>(mProcessesOnHold); 8072 for (int ip=0; ip<NP; ip++) { 8073 if (DEBUG_PROCESSES) Slog.v(TAG_PROCESSES, "Starting process on hold: " 8074 + procs.get(ip)); 8075 startProcessLocked(procs.get(ip), "on-hold", null); 8076 } 8077 } 8078 if (mFactoryTest == FactoryTest.FACTORY_TEST_LOW_LEVEL) { 8079 return; 8080 } 8081 // Start looking for apps that are abusing wake locks. 8082 Message nmsg = mHandler.obtainMessage(CHECK_EXCESSIVE_POWER_USE_MSG); 8083 mHandler.sendMessageDelayed(nmsg, mConstants.POWER_CHECK_INTERVAL); 8084 // Tell anyone interested that we are done booting! 8085 SystemProperties.set("sys.boot_completed", "1"); 8086 8087 // And trigger dev.bootcomplete if we are not showing encryption progress 8088 if (!"trigger_restart_min_framework".equals(SystemProperties.get("vold.decrypt")) 8089 || "".equals(SystemProperties.get("vold.encrypt_progress"))) { 8090 SystemProperties.set("dev.bootcomplete", "1"); 8091 } 8092 mUserController.sendBootCompleted( 8093 new IIntentReceiver.Stub() { 8094 @Override 8095 public void performReceive(Intent intent, int resultCode, 8096 String data, Bundle extras, boolean ordered, 8097 boolean sticky, int sendingUser) { 8098 synchronized (ActivityManagerService.this) { 8099 requestPssAllProcsLocked(SystemClock.uptimeMillis(), true, false); 8100 } 8101 } 8102 }); 8103 mUserController.scheduleStartProfiles(); 8104 } 8105 } 8106 8107 @Override 8108 public void bootAnimationComplete() { 8109 final boolean callFinishBooting; 8110 synchronized (this) { 8111 callFinishBooting = mCallFinishBooting; 8112 mBootAnimationComplete = true; 8113 } 8114 if (callFinishBooting) { 8115 Trace.traceBegin(Trace.TRACE_TAG_ACTIVITY_MANAGER, "FinishBooting"); 8116 finishBooting(); 8117 Trace.traceEnd(Trace.TRACE_TAG_ACTIVITY_MANAGER); 8118 } 8119 } 8120 8121 final void ensureBootCompleted() { 8122 boolean booting; 8123 boolean enableScreen; 8124 synchronized (this) { 8125 booting = mBooting; 8126 mBooting = false; 8127 enableScreen = !mBooted; 8128 mBooted = true; 8129 } 8130 8131 if (booting) { 8132 Trace.traceBegin(Trace.TRACE_TAG_ACTIVITY_MANAGER, "FinishBooting"); 8133 finishBooting(); 8134 Trace.traceEnd(Trace.TRACE_TAG_ACTIVITY_MANAGER); 8135 } 8136 8137 if (enableScreen) { 8138 enableScreenAfterBoot(); 8139 } 8140 } 8141 8142 @Override 8143 public final void activityResumed(IBinder token) { 8144 final long origId = Binder.clearCallingIdentity(); 8145 synchronized(this) { 8146 ActivityRecord.activityResumedLocked(token); 8147 mWindowManager.notifyAppResumedFinished(token); 8148 } 8149 Binder.restoreCallingIdentity(origId); 8150 } 8151 8152 @Override 8153 public final void activityPaused(IBinder token) { 8154 final long origId = Binder.clearCallingIdentity(); 8155 synchronized(this) { 8156 ActivityStack stack = ActivityRecord.getStackLocked(token); 8157 if (stack != null) { 8158 stack.activityPausedLocked(token, false); 8159 } 8160 } 8161 Binder.restoreCallingIdentity(origId); 8162 } 8163 8164 @Override 8165 public final void activityStopped(IBinder token, Bundle icicle, 8166 PersistableBundle persistentState, CharSequence description) { 8167 if (DEBUG_ALL) Slog.v(TAG, "Activity stopped: token=" + token); 8168 8169 // Refuse possible leaked file descriptors 8170 if (icicle != null && icicle.hasFileDescriptors()) { 8171 throw new IllegalArgumentException("File descriptors passed in Bundle"); 8172 } 8173 8174 final long origId = Binder.clearCallingIdentity(); 8175 8176 synchronized (this) { 8177 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 8178 if (r != null) { 8179 r.activityStoppedLocked(icicle, persistentState, description); 8180 } 8181 } 8182 8183 trimApplications(); 8184 8185 Binder.restoreCallingIdentity(origId); 8186 } 8187 8188 @Override 8189 public final void activityDestroyed(IBinder token) { 8190 if (DEBUG_SWITCH) Slog.v(TAG_SWITCH, "ACTIVITY DESTROYED: " + token); 8191 synchronized (this) { 8192 ActivityStack stack = ActivityRecord.getStackLocked(token); 8193 if (stack != null) { 8194 stack.activityDestroyedLocked(token, "activityDestroyed"); 8195 } 8196 } 8197 } 8198 8199 @Override 8200 public final void activityRelaunched(IBinder token) { 8201 final long origId = Binder.clearCallingIdentity(); 8202 synchronized (this) { 8203 mStackSupervisor.activityRelaunchedLocked(token); 8204 } 8205 Binder.restoreCallingIdentity(origId); 8206 } 8207 8208 @Override 8209 public void reportSizeConfigurations(IBinder token, int[] horizontalSizeConfiguration, 8210 int[] verticalSizeConfigurations, int[] smallestSizeConfigurations) { 8211 if (DEBUG_CONFIGURATION) Slog.v(TAG, "Report configuration: " + token + " " 8212 + horizontalSizeConfiguration + " " + verticalSizeConfigurations); 8213 synchronized (this) { 8214 ActivityRecord record = ActivityRecord.isInStackLocked(token); 8215 if (record == null) { 8216 throw new IllegalArgumentException("reportSizeConfigurations: ActivityRecord not " 8217 + "found for: " + token); 8218 } 8219 record.setSizeConfigurations(horizontalSizeConfiguration, 8220 verticalSizeConfigurations, smallestSizeConfigurations); 8221 } 8222 } 8223 8224 @Override 8225 public final void notifyLaunchTaskBehindComplete(IBinder token) { 8226 mStackSupervisor.scheduleLaunchTaskBehindComplete(token); 8227 } 8228 8229 @Override 8230 public final void notifyEnterAnimationComplete(IBinder token) { 8231 mHandler.sendMessage(mHandler.obtainMessage(ENTER_ANIMATION_COMPLETE_MSG, token)); 8232 } 8233 8234 @Override 8235 public String getCallingPackage(IBinder token) { 8236 synchronized (this) { 8237 ActivityRecord r = getCallingRecordLocked(token); 8238 return r != null ? r.info.packageName : null; 8239 } 8240 } 8241 8242 @Override 8243 public ComponentName getCallingActivity(IBinder token) { 8244 synchronized (this) { 8245 ActivityRecord r = getCallingRecordLocked(token); 8246 return r != null ? r.intent.getComponent() : null; 8247 } 8248 } 8249 8250 private ActivityRecord getCallingRecordLocked(IBinder token) { 8251 ActivityRecord r = ActivityRecord.isInStackLocked(token); 8252 if (r == null) { 8253 return null; 8254 } 8255 return r.resultTo; 8256 } 8257 8258 @Override 8259 public ComponentName getActivityClassForToken(IBinder token) { 8260 synchronized(this) { 8261 ActivityRecord r = ActivityRecord.isInStackLocked(token); 8262 if (r == null) { 8263 return null; 8264 } 8265 return r.intent.getComponent(); 8266 } 8267 } 8268 8269 @Override 8270 public String getPackageForToken(IBinder token) { 8271 synchronized(this) { 8272 ActivityRecord r = ActivityRecord.isInStackLocked(token); 8273 if (r == null) { 8274 return null; 8275 } 8276 return r.packageName; 8277 } 8278 } 8279 8280 @Override 8281 public boolean isRootVoiceInteraction(IBinder token) { 8282 synchronized(this) { 8283 ActivityRecord r = ActivityRecord.isInStackLocked(token); 8284 if (r == null) { 8285 return false; 8286 } 8287 return r.rootVoiceInteraction; 8288 } 8289 } 8290 8291 @Override 8292 public IIntentSender getIntentSender(int type, 8293 String packageName, IBinder token, String resultWho, 8294 int requestCode, Intent[] intents, String[] resolvedTypes, 8295 int flags, Bundle bOptions, int userId) { 8296 enforceNotIsolatedCaller("getIntentSender"); 8297 // Refuse possible leaked file descriptors 8298 if (intents != null) { 8299 if (intents.length < 1) { 8300 throw new IllegalArgumentException("Intents array length must be >= 1"); 8301 } 8302 for (int i=0; i<intents.length; i++) { 8303 Intent intent = intents[i]; 8304 if (intent != null) { 8305 if (intent.hasFileDescriptors()) { 8306 throw new IllegalArgumentException("File descriptors passed in Intent"); 8307 } 8308 if (type == ActivityManager.INTENT_SENDER_BROADCAST && 8309 (intent.getFlags()&Intent.FLAG_RECEIVER_BOOT_UPGRADE) != 0) { 8310 throw new IllegalArgumentException( 8311 "Can't use FLAG_RECEIVER_BOOT_UPGRADE here"); 8312 } 8313 intents[i] = new Intent(intent); 8314 } 8315 } 8316 if (resolvedTypes != null && resolvedTypes.length != intents.length) { 8317 throw new IllegalArgumentException( 8318 "Intent array length does not match resolvedTypes length"); 8319 } 8320 } 8321 if (bOptions != null) { 8322 if (bOptions.hasFileDescriptors()) { 8323 throw new IllegalArgumentException("File descriptors passed in options"); 8324 } 8325 } 8326 8327 synchronized(this) { 8328 int callingUid = Binder.getCallingUid(); 8329 int origUserId = userId; 8330 userId = mUserController.handleIncomingUser(Binder.getCallingPid(), callingUid, userId, 8331 type == ActivityManager.INTENT_SENDER_BROADCAST, 8332 ALLOW_NON_FULL, "getIntentSender", null); 8333 if (origUserId == UserHandle.USER_CURRENT) { 8334 // We don't want to evaluate this until the pending intent is 8335 // actually executed. However, we do want to always do the 8336 // security checking for it above. 8337 userId = UserHandle.USER_CURRENT; 8338 } 8339 try { 8340 if (callingUid != 0 && callingUid != SYSTEM_UID) { 8341 final int uid = AppGlobals.getPackageManager().getPackageUid(packageName, 8342 MATCH_DEBUG_TRIAGED_MISSING, UserHandle.getUserId(callingUid)); 8343 if (!UserHandle.isSameApp(callingUid, uid)) { 8344 String msg = "Permission Denial: getIntentSender() from pid=" 8345 + Binder.getCallingPid() 8346 + ", uid=" + Binder.getCallingUid() 8347 + ", (need uid=" + uid + ")" 8348 + " is not allowed to send as package " + packageName; 8349 Slog.w(TAG, msg); 8350 throw new SecurityException(msg); 8351 } 8352 } 8353 8354 return getIntentSenderLocked(type, packageName, callingUid, userId, 8355 token, resultWho, requestCode, intents, resolvedTypes, flags, bOptions); 8356 8357 } catch (RemoteException e) { 8358 throw new SecurityException(e); 8359 } 8360 } 8361 } 8362 8363 IIntentSender getIntentSenderLocked(int type, String packageName, 8364 int callingUid, int userId, IBinder token, String resultWho, 8365 int requestCode, Intent[] intents, String[] resolvedTypes, int flags, 8366 Bundle bOptions) { 8367 if (DEBUG_MU) Slog.v(TAG_MU, "getIntentSenderLocked(): uid=" + callingUid); 8368 ActivityRecord activity = null; 8369 if (type == ActivityManager.INTENT_SENDER_ACTIVITY_RESULT) { 8370 activity = ActivityRecord.isInStackLocked(token); 8371 if (activity == null) { 8372 Slog.w(TAG, "Failed createPendingResult: activity " + token + " not in any stack"); 8373 return null; 8374 } 8375 if (activity.finishing) { 8376 Slog.w(TAG, "Failed createPendingResult: activity " + activity + " is finishing"); 8377 return null; 8378 } 8379 } 8380 8381 // We're going to be splicing together extras before sending, so we're 8382 // okay poking into any contained extras. 8383 if (intents != null) { 8384 for (int i = 0; i < intents.length; i++) { 8385 intents[i].setDefusable(true); 8386 } 8387 } 8388 Bundle.setDefusable(bOptions, true); 8389 8390 final boolean noCreate = (flags&PendingIntent.FLAG_NO_CREATE) != 0; 8391 final boolean cancelCurrent = (flags&PendingIntent.FLAG_CANCEL_CURRENT) != 0; 8392 final boolean updateCurrent = (flags&PendingIntent.FLAG_UPDATE_CURRENT) != 0; 8393 flags &= ~(PendingIntent.FLAG_NO_CREATE|PendingIntent.FLAG_CANCEL_CURRENT 8394 |PendingIntent.FLAG_UPDATE_CURRENT); 8395 8396 PendingIntentRecord.Key key = new PendingIntentRecord.Key(type, packageName, activity, 8397 resultWho, requestCode, intents, resolvedTypes, flags, 8398 SafeActivityOptions.fromBundle(bOptions), userId); 8399 WeakReference<PendingIntentRecord> ref; 8400 ref = mIntentSenderRecords.get(key); 8401 PendingIntentRecord rec = ref != null ? ref.get() : null; 8402 if (rec != null) { 8403 if (!cancelCurrent) { 8404 if (updateCurrent) { 8405 if (rec.key.requestIntent != null) { 8406 rec.key.requestIntent.replaceExtras(intents != null ? 8407 intents[intents.length - 1] : null); 8408 } 8409 if (intents != null) { 8410 intents[intents.length-1] = rec.key.requestIntent; 8411 rec.key.allIntents = intents; 8412 rec.key.allResolvedTypes = resolvedTypes; 8413 } else { 8414 rec.key.allIntents = null; 8415 rec.key.allResolvedTypes = null; 8416 } 8417 } 8418 return rec; 8419 } 8420 makeIntentSenderCanceledLocked(rec); 8421 mIntentSenderRecords.remove(key); 8422 } 8423 if (noCreate) { 8424 return rec; 8425 } 8426 rec = new PendingIntentRecord(this, key, callingUid); 8427 mIntentSenderRecords.put(key, rec.ref); 8428 if (type == ActivityManager.INTENT_SENDER_ACTIVITY_RESULT) { 8429 if (activity.pendingResults == null) { 8430 activity.pendingResults 8431 = new HashSet<WeakReference<PendingIntentRecord>>(); 8432 } 8433 activity.pendingResults.add(rec.ref); 8434 } 8435 return rec; 8436 } 8437 8438 @Override 8439 public int sendIntentSender(IIntentSender target, IBinder whitelistToken, int code, 8440 Intent intent, String resolvedType, 8441 IIntentReceiver finishedReceiver, String requiredPermission, Bundle options) { 8442 if (target instanceof PendingIntentRecord) { 8443 return ((PendingIntentRecord)target).sendWithResult(code, intent, resolvedType, 8444 whitelistToken, finishedReceiver, requiredPermission, options); 8445 } else { 8446 if (intent == null) { 8447 // Weird case: someone has given us their own custom IIntentSender, and now 8448 // they have someone else trying to send to it but of course this isn't 8449 // really a PendingIntent, so there is no base Intent, and the caller isn't 8450 // supplying an Intent... but we never want to dispatch a null Intent to 8451 // a receiver, so um... let's make something up. 8452 Slog.wtf(TAG, "Can't use null intent with direct IIntentSender call"); 8453 intent = new Intent(Intent.ACTION_MAIN); 8454 } 8455 try { 8456 target.send(code, intent, resolvedType, whitelistToken, null, 8457 requiredPermission, options); 8458 } catch (RemoteException e) { 8459 } 8460 // Platform code can rely on getting a result back when the send is done, but if 8461 // this intent sender is from outside of the system we can't rely on it doing that. 8462 // So instead we don't give it the result receiver, and instead just directly 8463 // report the finish immediately. 8464 if (finishedReceiver != null) { 8465 try { 8466 finishedReceiver.performReceive(intent, 0, 8467 null, null, false, false, UserHandle.getCallingUserId()); 8468 } catch (RemoteException e) { 8469 } 8470 } 8471 return 0; 8472 } 8473 } 8474 8475 @Override 8476 public void cancelIntentSender(IIntentSender sender) { 8477 if (!(sender instanceof PendingIntentRecord)) { 8478 return; 8479 } 8480 synchronized(this) { 8481 PendingIntentRecord rec = (PendingIntentRecord)sender; 8482 try { 8483 final int uid = AppGlobals.getPackageManager().getPackageUid(rec.key.packageName, 8484 MATCH_DEBUG_TRIAGED_MISSING, UserHandle.getCallingUserId()); 8485 if (!UserHandle.isSameApp(uid, Binder.getCallingUid())) { 8486 String msg = "Permission Denial: cancelIntentSender() from pid=" 8487 + Binder.getCallingPid() 8488 + ", uid=" + Binder.getCallingUid() 8489 + " is not allowed to cancel package " 8490 + rec.key.packageName; 8491 Slog.w(TAG, msg); 8492 throw new SecurityException(msg); 8493 } 8494 } catch (RemoteException e) { 8495 throw new SecurityException(e); 8496 } 8497 cancelIntentSenderLocked(rec, true); 8498 } 8499 } 8500 8501 void cancelIntentSenderLocked(PendingIntentRecord rec, boolean cleanActivity) { 8502 makeIntentSenderCanceledLocked(rec); 8503 mIntentSenderRecords.remove(rec.key); 8504 if (cleanActivity && rec.key.activity != null) { 8505 rec.key.activity.pendingResults.remove(rec.ref); 8506 } 8507 } 8508 8509 void makeIntentSenderCanceledLocked(PendingIntentRecord rec) { 8510 rec.canceled = true; 8511 RemoteCallbackList<IResultReceiver> callbacks = rec.detachCancelListenersLocked(); 8512 if (callbacks != null) { 8513 mHandler.obtainMessage(DISPATCH_PENDING_INTENT_CANCEL_MSG, callbacks).sendToTarget(); 8514 } 8515 } 8516 8517 @Override 8518 public String getPackageForIntentSender(IIntentSender pendingResult) { 8519 if (!(pendingResult instanceof PendingIntentRecord)) { 8520 return null; 8521 } 8522 try { 8523 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 8524 return res.key.packageName; 8525 } catch (ClassCastException e) { 8526 } 8527 return null; 8528 } 8529 8530 @Override 8531 public void registerIntentSenderCancelListener(IIntentSender sender, IResultReceiver receiver) { 8532 if (!(sender instanceof PendingIntentRecord)) { 8533 return; 8534 } 8535 boolean isCancelled; 8536 synchronized(this) { 8537 PendingIntentRecord pendingIntent = (PendingIntentRecord) sender; 8538 isCancelled = pendingIntent.canceled; 8539 if (!isCancelled) { 8540 pendingIntent.registerCancelListenerLocked(receiver); 8541 } 8542 } 8543 if (isCancelled) { 8544 try { 8545 receiver.send(Activity.RESULT_CANCELED, null); 8546 } catch (RemoteException e) { 8547 } 8548 } 8549 } 8550 8551 @Override 8552 public void unregisterIntentSenderCancelListener(IIntentSender sender, 8553 IResultReceiver receiver) { 8554 if (!(sender instanceof PendingIntentRecord)) { 8555 return; 8556 } 8557 synchronized(this) { 8558 ((PendingIntentRecord)sender).unregisterCancelListenerLocked(receiver); 8559 } 8560 } 8561 8562 @Override 8563 public int getUidForIntentSender(IIntentSender sender) { 8564 if (sender instanceof PendingIntentRecord) { 8565 try { 8566 PendingIntentRecord res = (PendingIntentRecord)sender; 8567 return res.uid; 8568 } catch (ClassCastException e) { 8569 } 8570 } 8571 return -1; 8572 } 8573 8574 @Override 8575 public boolean isIntentSenderTargetedToPackage(IIntentSender pendingResult) { 8576 if (!(pendingResult instanceof PendingIntentRecord)) { 8577 return false; 8578 } 8579 try { 8580 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 8581 if (res.key.allIntents == null) { 8582 return false; 8583 } 8584 for (int i=0; i<res.key.allIntents.length; i++) { 8585 Intent intent = res.key.allIntents[i]; 8586 if (intent.getPackage() != null && intent.getComponent() != null) { 8587 return false; 8588 } 8589 } 8590 return true; 8591 } catch (ClassCastException e) { 8592 } 8593 return false; 8594 } 8595 8596 @Override 8597 public boolean isIntentSenderAnActivity(IIntentSender pendingResult) { 8598 if (!(pendingResult instanceof PendingIntentRecord)) { 8599 return false; 8600 } 8601 try { 8602 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 8603 if (res.key.type == ActivityManager.INTENT_SENDER_ACTIVITY) { 8604 return true; 8605 } 8606 return false; 8607 } catch (ClassCastException e) { 8608 } 8609 return false; 8610 } 8611 8612 @Override 8613 public boolean isIntentSenderAForegroundService(IIntentSender pendingResult) { 8614 if (pendingResult instanceof PendingIntentRecord) { 8615 final PendingIntentRecord res = (PendingIntentRecord) pendingResult; 8616 return res.key.type == ActivityManager.INTENT_SENDER_FOREGROUND_SERVICE; 8617 } 8618 return false; 8619 } 8620 8621 @Override 8622 public Intent getIntentForIntentSender(IIntentSender pendingResult) { 8623 enforceCallingPermission(Manifest.permission.GET_INTENT_SENDER_INTENT, 8624 "getIntentForIntentSender()"); 8625 if (!(pendingResult instanceof PendingIntentRecord)) { 8626 return null; 8627 } 8628 try { 8629 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 8630 return res.key.requestIntent != null ? new Intent(res.key.requestIntent) : null; 8631 } catch (ClassCastException e) { 8632 } 8633 return null; 8634 } 8635 8636 @Override 8637 public String getTagForIntentSender(IIntentSender pendingResult, String prefix) { 8638 if (!(pendingResult instanceof PendingIntentRecord)) { 8639 return null; 8640 } 8641 try { 8642 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 8643 synchronized (this) { 8644 return getTagForIntentSenderLocked(res, prefix); 8645 } 8646 } catch (ClassCastException e) { 8647 } 8648 return null; 8649 } 8650 8651 String getTagForIntentSenderLocked(PendingIntentRecord res, String prefix) { 8652 final Intent intent = res.key.requestIntent; 8653 if (intent != null) { 8654 if (res.lastTag != null && res.lastTagPrefix == prefix && (res.lastTagPrefix == null 8655 || res.lastTagPrefix.equals(prefix))) { 8656 return res.lastTag; 8657 } 8658 res.lastTagPrefix = prefix; 8659 final StringBuilder sb = new StringBuilder(128); 8660 if (prefix != null) { 8661 sb.append(prefix); 8662 } 8663 if (intent.getAction() != null) { 8664 sb.append(intent.getAction()); 8665 } else if (intent.getComponent() != null) { 8666 intent.getComponent().appendShortString(sb); 8667 } else { 8668 sb.append("?"); 8669 } 8670 return res.lastTag = sb.toString(); 8671 } 8672 return null; 8673 } 8674 8675 @Override 8676 public void setProcessLimit(int max) { 8677 enforceCallingPermission(android.Manifest.permission.SET_PROCESS_LIMIT, 8678 "setProcessLimit()"); 8679 synchronized (this) { 8680 mConstants.setOverrideMaxCachedProcesses(max); 8681 } 8682 trimApplications(); 8683 } 8684 8685 @Override 8686 public int getProcessLimit() { 8687 synchronized (this) { 8688 return mConstants.getOverrideMaxCachedProcesses(); 8689 } 8690 } 8691 8692 void importanceTokenDied(ImportanceToken token) { 8693 synchronized (ActivityManagerService.this) { 8694 synchronized (mPidsSelfLocked) { 8695 ImportanceToken cur 8696 = mImportantProcesses.get(token.pid); 8697 if (cur != token) { 8698 return; 8699 } 8700 mImportantProcesses.remove(token.pid); 8701 ProcessRecord pr = mPidsSelfLocked.get(token.pid); 8702 if (pr == null) { 8703 return; 8704 } 8705 pr.forcingToImportant = null; 8706 updateProcessForegroundLocked(pr, false, false); 8707 } 8708 updateOomAdjLocked(); 8709 } 8710 } 8711 8712 @Override 8713 public void setProcessImportant(IBinder token, int pid, boolean isForeground, String reason) { 8714 enforceCallingPermission(android.Manifest.permission.SET_PROCESS_LIMIT, 8715 "setProcessImportant()"); 8716 synchronized(this) { 8717 boolean changed = false; 8718 8719 synchronized (mPidsSelfLocked) { 8720 ProcessRecord pr = mPidsSelfLocked.get(pid); 8721 if (pr == null && isForeground) { 8722 Slog.w(TAG, "setProcessForeground called on unknown pid: " + pid); 8723 return; 8724 } 8725 ImportanceToken oldToken = mImportantProcesses.get(pid); 8726 if (oldToken != null) { 8727 oldToken.token.unlinkToDeath(oldToken, 0); 8728 mImportantProcesses.remove(pid); 8729 if (pr != null) { 8730 pr.forcingToImportant = null; 8731 } 8732 changed = true; 8733 } 8734 if (isForeground && token != null) { 8735 ImportanceToken newToken = new ImportanceToken(pid, token, reason) { 8736 @Override 8737 public void binderDied() { 8738 importanceTokenDied(this); 8739 } 8740 }; 8741 try { 8742 token.linkToDeath(newToken, 0); 8743 mImportantProcesses.put(pid, newToken); 8744 pr.forcingToImportant = newToken; 8745 changed = true; 8746 } catch (RemoteException e) { 8747 // If the process died while doing this, we will later 8748 // do the cleanup with the process death link. 8749 } 8750 } 8751 } 8752 8753 if (changed) { 8754 updateOomAdjLocked(); 8755 } 8756 } 8757 } 8758 8759 @Override 8760 public boolean isAppForeground(int uid) { 8761 synchronized (this) { 8762 UidRecord uidRec = mActiveUids.get(uid); 8763 if (uidRec == null || uidRec.idle) { 8764 return false; 8765 } 8766 return uidRec.curProcState <= ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 8767 } 8768 } 8769 8770 // NOTE: this is an internal method used by the OnShellCommand implementation only and should 8771 // be guarded by permission checking. 8772 int getUidState(int uid) { 8773 synchronized (this) { 8774 return getUidStateLocked(uid); 8775 } 8776 } 8777 8778 int getUidStateLocked(int uid) { 8779 UidRecord uidRec = mActiveUids.get(uid); 8780 return uidRec == null ? ActivityManager.PROCESS_STATE_NONEXISTENT : uidRec.curProcState; 8781 } 8782 8783 @Override 8784 public boolean isInMultiWindowMode(IBinder token) { 8785 final long origId = Binder.clearCallingIdentity(); 8786 try { 8787 synchronized(this) { 8788 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 8789 if (r == null) { 8790 return false; 8791 } 8792 // An activity is consider to be in multi-window mode if its task isn't fullscreen. 8793 return r.inMultiWindowMode(); 8794 } 8795 } finally { 8796 Binder.restoreCallingIdentity(origId); 8797 } 8798 } 8799 8800 @Override 8801 public boolean isInPictureInPictureMode(IBinder token) { 8802 final long origId = Binder.clearCallingIdentity(); 8803 try { 8804 synchronized(this) { 8805 return isInPictureInPictureMode(ActivityRecord.forTokenLocked(token)); 8806 } 8807 } finally { 8808 Binder.restoreCallingIdentity(origId); 8809 } 8810 } 8811 8812 private boolean isInPictureInPictureMode(ActivityRecord r) { 8813 if (r == null || r.getStack() == null || !r.inPinnedWindowingMode() 8814 || r.getStack().isInStackLocked(r) == null) { 8815 return false; 8816 } 8817 8818 // If we are animating to fullscreen then we have already dispatched the PIP mode 8819 // changed, so we should reflect that check here as well. 8820 final PinnedActivityStack stack = r.getStack(); 8821 final PinnedStackWindowController windowController = stack.getWindowContainerController(); 8822 return !windowController.isAnimatingBoundsToFullscreen(); 8823 } 8824 8825 @Override 8826 public boolean enterPictureInPictureMode(IBinder token, final PictureInPictureParams params) { 8827 final long origId = Binder.clearCallingIdentity(); 8828 try { 8829 synchronized(this) { 8830 final ActivityRecord r = ensureValidPictureInPictureActivityParamsLocked( 8831 "enterPictureInPictureMode", token, params); 8832 8833 // If the activity is already in picture in picture mode, then just return early 8834 if (isInPictureInPictureMode(r)) { 8835 return true; 8836 } 8837 8838 // Activity supports picture-in-picture, now check that we can enter PiP at this 8839 // point, if it is 8840 if (!r.checkEnterPictureInPictureState("enterPictureInPictureMode", 8841 false /* beforeStopping */)) { 8842 return false; 8843 } 8844 8845 final Runnable enterPipRunnable = () -> { 8846 // Only update the saved args from the args that are set 8847 r.pictureInPictureArgs.copyOnlySet(params); 8848 final float aspectRatio = r.pictureInPictureArgs.getAspectRatio(); 8849 final List<RemoteAction> actions = r.pictureInPictureArgs.getActions(); 8850 // Adjust the source bounds by the insets for the transition down 8851 final Rect sourceBounds = new Rect(r.pictureInPictureArgs.getSourceRectHint()); 8852 mStackSupervisor.moveActivityToPinnedStackLocked(r, sourceBounds, aspectRatio, 8853 "enterPictureInPictureMode"); 8854 final PinnedActivityStack stack = r.getStack(); 8855 stack.setPictureInPictureAspectRatio(aspectRatio); 8856 stack.setPictureInPictureActions(actions); 8857 MetricsLoggerWrapper.logPictureInPictureEnter(mContext, r.appInfo.uid, 8858 r.shortComponentName, r.supportsEnterPipOnTaskSwitch); 8859 logPictureInPictureArgs(params); 8860 }; 8861 8862 if (isKeyguardLocked()) { 8863 // If the keyguard is showing or occluded, then try and dismiss it before 8864 // entering picture-in-picture (this will prompt the user to authenticate if the 8865 // device is currently locked). 8866 try { 8867 dismissKeyguard(token, new KeyguardDismissCallback() { 8868 @Override 8869 public void onDismissSucceeded() throws RemoteException { 8870 mHandler.post(enterPipRunnable); 8871 } 8872 }, null /* message */); 8873 } catch (RemoteException e) { 8874 // Local call 8875 } 8876 } else { 8877 // Enter picture in picture immediately otherwise 8878 enterPipRunnable.run(); 8879 } 8880 return true; 8881 } 8882 } finally { 8883 Binder.restoreCallingIdentity(origId); 8884 } 8885 } 8886 8887 @Override 8888 public void setPictureInPictureParams(IBinder token, final PictureInPictureParams params) { 8889 final long origId = Binder.clearCallingIdentity(); 8890 try { 8891 synchronized(this) { 8892 final ActivityRecord r = ensureValidPictureInPictureActivityParamsLocked( 8893 "setPictureInPictureParams", token, params); 8894 8895 // Only update the saved args from the args that are set 8896 r.pictureInPictureArgs.copyOnlySet(params); 8897 if (r.inPinnedWindowingMode()) { 8898 // If the activity is already in picture-in-picture, update the pinned stack now 8899 // if it is not already expanding to fullscreen. Otherwise, the arguments will 8900 // be used the next time the activity enters PiP 8901 final PinnedActivityStack stack = r.getStack(); 8902 if (!stack.isAnimatingBoundsToFullscreen()) { 8903 stack.setPictureInPictureAspectRatio( 8904 r.pictureInPictureArgs.getAspectRatio()); 8905 stack.setPictureInPictureActions(r.pictureInPictureArgs.getActions()); 8906 } 8907 } 8908 logPictureInPictureArgs(params); 8909 } 8910 } finally { 8911 Binder.restoreCallingIdentity(origId); 8912 } 8913 } 8914 8915 @Override 8916 public int getMaxNumPictureInPictureActions(IBinder token) { 8917 // Currently, this is a static constant, but later, we may change this to be dependent on 8918 // the context of the activity 8919 return 3; 8920 } 8921 8922 private void logPictureInPictureArgs(PictureInPictureParams params) { 8923 if (params.hasSetActions()) { 8924 MetricsLogger.histogram(mContext, "tron_varz_picture_in_picture_actions_count", 8925 params.getActions().size()); 8926 } 8927 if (params.hasSetAspectRatio()) { 8928 LogMaker lm = new LogMaker(MetricsEvent.ACTION_PICTURE_IN_PICTURE_ASPECT_RATIO_CHANGED); 8929 lm.addTaggedData(MetricsEvent.PICTURE_IN_PICTURE_ASPECT_RATIO, params.getAspectRatio()); 8930 MetricsLogger.action(lm); 8931 } 8932 } 8933 8934 /** 8935 * Checks the state of the system and the activity associated with the given {@param token} to 8936 * verify that picture-in-picture is supported for that activity. 8937 * 8938 * @return the activity record for the given {@param token} if all the checks pass. 8939 */ 8940 private ActivityRecord ensureValidPictureInPictureActivityParamsLocked(String caller, 8941 IBinder token, PictureInPictureParams params) { 8942 if (!mSupportsPictureInPicture) { 8943 throw new IllegalStateException(caller 8944 + ": Device doesn't support picture-in-picture mode."); 8945 } 8946 8947 final ActivityRecord r = ActivityRecord.forTokenLocked(token); 8948 if (r == null) { 8949 throw new IllegalStateException(caller 8950 + ": Can't find activity for token=" + token); 8951 } 8952 8953 if (!r.supportsPictureInPicture()) { 8954 throw new IllegalStateException(caller 8955 + ": Current activity does not support picture-in-picture."); 8956 } 8957 8958 if (params.hasSetAspectRatio() 8959 && !mWindowManager.isValidPictureInPictureAspectRatio(r.getStack().mDisplayId, 8960 params.getAspectRatio())) { 8961 final float minAspectRatio = mContext.getResources().getFloat( 8962 com.android.internal.R.dimen.config_pictureInPictureMinAspectRatio); 8963 final float maxAspectRatio = mContext.getResources().getFloat( 8964 com.android.internal.R.dimen.config_pictureInPictureMaxAspectRatio); 8965 throw new IllegalArgumentException(String.format(caller 8966 + ": Aspect ratio is too extreme (must be between %f and %f).", 8967 minAspectRatio, maxAspectRatio)); 8968 } 8969 8970 // Truncate the number of actions if necessary 8971 params.truncateActions(getMaxNumPictureInPictureActions(token)); 8972 8973 return r; 8974 } 8975 8976 // ========================================================= 8977 // PROCESS INFO 8978 // ========================================================= 8979 8980 static class ProcessInfoService extends IProcessInfoService.Stub { 8981 final ActivityManagerService mActivityManagerService; 8982 ProcessInfoService(ActivityManagerService activityManagerService) { 8983 mActivityManagerService = activityManagerService; 8984 } 8985 8986 @Override 8987 public void getProcessStatesFromPids(/*in*/ int[] pids, /*out*/ int[] states) { 8988 mActivityManagerService.getProcessStatesAndOomScoresForPIDs( 8989 /*in*/ pids, /*out*/ states, null); 8990 } 8991 8992 @Override 8993 public void getProcessStatesAndOomScoresFromPids( 8994 /*in*/ int[] pids, /*out*/ int[] states, /*out*/ int[] scores) { 8995 mActivityManagerService.getProcessStatesAndOomScoresForPIDs( 8996 /*in*/ pids, /*out*/ states, /*out*/ scores); 8997 } 8998 } 8999 9000 /** 9001 * For each PID in the given input array, write the current process state 9002 * for that process into the states array, or -1 to indicate that no 9003 * process with the given PID exists. If scores array is provided, write 9004 * the oom score for the process into the scores array, with INVALID_ADJ 9005 * indicating the PID doesn't exist. 9006 */ 9007 public void getProcessStatesAndOomScoresForPIDs( 9008 /*in*/ int[] pids, /*out*/ int[] states, /*out*/ int[] scores) { 9009 if (scores != null) { 9010 enforceCallingPermission(android.Manifest.permission.GET_PROCESS_STATE_AND_OOM_SCORE, 9011 "getProcessStatesAndOomScoresForPIDs()"); 9012 } 9013 9014 if (pids == null) { 9015 throw new NullPointerException("pids"); 9016 } else if (states == null) { 9017 throw new NullPointerException("states"); 9018 } else if (pids.length != states.length) { 9019 throw new IllegalArgumentException("pids and states arrays have different lengths!"); 9020 } else if (scores != null && pids.length != scores.length) { 9021 throw new IllegalArgumentException("pids and scores arrays have different lengths!"); 9022 } 9023 9024 synchronized (mPidsSelfLocked) { 9025 for (int i = 0; i < pids.length; i++) { 9026 ProcessRecord pr = mPidsSelfLocked.get(pids[i]); 9027 states[i] = (pr == null) ? ActivityManager.PROCESS_STATE_NONEXISTENT : 9028 pr.curProcState; 9029 if (scores != null) { 9030 scores[i] = (pr == null) ? ProcessList.INVALID_ADJ : pr.curAdj; 9031 } 9032 } 9033 } 9034 } 9035 9036 // ========================================================= 9037 // PERMISSIONS 9038 // ========================================================= 9039 9040 static class PermissionController extends IPermissionController.Stub { 9041 ActivityManagerService mActivityManagerService; 9042 PermissionController(ActivityManagerService activityManagerService) { 9043 mActivityManagerService = activityManagerService; 9044 } 9045 9046 @Override 9047 public boolean checkPermission(String permission, int pid, int uid) { 9048 return mActivityManagerService.checkPermission(permission, pid, 9049 uid) == PackageManager.PERMISSION_GRANTED; 9050 } 9051 9052 @Override 9053 public int noteOp(String op, int uid, String packageName) { 9054 return mActivityManagerService.mAppOpsService 9055 .noteOperation(AppOpsManager.strOpToOp(op), uid, packageName); 9056 } 9057 9058 @Override 9059 public String[] getPackagesForUid(int uid) { 9060 return mActivityManagerService.mContext.getPackageManager() 9061 .getPackagesForUid(uid); 9062 } 9063 9064 @Override 9065 public boolean isRuntimePermission(String permission) { 9066 try { 9067 PermissionInfo info = mActivityManagerService.mContext.getPackageManager() 9068 .getPermissionInfo(permission, 0); 9069 return (info.protectionLevel & PermissionInfo.PROTECTION_MASK_BASE) 9070 == PermissionInfo.PROTECTION_DANGEROUS; 9071 } catch (NameNotFoundException nnfe) { 9072 Slog.e(TAG, "No such permission: "+ permission, nnfe); 9073 } 9074 return false; 9075 } 9076 9077 @Override 9078 public int getPackageUid(String packageName, int flags) { 9079 try { 9080 return mActivityManagerService.mContext.getPackageManager() 9081 .getPackageUid(packageName, flags); 9082 } catch (NameNotFoundException nnfe) { 9083 return -1; 9084 } 9085 } 9086 } 9087 9088 class IntentFirewallInterface implements IntentFirewall.AMSInterface { 9089 @Override 9090 public int checkComponentPermission(String permission, int pid, int uid, 9091 int owningUid, boolean exported) { 9092 return ActivityManagerService.this.checkComponentPermission(permission, pid, uid, 9093 owningUid, exported); 9094 } 9095 9096 @Override 9097 public Object getAMSLock() { 9098 return ActivityManagerService.this; 9099 } 9100 } 9101 9102 int checkComponentPermission(String permission, int pid, int uid, 9103 int owningUid, boolean exported) { 9104 if (pid == MY_PID) { 9105 return PackageManager.PERMISSION_GRANTED; 9106 } 9107 return ActivityManager.checkComponentPermission(permission, uid, 9108 owningUid, exported); 9109 } 9110 9111 /** 9112 * As the only public entry point for permissions checking, this method 9113 * can enforce the semantic that requesting a check on a null global 9114 * permission is automatically denied. (Internally a null permission 9115 * string is used when calling {@link #checkComponentPermission} in cases 9116 * when only uid-based security is needed.) 9117 * 9118 * This can be called with or without the global lock held. 9119 */ 9120 @Override 9121 public int checkPermission(String permission, int pid, int uid) { 9122 if (permission == null) { 9123 return PackageManager.PERMISSION_DENIED; 9124 } 9125 return checkComponentPermission(permission, pid, uid, -1, true); 9126 } 9127 9128 @Override 9129 public int checkPermissionWithToken(String permission, int pid, int uid, IBinder callerToken) { 9130 if (permission == null) { 9131 return PackageManager.PERMISSION_DENIED; 9132 } 9133 9134 // We might be performing an operation on behalf of an indirect binder 9135 // invocation, e.g. via {@link #openContentUri}. Check and adjust the 9136 // client identity accordingly before proceeding. 9137 Identity tlsIdentity = sCallerIdentity.get(); 9138 if (tlsIdentity != null && tlsIdentity.token == callerToken) { 9139 Slog.d(TAG, "checkComponentPermission() adjusting {pid,uid} to {" 9140 + tlsIdentity.pid + "," + tlsIdentity.uid + "}"); 9141 uid = tlsIdentity.uid; 9142 pid = tlsIdentity.pid; 9143 } 9144 9145 return checkComponentPermission(permission, pid, uid, -1, true); 9146 } 9147 9148 /** 9149 * Binder IPC calls go through the public entry point. 9150 * This can be called with or without the global lock held. 9151 */ 9152 int checkCallingPermission(String permission) { 9153 return checkPermission(permission, 9154 Binder.getCallingPid(), 9155 UserHandle.getAppId(Binder.getCallingUid())); 9156 } 9157 9158 /** 9159 * This can be called with or without the global lock held. 9160 */ 9161 void enforceCallingPermission(String permission, String func) { 9162 if (checkCallingPermission(permission) 9163 == PackageManager.PERMISSION_GRANTED) { 9164 return; 9165 } 9166 9167 String msg = "Permission Denial: " + func + " from pid=" 9168 + Binder.getCallingPid() 9169 + ", uid=" + Binder.getCallingUid() 9170 + " requires " + permission; 9171 Slog.w(TAG, msg); 9172 throw new SecurityException(msg); 9173 } 9174 9175 /** 9176 * This can be called with or without the global lock held. 9177 */ 9178 void enforcePermission(String permission, int pid, int uid, String func) { 9179 if (checkPermission(permission, pid, uid) == PackageManager.PERMISSION_GRANTED) { 9180 return; 9181 } 9182 9183 String msg = "Permission Denial: " + func + " from pid=" + pid + ", uid=" + uid 9184 + " requires " + permission; 9185 Slog.w(TAG, msg); 9186 throw new SecurityException(msg); 9187 } 9188 9189 /** 9190 * This can be called with or without the global lock held. 9191 */ 9192 void enforceCallerIsRecentsOrHasPermission(String permission, String func) { 9193 if (!mRecentTasks.isCallerRecents(Binder.getCallingUid())) { 9194 enforceCallingPermission(permission, func); 9195 } 9196 } 9197 9198 /** 9199 * Determine if UID is holding permissions required to access {@link Uri} in 9200 * the given {@link ProviderInfo}. Final permission checking is always done 9201 * in {@link ContentProvider}. 9202 */ 9203 private final boolean checkHoldingPermissionsLocked( 9204 IPackageManager pm, ProviderInfo pi, GrantUri grantUri, int uid, final int modeFlags) { 9205 if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION, 9206 "checkHoldingPermissionsLocked: uri=" + grantUri + " uid=" + uid); 9207 if (UserHandle.getUserId(uid) != grantUri.sourceUserId) { 9208 if (ActivityManager.checkComponentPermission(INTERACT_ACROSS_USERS, uid, -1, true) 9209 != PERMISSION_GRANTED) { 9210 return false; 9211 } 9212 } 9213 return checkHoldingPermissionsInternalLocked(pm, pi, grantUri, uid, modeFlags, true); 9214 } 9215 9216 private final boolean checkHoldingPermissionsInternalLocked(IPackageManager pm, ProviderInfo pi, 9217 GrantUri grantUri, int uid, final int modeFlags, boolean considerUidPermissions) { 9218 if (pi.applicationInfo.uid == uid) { 9219 return true; 9220 } else if (!pi.exported) { 9221 return false; 9222 } 9223 9224 boolean readMet = (modeFlags & Intent.FLAG_GRANT_READ_URI_PERMISSION) == 0; 9225 boolean writeMet = (modeFlags & Intent.FLAG_GRANT_WRITE_URI_PERMISSION) == 0; 9226 try { 9227 // check if target holds top-level <provider> permissions 9228 if (!readMet && pi.readPermission != null && considerUidPermissions 9229 && (pm.checkUidPermission(pi.readPermission, uid) == PERMISSION_GRANTED)) { 9230 readMet = true; 9231 } 9232 if (!writeMet && pi.writePermission != null && considerUidPermissions 9233 && (pm.checkUidPermission(pi.writePermission, uid) == PERMISSION_GRANTED)) { 9234 writeMet = true; 9235 } 9236 9237 // track if unprotected read/write is allowed; any denied 9238 // <path-permission> below removes this ability 9239 boolean allowDefaultRead = pi.readPermission == null; 9240 boolean allowDefaultWrite = pi.writePermission == null; 9241 9242 // check if target holds any <path-permission> that match uri 9243 final PathPermission[] pps = pi.pathPermissions; 9244 if (pps != null) { 9245 final String path = grantUri.uri.getPath(); 9246 int i = pps.length; 9247 while (i > 0 && (!readMet || !writeMet)) { 9248 i--; 9249 PathPermission pp = pps[i]; 9250 if (pp.match(path)) { 9251 if (!readMet) { 9252 final String pprperm = pp.getReadPermission(); 9253 if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION, 9254 "Checking read perm for " + pprperm + " for " + pp.getPath() 9255 + ": match=" + pp.match(path) 9256 + " check=" + pm.checkUidPermission(pprperm, uid)); 9257 if (pprperm != null) { 9258 if (considerUidPermissions && pm.checkUidPermission(pprperm, uid) 9259 == PERMISSION_GRANTED) { 9260 readMet = true; 9261 } else { 9262 allowDefaultRead = false; 9263 } 9264 } 9265 } 9266 if (!writeMet) { 9267 final String ppwperm = pp.getWritePermission(); 9268 if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION, 9269 "Checking write perm " + ppwperm + " for " + pp.getPath() 9270 + ": match=" + pp.match(path) 9271 + " check=" + pm.checkUidPermission(ppwperm, uid)); 9272 if (ppwperm != null) { 9273 if (considerUidPermissions && pm.checkUidPermission(ppwperm, uid) 9274 == PERMISSION_GRANTED) { 9275 writeMet = true; 9276 } else { 9277 allowDefaultWrite = false; 9278 } 9279 } 9280 } 9281 } 9282 } 9283 } 9284 9285 // grant unprotected <provider> read/write, if not blocked by 9286 // <path-permission> above 9287 if (allowDefaultRead) readMet = true; 9288 if (allowDefaultWrite) writeMet = true; 9289 9290 } catch (RemoteException e) { 9291 return false; 9292 } 9293 9294 return readMet && writeMet; 9295 } 9296 9297 public boolean isAppStartModeDisabled(int uid, String packageName) { 9298 synchronized (this) { 9299 return getAppStartModeLocked(uid, packageName, 0, -1, false, true, false) 9300 == ActivityManager.APP_START_MODE_DISABLED; 9301 } 9302 } 9303 9304 // Unified app-op and target sdk check 9305 int appRestrictedInBackgroundLocked(int uid, String packageName, int packageTargetSdk) { 9306 // Apps that target O+ are always subject to background check 9307 if (packageTargetSdk >= Build.VERSION_CODES.O) { 9308 if (DEBUG_BACKGROUND_CHECK) { 9309 Slog.i(TAG, "App " + uid + "/" + packageName + " targets O+, restricted"); 9310 } 9311 return ActivityManager.APP_START_MODE_DELAYED_RIGID; 9312 } 9313 // ...and legacy apps get an AppOp check 9314 int appop = mAppOpsService.noteOperation(AppOpsManager.OP_RUN_IN_BACKGROUND, 9315 uid, packageName); 9316 if (DEBUG_BACKGROUND_CHECK) { 9317 Slog.i(TAG, "Legacy app " + uid + "/" + packageName + " bg appop " + appop); 9318 } 9319 switch (appop) { 9320 case AppOpsManager.MODE_ALLOWED: 9321 // If force-background-check is enabled, restrict all apps that aren't whitelisted. 9322 if (mForceBackgroundCheck && 9323 !UserHandle.isCore(uid) && 9324 !isOnDeviceIdleWhitelistLocked(uid, /*allowExceptIdleToo=*/ true)) { 9325 if (DEBUG_BACKGROUND_CHECK) { 9326 Slog.i(TAG, "Force background check: " + 9327 uid + "/" + packageName + " restricted"); 9328 } 9329 return ActivityManager.APP_START_MODE_DELAYED; 9330 } 9331 return ActivityManager.APP_START_MODE_NORMAL; 9332 case AppOpsManager.MODE_IGNORED: 9333 return ActivityManager.APP_START_MODE_DELAYED; 9334 default: 9335 return ActivityManager.APP_START_MODE_DELAYED_RIGID; 9336 } 9337 } 9338 9339 // Service launch is available to apps with run-in-background exemptions but 9340 // some other background operations are not. If we're doing a check 9341 // of service-launch policy, allow those callers to proceed unrestricted. 9342 int appServicesRestrictedInBackgroundLocked(int uid, String packageName, int packageTargetSdk) { 9343 // Persistent app? 9344 if (mPackageManagerInt.isPackagePersistent(packageName)) { 9345 if (DEBUG_BACKGROUND_CHECK) { 9346 Slog.i(TAG, "App " + uid + "/" + packageName 9347 + " is persistent; not restricted in background"); 9348 } 9349 return ActivityManager.APP_START_MODE_NORMAL; 9350 } 9351 9352 // Non-persistent but background whitelisted? 9353 if (uidOnBackgroundWhitelist(uid)) { 9354 if (DEBUG_BACKGROUND_CHECK) { 9355 Slog.i(TAG, "App " + uid + "/" + packageName 9356 + " on background whitelist; not restricted in background"); 9357 } 9358 return ActivityManager.APP_START_MODE_NORMAL; 9359 } 9360 9361 // Is this app on the battery whitelist? 9362 if (isOnDeviceIdleWhitelistLocked(uid, /*allowExceptIdleToo=*/ false)) { 9363 if (DEBUG_BACKGROUND_CHECK) { 9364 Slog.i(TAG, "App " + uid + "/" + packageName 9365 + " on idle whitelist; not restricted in background"); 9366 } 9367 return ActivityManager.APP_START_MODE_NORMAL; 9368 } 9369 9370 // None of the service-policy criteria apply, so we apply the common criteria 9371 return appRestrictedInBackgroundLocked(uid, packageName, packageTargetSdk); 9372 } 9373 9374 int getAppStartModeLocked(int uid, String packageName, int packageTargetSdk, 9375 int callingPid, boolean alwaysRestrict, boolean disabledOnly, boolean forcedStandby) { 9376 UidRecord uidRec = mActiveUids.get(uid); 9377 if (DEBUG_BACKGROUND_CHECK) Slog.d(TAG, "checkAllowBackground: uid=" + uid + " pkg=" 9378 + packageName + " rec=" + uidRec + " always=" + alwaysRestrict + " idle=" 9379 + (uidRec != null ? uidRec.idle : false)); 9380 if (uidRec == null || alwaysRestrict || forcedStandby || uidRec.idle) { 9381 boolean ephemeral; 9382 if (uidRec == null) { 9383 ephemeral = getPackageManagerInternalLocked().isPackageEphemeral( 9384 UserHandle.getUserId(uid), packageName); 9385 } else { 9386 ephemeral = uidRec.ephemeral; 9387 } 9388 9389 if (ephemeral) { 9390 // We are hard-core about ephemeral apps not running in the background. 9391 return ActivityManager.APP_START_MODE_DISABLED; 9392 } else { 9393 if (disabledOnly) { 9394 // The caller is only interested in whether app starts are completely 9395 // disabled for the given package (that is, it is an instant app). So 9396 // we don't need to go further, which is all just seeing if we should 9397 // apply a "delayed" mode for a regular app. 9398 return ActivityManager.APP_START_MODE_NORMAL; 9399 } 9400 final int startMode = (alwaysRestrict) 9401 ? appRestrictedInBackgroundLocked(uid, packageName, packageTargetSdk) 9402 : appServicesRestrictedInBackgroundLocked(uid, packageName, 9403 packageTargetSdk); 9404 if (DEBUG_BACKGROUND_CHECK) { 9405 Slog.d(TAG, "checkAllowBackground: uid=" + uid 9406 + " pkg=" + packageName + " startMode=" + startMode 9407 + " onwhitelist=" + isOnDeviceIdleWhitelistLocked(uid, false) 9408 + " onwhitelist(ei)=" + isOnDeviceIdleWhitelistLocked(uid, true)); 9409 } 9410 if (startMode == ActivityManager.APP_START_MODE_DELAYED) { 9411 // This is an old app that has been forced into a "compatible as possible" 9412 // mode of background check. To increase compatibility, we will allow other 9413 // foreground apps to cause its services to start. 9414 if (callingPid >= 0) { 9415 ProcessRecord proc; 9416 synchronized (mPidsSelfLocked) { 9417 proc = mPidsSelfLocked.get(callingPid); 9418 } 9419 if (proc != null && 9420 !ActivityManager.isProcStateBackground(proc.curProcState)) { 9421 // Whoever is instigating this is in the foreground, so we will allow it 9422 // to go through. 9423 return ActivityManager.APP_START_MODE_NORMAL; 9424 } 9425 } 9426 } 9427 return startMode; 9428 } 9429 } 9430 return ActivityManager.APP_START_MODE_NORMAL; 9431 } 9432 9433 /** 9434 * @return whether a UID is in the system, user or temp doze whitelist. 9435 */ 9436 boolean isOnDeviceIdleWhitelistLocked(int uid, boolean allowExceptIdleToo) { 9437 final int appId = UserHandle.getAppId(uid); 9438 9439 final int[] whitelist = allowExceptIdleToo 9440 ? mDeviceIdleExceptIdleWhitelist 9441 : mDeviceIdleWhitelist; 9442 9443 return Arrays.binarySearch(whitelist, appId) >= 0 9444 || Arrays.binarySearch(mDeviceIdleTempWhitelist, appId) >= 0 9445 || mPendingTempWhitelist.indexOfKey(uid) >= 0; 9446 } 9447 9448 private ProviderInfo getProviderInfoLocked(String authority, int userHandle, int pmFlags) { 9449 ProviderInfo pi = null; 9450 ContentProviderRecord cpr = mProviderMap.getProviderByName(authority, userHandle); 9451 if (cpr != null) { 9452 pi = cpr.info; 9453 } else { 9454 try { 9455 pi = AppGlobals.getPackageManager().resolveContentProvider( 9456 authority, PackageManager.GET_URI_PERMISSION_PATTERNS | pmFlags, 9457 userHandle); 9458 } catch (RemoteException ex) { 9459 } 9460 } 9461 return pi; 9462 } 9463 9464 void grantEphemeralAccessLocked(int userId, Intent intent, 9465 int targetAppId, int ephemeralAppId) { 9466 getPackageManagerInternalLocked(). 9467 grantEphemeralAccess(userId, intent, targetAppId, ephemeralAppId); 9468 } 9469 9470 @GuardedBy("this") 9471 private UriPermission findUriPermissionLocked(int targetUid, GrantUri grantUri) { 9472 final ArrayMap<GrantUri, UriPermission> targetUris = mGrantedUriPermissions.get(targetUid); 9473 if (targetUris != null) { 9474 return targetUris.get(grantUri); 9475 } 9476 return null; 9477 } 9478 9479 @GuardedBy("this") 9480 private UriPermission findOrCreateUriPermissionLocked(String sourcePkg, 9481 String targetPkg, int targetUid, GrantUri grantUri) { 9482 ArrayMap<GrantUri, UriPermission> targetUris = mGrantedUriPermissions.get(targetUid); 9483 if (targetUris == null) { 9484 targetUris = Maps.newArrayMap(); 9485 mGrantedUriPermissions.put(targetUid, targetUris); 9486 } 9487 9488 UriPermission perm = targetUris.get(grantUri); 9489 if (perm == null) { 9490 perm = new UriPermission(sourcePkg, targetPkg, targetUid, grantUri); 9491 targetUris.put(grantUri, perm); 9492 } 9493 9494 return perm; 9495 } 9496 9497 @GuardedBy("this") 9498 private final boolean checkUriPermissionLocked(GrantUri grantUri, int uid, 9499 final int modeFlags) { 9500 final boolean persistable = (modeFlags & Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION) != 0; 9501 final int minStrength = persistable ? UriPermission.STRENGTH_PERSISTABLE 9502 : UriPermission.STRENGTH_OWNED; 9503 9504 // Root gets to do everything. 9505 if (uid == 0) { 9506 return true; 9507 } 9508 9509 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get(uid); 9510 if (perms == null) return false; 9511 9512 // First look for exact match 9513 final UriPermission exactPerm = perms.get(grantUri); 9514 if (exactPerm != null && exactPerm.getStrength(modeFlags) >= minStrength) { 9515 return true; 9516 } 9517 9518 // No exact match, look for prefixes 9519 final int N = perms.size(); 9520 for (int i = 0; i < N; i++) { 9521 final UriPermission perm = perms.valueAt(i); 9522 if (perm.uri.prefix && grantUri.uri.isPathPrefixMatch(perm.uri.uri) 9523 && perm.getStrength(modeFlags) >= minStrength) { 9524 return true; 9525 } 9526 } 9527 9528 return false; 9529 } 9530 9531 /** 9532 * @param uri This uri must NOT contain an embedded userId. 9533 * @param userId The userId in which the uri is to be resolved. 9534 */ 9535 @Override 9536 public int checkUriPermission(Uri uri, int pid, int uid, 9537 final int modeFlags, int userId, IBinder callerToken) { 9538 enforceNotIsolatedCaller("checkUriPermission"); 9539 9540 // Another redirected-binder-call permissions check as in 9541 // {@link checkPermissionWithToken}. 9542 Identity tlsIdentity = sCallerIdentity.get(); 9543 if (tlsIdentity != null && tlsIdentity.token == callerToken) { 9544 uid = tlsIdentity.uid; 9545 pid = tlsIdentity.pid; 9546 } 9547 9548 // Our own process gets to do everything. 9549 if (pid == MY_PID) { 9550 return PackageManager.PERMISSION_GRANTED; 9551 } 9552 synchronized (this) { 9553 return checkUriPermissionLocked(new GrantUri(userId, uri, false), uid, modeFlags) 9554 ? PackageManager.PERMISSION_GRANTED 9555 : PackageManager.PERMISSION_DENIED; 9556 } 9557 } 9558 9559 /** 9560 * Check if the targetPkg can be granted permission to access uri by 9561 * the callingUid using the given modeFlags. Throws a security exception 9562 * if callingUid is not allowed to do this. Returns the uid of the target 9563 * if the URI permission grant should be performed; returns -1 if it is not 9564 * needed (for example targetPkg already has permission to access the URI). 9565 * If you already know the uid of the target, you can supply it in 9566 * lastTargetUid else set that to -1. 9567 */ 9568 @GuardedBy("this") 9569 int checkGrantUriPermissionLocked(int callingUid, String targetPkg, GrantUri grantUri, 9570 final int modeFlags, int lastTargetUid) { 9571 if (!Intent.isAccessUriMode(modeFlags)) { 9572 return -1; 9573 } 9574 9575 if (targetPkg != null) { 9576 if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION, 9577 "Checking grant " + targetPkg + " permission to " + grantUri); 9578 } 9579 9580 final IPackageManager pm = AppGlobals.getPackageManager(); 9581 9582 // If this is not a content: uri, we can't do anything with it. 9583 if (!ContentResolver.SCHEME_CONTENT.equals(grantUri.uri.getScheme())) { 9584 if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION, 9585 "Can't grant URI permission for non-content URI: " + grantUri); 9586 return -1; 9587 } 9588 9589 // Bail early if system is trying to hand out permissions directly; it 9590 // must always grant permissions on behalf of someone explicit. 9591 final int callingAppId = UserHandle.getAppId(callingUid); 9592 if ((callingAppId == SYSTEM_UID) || (callingAppId == ROOT_UID)) { 9593 if ("com.android.settings.files".equals(grantUri.uri.getAuthority())) { 9594 // Exempted authority for 9595 // 1. cropping user photos and sharing a generated license html 9596 // file in Settings app 9597 // 2. sharing a generated license html file in TvSettings app 9598 } else { 9599 Slog.w(TAG, "For security reasons, the system cannot issue a Uri permission" 9600 + " grant to " + grantUri + "; use startActivityAsCaller() instead"); 9601 return -1; 9602 } 9603 } 9604 9605 final String authority = grantUri.uri.getAuthority(); 9606 final ProviderInfo pi = getProviderInfoLocked(authority, grantUri.sourceUserId, 9607 MATCH_DEBUG_TRIAGED_MISSING); 9608 if (pi == null) { 9609 Slog.w(TAG, "No content provider found for permission check: " + 9610 grantUri.uri.toSafeString()); 9611 return -1; 9612 } 9613 9614 int targetUid = lastTargetUid; 9615 if (targetUid < 0 && targetPkg != null) { 9616 try { 9617 targetUid = pm.getPackageUid(targetPkg, MATCH_DEBUG_TRIAGED_MISSING, 9618 UserHandle.getUserId(callingUid)); 9619 if (targetUid < 0) { 9620 if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION, 9621 "Can't grant URI permission no uid for: " + targetPkg); 9622 return -1; 9623 } 9624 } catch (RemoteException ex) { 9625 return -1; 9626 } 9627 } 9628 9629 // If we're extending a persistable grant, then we always need to create 9630 // the grant data structure so that take/release APIs work 9631 if ((modeFlags & Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION) != 0) { 9632 return targetUid; 9633 } 9634 9635 if (targetUid >= 0) { 9636 // First... does the target actually need this permission? 9637 if (checkHoldingPermissionsLocked(pm, pi, grantUri, targetUid, modeFlags)) { 9638 // No need to grant the target this permission. 9639 if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION, 9640 "Target " + targetPkg + " already has full permission to " + grantUri); 9641 return -1; 9642 } 9643 } else { 9644 // First... there is no target package, so can anyone access it? 9645 boolean allowed = pi.exported; 9646 if ((modeFlags&Intent.FLAG_GRANT_READ_URI_PERMISSION) != 0) { 9647 if (pi.readPermission != null) { 9648 allowed = false; 9649 } 9650 } 9651 if ((modeFlags&Intent.FLAG_GRANT_WRITE_URI_PERMISSION) != 0) { 9652 if (pi.writePermission != null) { 9653 allowed = false; 9654 } 9655 } 9656 if (pi.pathPermissions != null) { 9657 final int N = pi.pathPermissions.length; 9658 for (int i=0; i<N; i++) { 9659 if (pi.pathPermissions[i] != null 9660 && pi.pathPermissions[i].match(grantUri.uri.getPath())) { 9661 if ((modeFlags&Intent.FLAG_GRANT_READ_URI_PERMISSION) != 0) { 9662 if (pi.pathPermissions[i].getReadPermission() != null) { 9663 allowed = false; 9664 } 9665 } 9666 if ((modeFlags&Intent.FLAG_GRANT_WRITE_URI_PERMISSION) != 0) { 9667 if (pi.pathPermissions[i].getWritePermission() != null) { 9668 allowed = false; 9669 } 9670 } 9671 break; 9672 } 9673 } 9674 } 9675 if (allowed) { 9676 return -1; 9677 } 9678 } 9679 9680 /* There is a special cross user grant if: 9681 * - The target is on another user. 9682 * - Apps on the current user can access the uri without any uid permissions. 9683 * In this case, we grant a uri permission, even if the ContentProvider does not normally 9684 * grant uri permissions. 9685 */ 9686 boolean specialCrossUserGrant = UserHandle.getUserId(targetUid) != grantUri.sourceUserId 9687 && checkHoldingPermissionsInternalLocked(pm, pi, grantUri, callingUid, 9688 modeFlags, false /*without considering the uid permissions*/); 9689 9690 // Second... is the provider allowing granting of URI permissions? 9691 if (!specialCrossUserGrant) { 9692 if (!pi.grantUriPermissions) { 9693 throw new SecurityException("Provider " + pi.packageName 9694 + "/" + pi.name 9695 + " does not allow granting of Uri permissions (uri " 9696 + grantUri + ")"); 9697 } 9698 if (pi.uriPermissionPatterns != null) { 9699 final int N = pi.uriPermissionPatterns.length; 9700 boolean allowed = false; 9701 for (int i=0; i<N; i++) { 9702 if (pi.uriPermissionPatterns[i] != null 9703 && pi.uriPermissionPatterns[i].match(grantUri.uri.getPath())) { 9704 allowed = true; 9705 break; 9706 } 9707 } 9708 if (!allowed) { 9709 throw new SecurityException("Provider " + pi.packageName 9710 + "/" + pi.name 9711 + " does not allow granting of permission to path of Uri " 9712 + grantUri); 9713 } 9714 } 9715 } 9716 9717 // Third... does the caller itself have permission to access 9718 // this uri? 9719 if (!checkHoldingPermissionsLocked(pm, pi, grantUri, callingUid, modeFlags)) { 9720 // Require they hold a strong enough Uri permission 9721 if (!checkUriPermissionLocked(grantUri, callingUid, modeFlags)) { 9722 if (android.Manifest.permission.MANAGE_DOCUMENTS.equals(pi.readPermission)) { 9723 throw new SecurityException( 9724 "UID " + callingUid + " does not have permission to " + grantUri 9725 + "; you could obtain access using ACTION_OPEN_DOCUMENT " 9726 + "or related APIs"); 9727 } else { 9728 throw new SecurityException( 9729 "UID " + callingUid + " does not have permission to " + grantUri); 9730 } 9731 } 9732 } 9733 return targetUid; 9734 } 9735 9736 /** 9737 * @param uri This uri must NOT contain an embedded userId. 9738 * @param userId The userId in which the uri is to be resolved. 9739 */ 9740 @Override 9741 public int checkGrantUriPermission(int callingUid, String targetPkg, Uri uri, 9742 final int modeFlags, int userId) { 9743 enforceNotIsolatedCaller("checkGrantUriPermission"); 9744 synchronized(this) { 9745 return checkGrantUriPermissionLocked(callingUid, targetPkg, 9746 new GrantUri(userId, uri, false), modeFlags, -1); 9747 } 9748 } 9749 9750 @GuardedBy("this") 9751 void grantUriPermissionUncheckedLocked(int targetUid, String targetPkg, GrantUri grantUri, 9752 final int modeFlags, UriPermissionOwner owner) { 9753 if (!Intent.isAccessUriMode(modeFlags)) { 9754 return; 9755 } 9756 9757 // So here we are: the caller has the assumed permission 9758 // to the uri, and the target doesn't. Let's now give this to 9759 // the target. 9760 9761 if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION, 9762 "Granting " + targetPkg + "/" + targetUid + " permission to " + grantUri); 9763 9764 final String authority = grantUri.uri.getAuthority(); 9765 final ProviderInfo pi = getProviderInfoLocked(authority, grantUri.sourceUserId, 9766 MATCH_DEBUG_TRIAGED_MISSING); 9767 if (pi == null) { 9768 Slog.w(TAG, "No content provider found for grant: " + grantUri.toSafeString()); 9769 return; 9770 } 9771 9772 if ((modeFlags & Intent.FLAG_GRANT_PREFIX_URI_PERMISSION) != 0) { 9773 grantUri.prefix = true; 9774 } 9775 final UriPermission perm = findOrCreateUriPermissionLocked( 9776 pi.packageName, targetPkg, targetUid, grantUri); 9777 perm.grantModes(modeFlags, owner); 9778 } 9779 9780 @GuardedBy("this") 9781 void grantUriPermissionLocked(int callingUid, String targetPkg, GrantUri grantUri, 9782 final int modeFlags, UriPermissionOwner owner, int targetUserId) { 9783 if (targetPkg == null) { 9784 throw new NullPointerException("targetPkg"); 9785 } 9786 int targetUid; 9787 final IPackageManager pm = AppGlobals.getPackageManager(); 9788 try { 9789 targetUid = pm.getPackageUid(targetPkg, MATCH_DEBUG_TRIAGED_MISSING, targetUserId); 9790 } catch (RemoteException ex) { 9791 return; 9792 } 9793 9794 targetUid = checkGrantUriPermissionLocked(callingUid, targetPkg, grantUri, modeFlags, 9795 targetUid); 9796 if (targetUid < 0) { 9797 return; 9798 } 9799 9800 grantUriPermissionUncheckedLocked(targetUid, targetPkg, grantUri, modeFlags, 9801 owner); 9802 } 9803 9804 static class NeededUriGrants extends ArrayList<GrantUri> { 9805 final String targetPkg; 9806 final int targetUid; 9807 final int flags; 9808 9809 NeededUriGrants(String targetPkg, int targetUid, int flags) { 9810 this.targetPkg = targetPkg; 9811 this.targetUid = targetUid; 9812 this.flags = flags; 9813 } 9814 9815 void writeToProto(ProtoOutputStream proto, long fieldId) { 9816 long token = proto.start(fieldId); 9817 proto.write(NeededUriGrantsProto.TARGET_PACKAGE, targetPkg); 9818 proto.write(NeededUriGrantsProto.TARGET_UID, targetUid); 9819 proto.write(NeededUriGrantsProto.FLAGS, flags); 9820 9821 final int N = this.size(); 9822 for (int i=0; i<N; i++) { 9823 this.get(i).writeToProto(proto, NeededUriGrantsProto.GRANTS); 9824 } 9825 proto.end(token); 9826 } 9827 } 9828 9829 /** 9830 * Like checkGrantUriPermissionLocked, but takes an Intent. 9831 */ 9832 @GuardedBy("this") 9833 NeededUriGrants checkGrantUriPermissionFromIntentLocked(int callingUid, 9834 String targetPkg, Intent intent, int mode, NeededUriGrants needed, int targetUserId) { 9835 if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION, 9836 "Checking URI perm to data=" + (intent != null ? intent.getData() : null) 9837 + " clip=" + (intent != null ? intent.getClipData() : null) 9838 + " from " + intent + "; flags=0x" 9839 + Integer.toHexString(intent != null ? intent.getFlags() : 0)); 9840 9841 if (targetPkg == null) { 9842 throw new NullPointerException("targetPkg"); 9843 } 9844 9845 if (intent == null) { 9846 return null; 9847 } 9848 Uri data = intent.getData(); 9849 ClipData clip = intent.getClipData(); 9850 if (data == null && clip == null) { 9851 return null; 9852 } 9853 // Default userId for uris in the intent (if they don't specify it themselves) 9854 int contentUserHint = intent.getContentUserHint(); 9855 if (contentUserHint == UserHandle.USER_CURRENT) { 9856 contentUserHint = UserHandle.getUserId(callingUid); 9857 } 9858 final IPackageManager pm = AppGlobals.getPackageManager(); 9859 int targetUid; 9860 if (needed != null) { 9861 targetUid = needed.targetUid; 9862 } else { 9863 try { 9864 targetUid = pm.getPackageUid(targetPkg, MATCH_DEBUG_TRIAGED_MISSING, 9865 targetUserId); 9866 } catch (RemoteException ex) { 9867 return null; 9868 } 9869 if (targetUid < 0) { 9870 if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION, 9871 "Can't grant URI permission no uid for: " + targetPkg 9872 + " on user " + targetUserId); 9873 return null; 9874 } 9875 } 9876 if (data != null) { 9877 GrantUri grantUri = GrantUri.resolve(contentUserHint, data); 9878 targetUid = checkGrantUriPermissionLocked(callingUid, targetPkg, grantUri, mode, 9879 targetUid); 9880 if (targetUid > 0) { 9881 if (needed == null) { 9882 needed = new NeededUriGrants(targetPkg, targetUid, mode); 9883 } 9884 needed.add(grantUri); 9885 } 9886 } 9887 if (clip != null) { 9888 for (int i=0; i<clip.getItemCount(); i++) { 9889 Uri uri = clip.getItemAt(i).getUri(); 9890 if (uri != null) { 9891 GrantUri grantUri = GrantUri.resolve(contentUserHint, uri); 9892 targetUid = checkGrantUriPermissionLocked(callingUid, targetPkg, grantUri, mode, 9893 targetUid); 9894 if (targetUid > 0) { 9895 if (needed == null) { 9896 needed = new NeededUriGrants(targetPkg, targetUid, mode); 9897 } 9898 needed.add(grantUri); 9899 } 9900 } else { 9901 Intent clipIntent = clip.getItemAt(i).getIntent(); 9902 if (clipIntent != null) { 9903 NeededUriGrants newNeeded = checkGrantUriPermissionFromIntentLocked( 9904 callingUid, targetPkg, clipIntent, mode, needed, targetUserId); 9905 if (newNeeded != null) { 9906 needed = newNeeded; 9907 } 9908 } 9909 } 9910 } 9911 } 9912 9913 return needed; 9914 } 9915 9916 /** 9917 * Like grantUriPermissionUncheckedLocked, but takes an Intent. 9918 */ 9919 @GuardedBy("this") 9920 void grantUriPermissionUncheckedFromIntentLocked(NeededUriGrants needed, 9921 UriPermissionOwner owner) { 9922 if (needed != null) { 9923 for (int i=0; i<needed.size(); i++) { 9924 GrantUri grantUri = needed.get(i); 9925 grantUriPermissionUncheckedLocked(needed.targetUid, needed.targetPkg, 9926 grantUri, needed.flags, owner); 9927 } 9928 } 9929 } 9930 9931 @GuardedBy("this") 9932 void grantUriPermissionFromIntentLocked(int callingUid, 9933 String targetPkg, Intent intent, UriPermissionOwner owner, int targetUserId) { 9934 NeededUriGrants needed = checkGrantUriPermissionFromIntentLocked(callingUid, targetPkg, 9935 intent, intent != null ? intent.getFlags() : 0, null, targetUserId); 9936 if (needed == null) { 9937 return; 9938 } 9939 9940 grantUriPermissionUncheckedFromIntentLocked(needed, owner); 9941 } 9942 9943 /** 9944 * @param uri This uri must NOT contain an embedded userId. 9945 * @param userId The userId in which the uri is to be resolved. 9946 */ 9947 @Override 9948 public void grantUriPermission(IApplicationThread caller, String targetPkg, Uri uri, 9949 final int modeFlags, int userId) { 9950 enforceNotIsolatedCaller("grantUriPermission"); 9951 GrantUri grantUri = new GrantUri(userId, uri, false); 9952 synchronized(this) { 9953 final ProcessRecord r = getRecordForAppLocked(caller); 9954 if (r == null) { 9955 throw new SecurityException("Unable to find app for caller " 9956 + caller 9957 + " when granting permission to uri " + grantUri); 9958 } 9959 if (targetPkg == null) { 9960 throw new IllegalArgumentException("null target"); 9961 } 9962 if (grantUri == null) { 9963 throw new IllegalArgumentException("null uri"); 9964 } 9965 9966 Preconditions.checkFlagsArgument(modeFlags, Intent.FLAG_GRANT_READ_URI_PERMISSION 9967 | Intent.FLAG_GRANT_WRITE_URI_PERMISSION 9968 | Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION 9969 | Intent.FLAG_GRANT_PREFIX_URI_PERMISSION); 9970 9971 grantUriPermissionLocked(r.uid, targetPkg, grantUri, modeFlags, null, 9972 UserHandle.getUserId(r.uid)); 9973 } 9974 } 9975 9976 @GuardedBy("this") 9977 void removeUriPermissionIfNeededLocked(UriPermission perm) { 9978 if (perm.modeFlags == 0) { 9979 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get( 9980 perm.targetUid); 9981 if (perms != null) { 9982 if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION, 9983 "Removing " + perm.targetUid + " permission to " + perm.uri); 9984 9985 perms.remove(perm.uri); 9986 if (perms.isEmpty()) { 9987 mGrantedUriPermissions.remove(perm.targetUid); 9988 } 9989 } 9990 } 9991 } 9992 9993 @GuardedBy("this") 9994 private void revokeUriPermissionLocked(String targetPackage, int callingUid, GrantUri grantUri, 9995 final int modeFlags) { 9996 if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION, 9997 "Revoking all granted permissions to " + grantUri); 9998 9999 final IPackageManager pm = AppGlobals.getPackageManager(); 10000 final String authority = grantUri.uri.getAuthority(); 10001 final ProviderInfo pi = getProviderInfoLocked(authority, grantUri.sourceUserId, 10002 MATCH_DIRECT_BOOT_AWARE | MATCH_DIRECT_BOOT_UNAWARE); 10003 if (pi == null) { 10004 Slog.w(TAG, "No content provider found for permission revoke: " 10005 + grantUri.toSafeString()); 10006 return; 10007 } 10008 10009 // Does the caller have this permission on the URI? 10010 if (!checkHoldingPermissionsLocked(pm, pi, grantUri, callingUid, modeFlags)) { 10011 // If they don't have direct access to the URI, then revoke any 10012 // ownerless URI permissions that have been granted to them. 10013 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get(callingUid); 10014 if (perms != null) { 10015 boolean persistChanged = false; 10016 for (int i = perms.size()-1; i >= 0; i--) { 10017 final UriPermission perm = perms.valueAt(i); 10018 if (targetPackage != null && !targetPackage.equals(perm.targetPkg)) { 10019 continue; 10020 } 10021 if (perm.uri.sourceUserId == grantUri.sourceUserId 10022 && perm.uri.uri.isPathPrefixMatch(grantUri.uri)) { 10023 if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION, 10024 "Revoking non-owned " + perm.targetUid 10025 + " permission to " + perm.uri); 10026 persistChanged |= perm.revokeModes( 10027 modeFlags | Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION, false); 10028 if (perm.modeFlags == 0) { 10029 perms.removeAt(i); 10030 } 10031 } 10032 } 10033 if (perms.isEmpty()) { 10034 mGrantedUriPermissions.remove(callingUid); 10035 } 10036 if (persistChanged) { 10037 schedulePersistUriGrants(); 10038 } 10039 } 10040 return; 10041 } 10042 10043 boolean persistChanged = false; 10044 10045 // Go through all of the permissions and remove any that match. 10046 for (int i = mGrantedUriPermissions.size()-1; i >= 0; i--) { 10047 final int targetUid = mGrantedUriPermissions.keyAt(i); 10048 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i); 10049 10050 for (int j = perms.size()-1; j >= 0; j--) { 10051 final UriPermission perm = perms.valueAt(j); 10052 if (targetPackage != null && !targetPackage.equals(perm.targetPkg)) { 10053 continue; 10054 } 10055 if (perm.uri.sourceUserId == grantUri.sourceUserId 10056 && perm.uri.uri.isPathPrefixMatch(grantUri.uri)) { 10057 if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION, 10058 "Revoking " + perm.targetUid + " permission to " + perm.uri); 10059 persistChanged |= perm.revokeModes( 10060 modeFlags | Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION, 10061 targetPackage == null); 10062 if (perm.modeFlags == 0) { 10063 perms.removeAt(j); 10064 } 10065 } 10066 } 10067 10068 if (perms.isEmpty()) { 10069 mGrantedUriPermissions.removeAt(i); 10070 } 10071 } 10072 10073 if (persistChanged) { 10074 schedulePersistUriGrants(); 10075 } 10076 } 10077 10078 /** 10079 * @param uri This uri must NOT contain an embedded userId. 10080 * @param userId The userId in which the uri is to be resolved. 10081 */ 10082 @Override 10083 public void revokeUriPermission(IApplicationThread caller, String targetPackage, Uri uri, 10084 final int modeFlags, int userId) { 10085 enforceNotIsolatedCaller("revokeUriPermission"); 10086 synchronized(this) { 10087 final ProcessRecord r = getRecordForAppLocked(caller); 10088 if (r == null) { 10089 throw new SecurityException("Unable to find app for caller " 10090 + caller 10091 + " when revoking permission to uri " + uri); 10092 } 10093 if (uri == null) { 10094 Slog.w(TAG, "revokeUriPermission: null uri"); 10095 return; 10096 } 10097 10098 if (!Intent.isAccessUriMode(modeFlags)) { 10099 return; 10100 } 10101 10102 final String authority = uri.getAuthority(); 10103 final ProviderInfo pi = getProviderInfoLocked(authority, userId, 10104 MATCH_DIRECT_BOOT_AWARE | MATCH_DIRECT_BOOT_UNAWARE); 10105 if (pi == null) { 10106 Slog.w(TAG, "No content provider found for permission revoke: " 10107 + uri.toSafeString()); 10108 return; 10109 } 10110 10111 revokeUriPermissionLocked(targetPackage, r.uid, new GrantUri(userId, uri, false), 10112 modeFlags); 10113 } 10114 } 10115 10116 /** 10117 * Remove any {@link UriPermission} granted <em>from</em> or <em>to</em> the 10118 * given package. 10119 * 10120 * @param packageName Package name to match, or {@code null} to apply to all 10121 * packages. 10122 * @param userHandle User to match, or {@link UserHandle#USER_ALL} to apply 10123 * to all users. 10124 * @param persistable If persistable grants should be removed. 10125 * @param targetOnly When {@code true}, only remove permissions where the app is the target, 10126 * not source. 10127 */ 10128 @GuardedBy("this") 10129 private void removeUriPermissionsForPackageLocked( 10130 String packageName, int userHandle, boolean persistable, boolean targetOnly) { 10131 if (userHandle == UserHandle.USER_ALL && packageName == null) { 10132 throw new IllegalArgumentException("Must narrow by either package or user"); 10133 } 10134 10135 boolean persistChanged = false; 10136 10137 int N = mGrantedUriPermissions.size(); 10138 for (int i = 0; i < N; i++) { 10139 final int targetUid = mGrantedUriPermissions.keyAt(i); 10140 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i); 10141 10142 // Only inspect grants matching user 10143 if (userHandle == UserHandle.USER_ALL 10144 || userHandle == UserHandle.getUserId(targetUid)) { 10145 for (Iterator<UriPermission> it = perms.values().iterator(); it.hasNext();) { 10146 final UriPermission perm = it.next(); 10147 10148 // Only inspect grants matching package 10149 if (packageName == null || (!targetOnly && perm.sourcePkg.equals(packageName)) 10150 || perm.targetPkg.equals(packageName)) { 10151 // Hacky solution as part of fixing a security bug; ignore 10152 // grants associated with DownloadManager so we don't have 10153 // to immediately launch it to regrant the permissions 10154 if (Downloads.Impl.AUTHORITY.equals(perm.uri.uri.getAuthority()) 10155 && !persistable) continue; 10156 10157 persistChanged |= perm.revokeModes(persistable 10158 ? ~0 : ~Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION, true); 10159 10160 // Only remove when no modes remain; any persisted grants 10161 // will keep this alive. 10162 if (perm.modeFlags == 0) { 10163 it.remove(); 10164 } 10165 } 10166 } 10167 10168 if (perms.isEmpty()) { 10169 mGrantedUriPermissions.remove(targetUid); 10170 N--; 10171 i--; 10172 } 10173 } 10174 } 10175 10176 if (persistChanged) { 10177 schedulePersistUriGrants(); 10178 } 10179 } 10180 10181 @Override 10182 public IBinder newUriPermissionOwner(String name) { 10183 enforceNotIsolatedCaller("newUriPermissionOwner"); 10184 synchronized(this) { 10185 UriPermissionOwner owner = new UriPermissionOwner(this, name); 10186 return owner.getExternalTokenLocked(); 10187 } 10188 } 10189 10190 @Override 10191 public IBinder getUriPermissionOwnerForActivity(IBinder activityToken) { 10192 enforceNotIsolatedCaller("getUriPermissionOwnerForActivity"); 10193 synchronized(this) { 10194 ActivityRecord r = ActivityRecord.isInStackLocked(activityToken); 10195 if (r == null) { 10196 throw new IllegalArgumentException("Activity does not exist; token=" 10197 + activityToken); 10198 } 10199 return r.getUriPermissionsLocked().getExternalTokenLocked(); 10200 } 10201 } 10202 /** 10203 * @param uri This uri must NOT contain an embedded userId. 10204 * @param sourceUserId The userId in which the uri is to be resolved. 10205 * @param targetUserId The userId of the app that receives the grant. 10206 */ 10207 @Override 10208 public void grantUriPermissionFromOwner(IBinder token, int fromUid, String targetPkg, Uri uri, 10209 final int modeFlags, int sourceUserId, int targetUserId) { 10210 targetUserId = mUserController.handleIncomingUser(Binder.getCallingPid(), 10211 Binder.getCallingUid(), targetUserId, false, ALLOW_FULL_ONLY, 10212 "grantUriPermissionFromOwner", null); 10213 synchronized(this) { 10214 UriPermissionOwner owner = UriPermissionOwner.fromExternalToken(token); 10215 if (owner == null) { 10216 throw new IllegalArgumentException("Unknown owner: " + token); 10217 } 10218 if (fromUid != Binder.getCallingUid()) { 10219 if (Binder.getCallingUid() != myUid()) { 10220 // Only system code can grant URI permissions on behalf 10221 // of other users. 10222 throw new SecurityException("nice try"); 10223 } 10224 } 10225 if (targetPkg == null) { 10226 throw new IllegalArgumentException("null target"); 10227 } 10228 if (uri == null) { 10229 throw new IllegalArgumentException("null uri"); 10230 } 10231 10232 grantUriPermissionLocked(fromUid, targetPkg, new GrantUri(sourceUserId, uri, false), 10233 modeFlags, owner, targetUserId); 10234 } 10235 } 10236 10237 /** 10238 * @param uri This uri must NOT contain an embedded userId. 10239 * @param userId The userId in which the uri is to be resolved. 10240 */ 10241 @Override 10242 public void revokeUriPermissionFromOwner(IBinder token, Uri uri, int mode, int userId) { 10243 synchronized(this) { 10244 UriPermissionOwner owner = UriPermissionOwner.fromExternalToken(token); 10245 if (owner == null) { 10246 throw new IllegalArgumentException("Unknown owner: " + token); 10247 } 10248 10249 if (uri == null) { 10250 owner.removeUriPermissionsLocked(mode); 10251 } else { 10252 final boolean prefix = (mode & Intent.FLAG_GRANT_PREFIX_URI_PERMISSION) != 0; 10253 owner.removeUriPermissionLocked(new GrantUri(userId, uri, prefix), mode); 10254 } 10255 } 10256 } 10257 10258 private void schedulePersistUriGrants() { 10259 if (!mHandler.hasMessages(PERSIST_URI_GRANTS_MSG)) { 10260 mHandler.sendMessageDelayed(mHandler.obtainMessage(PERSIST_URI_GRANTS_MSG), 10261 10 * DateUtils.SECOND_IN_MILLIS); 10262 } 10263 } 10264 10265 private void writeGrantedUriPermissions() { 10266 if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION, "writeGrantedUriPermissions()"); 10267 10268 final long startTime = SystemClock.uptimeMillis(); 10269 10270 // Snapshot permissions so we can persist without lock 10271 ArrayList<UriPermission.Snapshot> persist = Lists.newArrayList(); 10272 synchronized (this) { 10273 final int size = mGrantedUriPermissions.size(); 10274 for (int i = 0; i < size; i++) { 10275 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i); 10276 for (UriPermission perm : perms.values()) { 10277 if (perm.persistedModeFlags != 0) { 10278 persist.add(perm.snapshot()); 10279 } 10280 } 10281 } 10282 } 10283 10284 FileOutputStream fos = null; 10285 try { 10286 fos = mGrantFile.startWrite(startTime); 10287 10288 XmlSerializer out = new FastXmlSerializer(); 10289 out.setOutput(fos, StandardCharsets.UTF_8.name()); 10290 out.startDocument(null, true); 10291 out.startTag(null, TAG_URI_GRANTS); 10292 for (UriPermission.Snapshot perm : persist) { 10293 out.startTag(null, TAG_URI_GRANT); 10294 writeIntAttribute(out, ATTR_SOURCE_USER_ID, perm.uri.sourceUserId); 10295 writeIntAttribute(out, ATTR_TARGET_USER_ID, perm.targetUserId); 10296 out.attribute(null, ATTR_SOURCE_PKG, perm.sourcePkg); 10297 out.attribute(null, ATTR_TARGET_PKG, perm.targetPkg); 10298 out.attribute(null, ATTR_URI, String.valueOf(perm.uri.uri)); 10299 writeBooleanAttribute(out, ATTR_PREFIX, perm.uri.prefix); 10300 writeIntAttribute(out, ATTR_MODE_FLAGS, perm.persistedModeFlags); 10301 writeLongAttribute(out, ATTR_CREATED_TIME, perm.persistedCreateTime); 10302 out.endTag(null, TAG_URI_GRANT); 10303 } 10304 out.endTag(null, TAG_URI_GRANTS); 10305 out.endDocument(); 10306 10307 mGrantFile.finishWrite(fos); 10308 } catch (IOException e) { 10309 if (fos != null) { 10310 mGrantFile.failWrite(fos); 10311 } 10312 } 10313 } 10314 10315 @GuardedBy("this") 10316 private void readGrantedUriPermissionsLocked() { 10317 if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION, "readGrantedUriPermissions()"); 10318 10319 final long now = System.currentTimeMillis(); 10320 10321 FileInputStream fis = null; 10322 try { 10323 fis = mGrantFile.openRead(); 10324 final XmlPullParser in = Xml.newPullParser(); 10325 in.setInput(fis, StandardCharsets.UTF_8.name()); 10326 10327 int type; 10328 while ((type = in.next()) != END_DOCUMENT) { 10329 final String tag = in.getName(); 10330 if (type == START_TAG) { 10331 if (TAG_URI_GRANT.equals(tag)) { 10332 final int sourceUserId; 10333 final int targetUserId; 10334 final int userHandle = readIntAttribute(in, 10335 ATTR_USER_HANDLE, UserHandle.USER_NULL); 10336 if (userHandle != UserHandle.USER_NULL) { 10337 // For backwards compatibility. 10338 sourceUserId = userHandle; 10339 targetUserId = userHandle; 10340 } else { 10341 sourceUserId = readIntAttribute(in, ATTR_SOURCE_USER_ID); 10342 targetUserId = readIntAttribute(in, ATTR_TARGET_USER_ID); 10343 } 10344 final String sourcePkg = in.getAttributeValue(null, ATTR_SOURCE_PKG); 10345 final String targetPkg = in.getAttributeValue(null, ATTR_TARGET_PKG); 10346 final Uri uri = Uri.parse(in.getAttributeValue(null, ATTR_URI)); 10347 final boolean prefix = readBooleanAttribute(in, ATTR_PREFIX); 10348 final int modeFlags = readIntAttribute(in, ATTR_MODE_FLAGS); 10349 final long createdTime = readLongAttribute(in, ATTR_CREATED_TIME, now); 10350 10351 // Sanity check that provider still belongs to source package 10352 // Both direct boot aware and unaware packages are fine as we 10353 // will do filtering at query time to avoid multiple parsing. 10354 final ProviderInfo pi = getProviderInfoLocked( 10355 uri.getAuthority(), sourceUserId, MATCH_DIRECT_BOOT_AWARE 10356 | MATCH_DIRECT_BOOT_UNAWARE); 10357 if (pi != null && sourcePkg.equals(pi.packageName)) { 10358 int targetUid = -1; 10359 try { 10360 targetUid = AppGlobals.getPackageManager().getPackageUid( 10361 targetPkg, MATCH_UNINSTALLED_PACKAGES, targetUserId); 10362 } catch (RemoteException e) { 10363 } 10364 if (targetUid != -1) { 10365 final UriPermission perm = findOrCreateUriPermissionLocked( 10366 sourcePkg, targetPkg, targetUid, 10367 new GrantUri(sourceUserId, uri, prefix)); 10368 perm.initPersistedModes(modeFlags, createdTime); 10369 } 10370 } else { 10371 Slog.w(TAG, "Persisted grant for " + uri + " had source " + sourcePkg 10372 + " but instead found " + pi); 10373 } 10374 } 10375 } 10376 } 10377 } catch (FileNotFoundException e) { 10378 // Missing grants is okay 10379 } catch (IOException e) { 10380 Slog.wtf(TAG, "Failed reading Uri grants", e); 10381 } catch (XmlPullParserException e) { 10382 Slog.wtf(TAG, "Failed reading Uri grants", e); 10383 } finally { 10384 IoUtils.closeQuietly(fis); 10385 } 10386 } 10387 10388 /** 10389 * @param uri This uri must NOT contain an embedded userId. 10390 * @param toPackage Name of package whose uri is being granted to (if {@code null}, uses 10391 * calling uid) 10392 * @param userId The userId in which the uri is to be resolved. 10393 */ 10394 @Override 10395 public void takePersistableUriPermission(Uri uri, final int modeFlags, 10396 @Nullable String toPackage, int userId) { 10397 final int uid; 10398 if (toPackage != null) { 10399 enforceCallingPermission(android.Manifest.permission.FORCE_PERSISTABLE_URI_PERMISSIONS, 10400 "takePersistableUriPermission"); 10401 uid = mPackageManagerInt.getPackageUid(toPackage, 0, userId); 10402 } else { 10403 enforceNotIsolatedCaller("takePersistableUriPermission"); 10404 uid = Binder.getCallingUid(); 10405 } 10406 10407 Preconditions.checkFlagsArgument(modeFlags, 10408 Intent.FLAG_GRANT_READ_URI_PERMISSION | Intent.FLAG_GRANT_WRITE_URI_PERMISSION); 10409 10410 synchronized (this) { 10411 boolean persistChanged = false; 10412 GrantUri grantUri = new GrantUri(userId, uri, false); 10413 10414 UriPermission exactPerm = findUriPermissionLocked(uid, grantUri); 10415 UriPermission prefixPerm = findUriPermissionLocked(uid, 10416 new GrantUri(userId, uri, true)); 10417 10418 final boolean exactValid = (exactPerm != null) 10419 && ((modeFlags & exactPerm.persistableModeFlags) == modeFlags); 10420 final boolean prefixValid = (prefixPerm != null) 10421 && ((modeFlags & prefixPerm.persistableModeFlags) == modeFlags); 10422 10423 if (!(exactValid || prefixValid)) { 10424 throw new SecurityException("No persistable permission grants found for UID " 10425 + uid + " and Uri " + grantUri.toSafeString()); 10426 } 10427 10428 if (exactValid) { 10429 persistChanged |= exactPerm.takePersistableModes(modeFlags); 10430 } 10431 if (prefixValid) { 10432 persistChanged |= prefixPerm.takePersistableModes(modeFlags); 10433 } 10434 10435 persistChanged |= maybePrunePersistedUriGrantsLocked(uid); 10436 10437 if (persistChanged) { 10438 schedulePersistUriGrants(); 10439 } 10440 } 10441 } 10442 10443 /** 10444 * @param uri This uri must NOT contain an embedded userId. 10445 * @param toPackage Name of the target package whose uri is being released (if {@code null}, 10446 * uses calling uid) 10447 * @param userId The userId in which the uri is to be resolved. 10448 */ 10449 @Override 10450 public void releasePersistableUriPermission(Uri uri, final int modeFlags, 10451 @Nullable String toPackage, int userId) { 10452 10453 final int uid; 10454 if (toPackage != null) { 10455 enforceCallingPermission(android.Manifest.permission.FORCE_PERSISTABLE_URI_PERMISSIONS, 10456 "releasePersistableUriPermission"); 10457 uid = mPackageManagerInt.getPackageUid(toPackage, 0, userId); 10458 } else { 10459 enforceNotIsolatedCaller("releasePersistableUriPermission"); 10460 uid = Binder.getCallingUid(); 10461 } 10462 10463 Preconditions.checkFlagsArgument(modeFlags, 10464 Intent.FLAG_GRANT_READ_URI_PERMISSION | Intent.FLAG_GRANT_WRITE_URI_PERMISSION); 10465 10466 synchronized (this) { 10467 boolean persistChanged = false; 10468 10469 UriPermission exactPerm = findUriPermissionLocked(uid, 10470 new GrantUri(userId, uri, false)); 10471 UriPermission prefixPerm = findUriPermissionLocked(uid, 10472 new GrantUri(userId, uri, true)); 10473 if (exactPerm == null && prefixPerm == null && toPackage == null) { 10474 throw new SecurityException("No permission grants found for UID " + uid 10475 + " and Uri " + uri.toSafeString()); 10476 } 10477 10478 if (exactPerm != null) { 10479 persistChanged |= exactPerm.releasePersistableModes(modeFlags); 10480 removeUriPermissionIfNeededLocked(exactPerm); 10481 } 10482 if (prefixPerm != null) { 10483 persistChanged |= prefixPerm.releasePersistableModes(modeFlags); 10484 removeUriPermissionIfNeededLocked(prefixPerm); 10485 } 10486 10487 if (persistChanged) { 10488 schedulePersistUriGrants(); 10489 } 10490 } 10491 } 10492 10493 /** 10494 * Prune any older {@link UriPermission} for the given UID until outstanding 10495 * persisted grants are below {@link #MAX_PERSISTED_URI_GRANTS}. 10496 * 10497 * @return if any mutations occured that require persisting. 10498 */ 10499 @GuardedBy("this") 10500 private boolean maybePrunePersistedUriGrantsLocked(int uid) { 10501 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get(uid); 10502 if (perms == null) return false; 10503 if (perms.size() < MAX_PERSISTED_URI_GRANTS) return false; 10504 10505 final ArrayList<UriPermission> persisted = Lists.newArrayList(); 10506 for (UriPermission perm : perms.values()) { 10507 if (perm.persistedModeFlags != 0) { 10508 persisted.add(perm); 10509 } 10510 } 10511 10512 final int trimCount = persisted.size() - MAX_PERSISTED_URI_GRANTS; 10513 if (trimCount <= 0) return false; 10514 10515 Collections.sort(persisted, new UriPermission.PersistedTimeComparator()); 10516 for (int i = 0; i < trimCount; i++) { 10517 final UriPermission perm = persisted.get(i); 10518 10519 if (DEBUG_URI_PERMISSION) Slog.v(TAG_URI_PERMISSION, 10520 "Trimming grant created at " + perm.persistedCreateTime); 10521 10522 perm.releasePersistableModes(~0); 10523 removeUriPermissionIfNeededLocked(perm); 10524 } 10525 10526 return true; 10527 } 10528 10529 @Override 10530 public ParceledListSlice<android.content.UriPermission> getPersistedUriPermissions( 10531 String packageName, boolean incoming) { 10532 enforceNotIsolatedCaller("getPersistedUriPermissions"); 10533 Preconditions.checkNotNull(packageName, "packageName"); 10534 10535 final int callingUid = Binder.getCallingUid(); 10536 final int callingUserId = UserHandle.getUserId(callingUid); 10537 final IPackageManager pm = AppGlobals.getPackageManager(); 10538 try { 10539 final int packageUid = pm.getPackageUid(packageName, 10540 MATCH_DIRECT_BOOT_AWARE | MATCH_DIRECT_BOOT_UNAWARE, callingUserId); 10541 if (packageUid != callingUid) { 10542 throw new SecurityException( 10543 "Package " + packageName + " does not belong to calling UID " + callingUid); 10544 } 10545 } catch (RemoteException e) { 10546 throw new SecurityException("Failed to verify package name ownership"); 10547 } 10548 10549 final ArrayList<android.content.UriPermission> result = Lists.newArrayList(); 10550 synchronized (this) { 10551 if (incoming) { 10552 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get( 10553 callingUid); 10554 if (perms == null) { 10555 Slog.w(TAG, "No permission grants found for " + packageName); 10556 } else { 10557 for (int j = 0; j < perms.size(); j++) { 10558 final UriPermission perm = perms.valueAt(j); 10559 if (packageName.equals(perm.targetPkg) && perm.persistedModeFlags != 0) { 10560 result.add(perm.buildPersistedPublicApiObject()); 10561 } 10562 } 10563 } 10564 } else { 10565 final int size = mGrantedUriPermissions.size(); 10566 for (int i = 0; i < size; i++) { 10567 final ArrayMap<GrantUri, UriPermission> perms = 10568 mGrantedUriPermissions.valueAt(i); 10569 for (int j = 0; j < perms.size(); j++) { 10570 final UriPermission perm = perms.valueAt(j); 10571 if (packageName.equals(perm.sourcePkg) && perm.persistedModeFlags != 0) { 10572 result.add(perm.buildPersistedPublicApiObject()); 10573 } 10574 } 10575 } 10576 } 10577 } 10578 return new ParceledListSlice<android.content.UriPermission>(result); 10579 } 10580 10581 @Override 10582 public ParceledListSlice<GrantedUriPermission> getGrantedUriPermissions( 10583 @Nullable String packageName, int userId) { 10584 enforceCallingPermission(android.Manifest.permission.GET_APP_GRANTED_URI_PERMISSIONS, 10585 "getGrantedUriPermissions"); 10586 10587 final List<GrantedUriPermission> result = new ArrayList<>(); 10588 synchronized (this) { 10589 final int size = mGrantedUriPermissions.size(); 10590 for (int i = 0; i < size; i++) { 10591 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i); 10592 for (int j = 0; j < perms.size(); j++) { 10593 final UriPermission perm = perms.valueAt(j); 10594 if ((packageName == null || packageName.equals(perm.targetPkg)) 10595 && perm.targetUserId == userId 10596 && perm.persistedModeFlags != 0) { 10597 result.add(perm.buildGrantedUriPermission()); 10598 } 10599 } 10600 } 10601 } 10602 return new ParceledListSlice<>(result); 10603 } 10604 10605 @Override 10606 public void clearGrantedUriPermissions(String packageName, int userId) { 10607 enforceCallingPermission(android.Manifest.permission.CLEAR_APP_GRANTED_URI_PERMISSIONS, 10608 "clearGrantedUriPermissions"); 10609 synchronized(this) { 10610 removeUriPermissionsForPackageLocked(packageName, userId, true, true); 10611 } 10612 } 10613 10614 @Override 10615 public void showWaitingForDebugger(IApplicationThread who, boolean waiting) { 10616 synchronized (this) { 10617 ProcessRecord app = 10618 who != null ? getRecordForAppLocked(who) : null; 10619 if (app == null) return; 10620 10621 Message msg = Message.obtain(); 10622 msg.what = WAIT_FOR_DEBUGGER_UI_MSG; 10623 msg.obj = app; 10624 msg.arg1 = waiting ? 1 : 0; 10625 mUiHandler.sendMessage(msg); 10626 } 10627 } 10628 10629 @Override 10630 public void getMemoryInfo(ActivityManager.MemoryInfo outInfo) { 10631 final long homeAppMem = mProcessList.getMemLevel(ProcessList.HOME_APP_ADJ); 10632 final long cachedAppMem = mProcessList.getMemLevel(ProcessList.CACHED_APP_MIN_ADJ); 10633 outInfo.availMem = getFreeMemory(); 10634 outInfo.totalMem = getTotalMemory(); 10635 outInfo.threshold = homeAppMem; 10636 outInfo.lowMemory = outInfo.availMem < (homeAppMem + ((cachedAppMem-homeAppMem)/2)); 10637 outInfo.hiddenAppThreshold = cachedAppMem; 10638 outInfo.secondaryServerThreshold = mProcessList.getMemLevel( 10639 ProcessList.SERVICE_ADJ); 10640 outInfo.visibleAppThreshold = mProcessList.getMemLevel( 10641 ProcessList.VISIBLE_APP_ADJ); 10642 outInfo.foregroundAppThreshold = mProcessList.getMemLevel( 10643 ProcessList.FOREGROUND_APP_ADJ); 10644 } 10645 10646 // ========================================================= 10647 // TASK MANAGEMENT 10648 // ========================================================= 10649 10650 @Override 10651 public List<IBinder> getAppTasks(String callingPackage) { 10652 int callingUid = Binder.getCallingUid(); 10653 long ident = Binder.clearCallingIdentity(); 10654 try { 10655 synchronized(this) { 10656 return mRecentTasks.getAppTasksList(callingUid, callingPackage); 10657 } 10658 } finally { 10659 Binder.restoreCallingIdentity(ident); 10660 } 10661 } 10662 10663 @Override 10664 public List<RunningTaskInfo> getTasks(int maxNum) { 10665 return getFilteredTasks(maxNum, ACTIVITY_TYPE_UNDEFINED, WINDOWING_MODE_UNDEFINED); 10666 } 10667 10668 @Override 10669 public List<RunningTaskInfo> getFilteredTasks(int maxNum, @ActivityType int ignoreActivityType, 10670 @WindowingMode int ignoreWindowingMode) { 10671 final int callingUid = Binder.getCallingUid(); 10672 ArrayList<RunningTaskInfo> list = new ArrayList<>(); 10673 10674 synchronized(this) { 10675 if (DEBUG_ALL) Slog.v(TAG, "getTasks: max=" + maxNum); 10676 10677 final boolean allowed = isGetTasksAllowed("getTasks", Binder.getCallingPid(), 10678 callingUid); 10679 mStackSupervisor.getRunningTasks(maxNum, list, ignoreActivityType, 10680 ignoreWindowingMode, callingUid, allowed); 10681 } 10682 10683 return list; 10684 } 10685 10686 private boolean isGetTasksAllowed(String caller, int callingPid, int callingUid) { 10687 if (mRecentTasks.isCallerRecents(callingUid)) { 10688 // Always allow the recents component to get tasks 10689 return true; 10690 } 10691 10692 boolean allowed = checkPermission(android.Manifest.permission.REAL_GET_TASKS, 10693 callingPid, callingUid) == PackageManager.PERMISSION_GRANTED; 10694 if (!allowed) { 10695 if (checkPermission(android.Manifest.permission.GET_TASKS, 10696 callingPid, callingUid) == PackageManager.PERMISSION_GRANTED) { 10697 // Temporary compatibility: some existing apps on the system image may 10698 // still be requesting the old permission and not switched to the new 10699 // one; if so, we'll still allow them full access. This means we need 10700 // to see if they are holding the old permission and are a system app. 10701 try { 10702 if (AppGlobals.getPackageManager().isUidPrivileged(callingUid)) { 10703 allowed = true; 10704 if (DEBUG_TASKS) Slog.w(TAG, caller + ": caller " + callingUid 10705 + " is using old GET_TASKS but privileged; allowing"); 10706 } 10707 } catch (RemoteException e) { 10708 } 10709 } 10710 } 10711 if (!allowed) { 10712 if (DEBUG_TASKS) Slog.w(TAG, caller + ": caller " + callingUid 10713 + " does not hold REAL_GET_TASKS; limiting output"); 10714 } 10715 return allowed; 10716 } 10717 10718 @Override 10719 public ParceledListSlice<ActivityManager.RecentTaskInfo> getRecentTasks(int maxNum, int flags, 10720 int userId) { 10721 final int callingUid = Binder.getCallingUid(); 10722 userId = mUserController.handleIncomingUser(Binder.getCallingPid(), callingUid, userId, 10723 false, ALLOW_FULL_ONLY, "getRecentTasks", null); 10724 final boolean allowed = isGetTasksAllowed("getRecentTasks", Binder.getCallingPid(), 10725 callingUid); 10726 final boolean detailed = checkCallingPermission( 10727 android.Manifest.permission.GET_DETAILED_TASKS) 10728 == PackageManager.PERMISSION_GRANTED; 10729 10730 synchronized (this) { 10731 return mRecentTasks.getRecentTasks(maxNum, flags, allowed, detailed, userId, 10732 callingUid); 10733 } 10734 } 10735 10736 @Override 10737 public ActivityManager.TaskDescription getTaskDescription(int id) { 10738 synchronized (this) { 10739 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS, "getTaskDescription()"); 10740 final TaskRecord tr = mStackSupervisor.anyTaskForIdLocked(id, 10741 MATCH_TASK_IN_STACKS_OR_RECENT_TASKS); 10742 if (tr != null) { 10743 return tr.lastTaskDescription; 10744 } 10745 } 10746 return null; 10747 } 10748 10749 @Override 10750 public int addAppTask(IBinder activityToken, Intent intent, 10751 ActivityManager.TaskDescription description, Bitmap thumbnail) throws RemoteException { 10752 final int callingUid = Binder.getCallingUid(); 10753 final long callingIdent = Binder.clearCallingIdentity(); 10754 10755 try { 10756 synchronized (this) { 10757 ActivityRecord r = ActivityRecord.isInStackLocked(activityToken); 10758 if (r == null) { 10759 throw new IllegalArgumentException("Activity does not exist; token=" 10760 + activityToken); 10761 } 10762 ComponentName comp = intent.getComponent(); 10763 if (comp == null) { 10764 throw new IllegalArgumentException("Intent " + intent 10765 + " must specify explicit component"); 10766 } 10767 if (thumbnail.getWidth() != mThumbnailWidth 10768 || thumbnail.getHeight() != mThumbnailHeight) { 10769 throw new IllegalArgumentException("Bad thumbnail size: got " 10770 + thumbnail.getWidth() + "x" + thumbnail.getHeight() + ", require " 10771 + mThumbnailWidth + "x" + mThumbnailHeight); 10772 } 10773 if (intent.getSelector() != null) { 10774 intent.setSelector(null); 10775 } 10776 if (intent.getSourceBounds() != null) { 10777 intent.setSourceBounds(null); 10778 } 10779 if ((intent.getFlags()&Intent.FLAG_ACTIVITY_NEW_DOCUMENT) != 0) { 10780 if ((intent.getFlags()&Intent.FLAG_ACTIVITY_RETAIN_IN_RECENTS) == 0) { 10781 // The caller has added this as an auto-remove task... that makes no 10782 // sense, so turn off auto-remove. 10783 intent.addFlags(Intent.FLAG_ACTIVITY_RETAIN_IN_RECENTS); 10784 } 10785 } 10786 final ActivityInfo ainfo = AppGlobals.getPackageManager().getActivityInfo(comp, 10787 STOCK_PM_FLAGS, UserHandle.getUserId(callingUid)); 10788 if (ainfo.applicationInfo.uid != callingUid) { 10789 throw new SecurityException( 10790 "Can't add task for another application: target uid=" 10791 + ainfo.applicationInfo.uid + ", calling uid=" + callingUid); 10792 } 10793 10794 final ActivityStack stack = r.getStack(); 10795 final TaskRecord task = stack.createTaskRecord( 10796 mStackSupervisor.getNextTaskIdForUserLocked(r.userId), ainfo, intent, 10797 null /* voiceSession */, null /* voiceInteractor */, !ON_TOP); 10798 if (!mRecentTasks.addToBottom(task)) { 10799 // The app has too many tasks already and we can't add any more 10800 stack.removeTask(task, "addAppTask", REMOVE_TASK_MODE_DESTROYING); 10801 return INVALID_TASK_ID; 10802 } 10803 task.lastTaskDescription.copyFrom(description); 10804 10805 // TODO: Send the thumbnail to WM to store it. 10806 10807 return task.taskId; 10808 } 10809 } finally { 10810 Binder.restoreCallingIdentity(callingIdent); 10811 } 10812 } 10813 10814 @Override 10815 public Point getAppTaskThumbnailSize() { 10816 synchronized (this) { 10817 return new Point(mThumbnailWidth, mThumbnailHeight); 10818 } 10819 } 10820 10821 @Override 10822 public void setTaskDescription(IBinder token, ActivityManager.TaskDescription td) { 10823 synchronized (this) { 10824 ActivityRecord r = ActivityRecord.isInStackLocked(token); 10825 if (r != null) { 10826 r.setTaskDescription(td); 10827 final TaskRecord task = r.getTask(); 10828 task.updateTaskDescription(); 10829 mTaskChangeNotificationController.notifyTaskDescriptionChanged(task.taskId, td); 10830 } 10831 } 10832 } 10833 10834 @Override 10835 public void setTaskResizeable(int taskId, int resizeableMode) { 10836 synchronized (this) { 10837 final TaskRecord task = mStackSupervisor.anyTaskForIdLocked( 10838 taskId, MATCH_TASK_IN_STACKS_OR_RECENT_TASKS); 10839 if (task == null) { 10840 Slog.w(TAG, "setTaskResizeable: taskId=" + taskId + " not found"); 10841 return; 10842 } 10843 task.setResizeMode(resizeableMode); 10844 } 10845 } 10846 10847 @Override 10848 public void resizeTask(int taskId, Rect bounds, int resizeMode) { 10849 enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "resizeTask()"); 10850 long ident = Binder.clearCallingIdentity(); 10851 try { 10852 synchronized (this) { 10853 TaskRecord task = mStackSupervisor.anyTaskForIdLocked(taskId); 10854 if (task == null) { 10855 Slog.w(TAG, "resizeTask: taskId=" + taskId + " not found"); 10856 return; 10857 } 10858 // Place the task in the right stack if it isn't there already based on 10859 // the requested bounds. 10860 // The stack transition logic is: 10861 // - a null bounds on a freeform task moves that task to fullscreen 10862 // - a non-null bounds on a non-freeform (fullscreen OR docked) task moves 10863 // that task to freeform 10864 // - otherwise the task is not moved 10865 ActivityStack stack = task.getStack(); 10866 if (!task.getWindowConfiguration().canResizeTask()) { 10867 throw new IllegalArgumentException("resizeTask not allowed on task=" + task); 10868 } 10869 if (bounds == null && stack.getWindowingMode() == WINDOWING_MODE_FREEFORM) { 10870 stack = stack.getDisplay().getOrCreateStack( 10871 WINDOWING_MODE_FULLSCREEN, stack.getActivityType(), ON_TOP); 10872 } else if (bounds != null && stack.getWindowingMode() != WINDOWING_MODE_FREEFORM) { 10873 stack = stack.getDisplay().getOrCreateStack( 10874 WINDOWING_MODE_FREEFORM, stack.getActivityType(), ON_TOP); 10875 } 10876 10877 // Reparent the task to the right stack if necessary 10878 boolean preserveWindow = (resizeMode & RESIZE_MODE_PRESERVE_WINDOW) != 0; 10879 if (stack != task.getStack()) { 10880 // Defer resume until the task is resized below 10881 task.reparent(stack, ON_TOP, REPARENT_KEEP_STACK_AT_FRONT, ANIMATE, 10882 DEFER_RESUME, "resizeTask"); 10883 preserveWindow = false; 10884 } 10885 10886 // After reparenting (which only resizes the task to the stack bounds), resize the 10887 // task to the actual bounds provided 10888 task.resize(bounds, resizeMode, preserveWindow, !DEFER_RESUME); 10889 } 10890 } finally { 10891 Binder.restoreCallingIdentity(ident); 10892 } 10893 } 10894 10895 @Override 10896 public Rect getTaskBounds(int taskId) { 10897 enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "getTaskBounds()"); 10898 long ident = Binder.clearCallingIdentity(); 10899 Rect rect = new Rect(); 10900 try { 10901 synchronized (this) { 10902 final TaskRecord task = mStackSupervisor.anyTaskForIdLocked(taskId, 10903 MATCH_TASK_IN_STACKS_OR_RECENT_TASKS); 10904 if (task == null) { 10905 Slog.w(TAG, "getTaskBounds: taskId=" + taskId + " not found"); 10906 return rect; 10907 } 10908 if (task.getStack() != null) { 10909 // Return the bounds from window manager since it will be adjusted for various 10910 // things like the presense of a docked stack for tasks that aren't resizeable. 10911 task.getWindowContainerBounds(rect); 10912 } else { 10913 // Task isn't in window manager yet since it isn't associated with a stack. 10914 // Return the persist value from activity manager 10915 if (!task.matchParentBounds()) { 10916 rect.set(task.getBounds()); 10917 } else if (task.mLastNonFullscreenBounds != null) { 10918 rect.set(task.mLastNonFullscreenBounds); 10919 } 10920 } 10921 } 10922 } finally { 10923 Binder.restoreCallingIdentity(ident); 10924 } 10925 return rect; 10926 } 10927 10928 @Override 10929 public void cancelTaskWindowTransition(int taskId) { 10930 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS, 10931 "cancelTaskWindowTransition()"); 10932 final long ident = Binder.clearCallingIdentity(); 10933 try { 10934 synchronized (this) { 10935 final TaskRecord task = mStackSupervisor.anyTaskForIdLocked(taskId, 10936 MATCH_TASK_IN_STACKS_ONLY); 10937 if (task == null) { 10938 Slog.w(TAG, "cancelTaskWindowTransition: taskId=" + taskId + " not found"); 10939 return; 10940 } 10941 task.cancelWindowTransition(); 10942 } 10943 } finally { 10944 Binder.restoreCallingIdentity(ident); 10945 } 10946 } 10947 10948 @Override 10949 public TaskSnapshot getTaskSnapshot(int taskId, boolean reducedResolution) { 10950 enforceCallerIsRecentsOrHasPermission(READ_FRAME_BUFFER, "getTaskSnapshot()"); 10951 final long ident = Binder.clearCallingIdentity(); 10952 try { 10953 final TaskRecord task; 10954 synchronized (this) { 10955 task = mStackSupervisor.anyTaskForIdLocked(taskId, 10956 MATCH_TASK_IN_STACKS_OR_RECENT_TASKS); 10957 if (task == null) { 10958 Slog.w(TAG, "getTaskSnapshot: taskId=" + taskId + " not found"); 10959 return null; 10960 } 10961 } 10962 // Don't call this while holding the lock as this operation might hit the disk. 10963 return task.getSnapshot(reducedResolution); 10964 } finally { 10965 Binder.restoreCallingIdentity(ident); 10966 } 10967 } 10968 10969 @Override 10970 public Bitmap getTaskDescriptionIcon(String filePath, int userId) { 10971 userId = mUserController.handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 10972 userId, false, ALLOW_FULL_ONLY, "getTaskDescriptionIcon", null); 10973 10974 final File passedIconFile = new File(filePath); 10975 final File legitIconFile = new File(TaskPersister.getUserImagesDir(userId), 10976 passedIconFile.getName()); 10977 if (!legitIconFile.getPath().equals(filePath) 10978 || !filePath.contains(ActivityRecord.ACTIVITY_ICON_SUFFIX)) { 10979 throw new IllegalArgumentException("Bad file path: " + filePath 10980 + " passed for userId " + userId); 10981 } 10982 return mRecentTasks.getTaskDescriptionIcon(filePath); 10983 } 10984 10985 @Override 10986 public void startInPlaceAnimationOnFrontMostApplication(Bundle opts) 10987 throws RemoteException { 10988 final SafeActivityOptions safeOptions = SafeActivityOptions.fromBundle(opts); 10989 final ActivityOptions activityOptions = safeOptions != null 10990 ? safeOptions.getOptions(mStackSupervisor) 10991 : null; 10992 if (activityOptions == null 10993 || activityOptions.getAnimationType() != ActivityOptions.ANIM_CUSTOM_IN_PLACE 10994 || activityOptions.getCustomInPlaceResId() == 0) { 10995 throw new IllegalArgumentException("Expected in-place ActivityOption " + 10996 "with valid animation"); 10997 } 10998 mWindowManager.prepareAppTransition(TRANSIT_TASK_IN_PLACE, false); 10999 mWindowManager.overridePendingAppTransitionInPlace(activityOptions.getPackageName(), 11000 activityOptions.getCustomInPlaceResId()); 11001 mWindowManager.executeAppTransition(); 11002 } 11003 11004 @Override 11005 public void removeStack(int stackId) { 11006 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS, "removeStack()"); 11007 synchronized (this) { 11008 final long ident = Binder.clearCallingIdentity(); 11009 try { 11010 final ActivityStack stack = mStackSupervisor.getStack(stackId); 11011 if (stack == null) { 11012 Slog.w(TAG, "removeStack: No stack with id=" + stackId); 11013 return; 11014 } 11015 if (!stack.isActivityTypeStandardOrUndefined()) { 11016 throw new IllegalArgumentException( 11017 "Removing non-standard stack is not allowed."); 11018 } 11019 mStackSupervisor.removeStack(stack); 11020 } finally { 11021 Binder.restoreCallingIdentity(ident); 11022 } 11023 } 11024 } 11025 11026 /** 11027 * Removes stacks in the input windowing modes from the system if they are of activity type 11028 * ACTIVITY_TYPE_STANDARD or ACTIVITY_TYPE_UNDEFINED 11029 */ 11030 @Override 11031 public void removeStacksInWindowingModes(int[] windowingModes) { 11032 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS, 11033 "removeStacksInWindowingModes()"); 11034 synchronized (this) { 11035 final long ident = Binder.clearCallingIdentity(); 11036 try { 11037 mStackSupervisor.removeStacksInWindowingModes(windowingModes); 11038 } finally { 11039 Binder.restoreCallingIdentity(ident); 11040 } 11041 } 11042 } 11043 11044 @Override 11045 public void removeStacksWithActivityTypes(int[] activityTypes) { 11046 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS, 11047 "removeStacksWithActivityTypes()"); 11048 synchronized (this) { 11049 final long ident = Binder.clearCallingIdentity(); 11050 try { 11051 mStackSupervisor.removeStacksWithActivityTypes(activityTypes); 11052 } finally { 11053 Binder.restoreCallingIdentity(ident); 11054 } 11055 } 11056 } 11057 11058 @Override 11059 public void moveStackToDisplay(int stackId, int displayId) { 11060 enforceCallingPermission(INTERNAL_SYSTEM_WINDOW, "moveStackToDisplay()"); 11061 11062 synchronized (this) { 11063 final long ident = Binder.clearCallingIdentity(); 11064 try { 11065 if (DEBUG_STACK) Slog.d(TAG_STACK, "moveStackToDisplay: moving stackId=" + stackId 11066 + " to displayId=" + displayId); 11067 mStackSupervisor.moveStackToDisplayLocked(stackId, displayId, ON_TOP); 11068 } finally { 11069 Binder.restoreCallingIdentity(ident); 11070 } 11071 } 11072 } 11073 11074 @Override 11075 public boolean removeTask(int taskId) { 11076 enforceCallerIsRecentsOrHasPermission(REMOVE_TASKS, "removeTask()"); 11077 synchronized (this) { 11078 final long ident = Binder.clearCallingIdentity(); 11079 try { 11080 return mStackSupervisor.removeTaskByIdLocked(taskId, true, REMOVE_FROM_RECENTS, 11081 "remove-task"); 11082 } finally { 11083 Binder.restoreCallingIdentity(ident); 11084 } 11085 } 11086 } 11087 11088 /** 11089 * TODO: Add mController hook 11090 */ 11091 @Override 11092 public void moveTaskToFront(int taskId, int flags, Bundle bOptions) { 11093 enforceCallingPermission(android.Manifest.permission.REORDER_TASKS, "moveTaskToFront()"); 11094 11095 if (DEBUG_STACK) Slog.d(TAG_STACK, "moveTaskToFront: moving taskId=" + taskId); 11096 synchronized(this) { 11097 moveTaskToFrontLocked(taskId, flags, SafeActivityOptions.fromBundle(bOptions), 11098 false /* fromRecents */); 11099 } 11100 } 11101 11102 void moveTaskToFrontLocked(int taskId, int flags, SafeActivityOptions options, 11103 boolean fromRecents) { 11104 11105 if (!checkAppSwitchAllowedLocked(Binder.getCallingPid(), 11106 Binder.getCallingUid(), -1, -1, "Task to front")) { 11107 SafeActivityOptions.abort(options); 11108 return; 11109 } 11110 final long origId = Binder.clearCallingIdentity(); 11111 try { 11112 final TaskRecord task = mStackSupervisor.anyTaskForIdLocked(taskId); 11113 if (task == null) { 11114 Slog.d(TAG, "Could not find task for id: "+ taskId); 11115 return; 11116 } 11117 if (mLockTaskController.isLockTaskModeViolation(task)) { 11118 Slog.e(TAG, "moveTaskToFront: Attempt to violate Lock Task Mode"); 11119 return; 11120 } 11121 ActivityOptions realOptions = options != null 11122 ? options.getOptions(mStackSupervisor) 11123 : null; 11124 mStackSupervisor.findTaskToMoveToFront(task, flags, realOptions, "moveTaskToFront", 11125 false /* forceNonResizable */); 11126 11127 final ActivityRecord topActivity = task.getTopActivity(); 11128 if (topActivity != null) { 11129 11130 // We are reshowing a task, use a starting window to hide the initial draw delay 11131 // so the transition can start earlier. 11132 topActivity.showStartingWindow(null /* prev */, false /* newTask */, 11133 true /* taskSwitch */, fromRecents); 11134 } 11135 } finally { 11136 Binder.restoreCallingIdentity(origId); 11137 } 11138 SafeActivityOptions.abort(options); 11139 } 11140 11141 /** 11142 * Attempts to move a task backwards in z-order (the order of activities within the task is 11143 * unchanged). 11144 * 11145 * There are several possible results of this call: 11146 * - if the task is locked, then we will show the lock toast 11147 * - if there is a task behind the provided task, then that task is made visible and resumed as 11148 * this task is moved to the back 11149 * - otherwise, if there are no other tasks in the stack: 11150 * - if this task is in the pinned stack, then we remove the stack completely, which will 11151 * have the effect of moving the task to the top or bottom of the fullscreen stack 11152 * (depending on whether it is visible) 11153 * - otherwise, we simply return home and hide this task 11154 * 11155 * @param token A reference to the activity we wish to move 11156 * @param nonRoot If false then this only works if the activity is the root 11157 * of a task; if true it will work for any activity in a task. 11158 * @return Returns true if the move completed, false if not. 11159 */ 11160 @Override 11161 public boolean moveActivityTaskToBack(IBinder token, boolean nonRoot) { 11162 enforceNotIsolatedCaller("moveActivityTaskToBack"); 11163 synchronized(this) { 11164 final long origId = Binder.clearCallingIdentity(); 11165 try { 11166 int taskId = ActivityRecord.getTaskForActivityLocked(token, !nonRoot); 11167 final TaskRecord task = mStackSupervisor.anyTaskForIdLocked(taskId); 11168 if (task != null) { 11169 return ActivityRecord.getStackLocked(token).moveTaskToBackLocked(taskId); 11170 } 11171 } finally { 11172 Binder.restoreCallingIdentity(origId); 11173 } 11174 } 11175 return false; 11176 } 11177 11178 @Override 11179 public void moveTaskBackwards(int task) { 11180 enforceCallingPermission(android.Manifest.permission.REORDER_TASKS, 11181 "moveTaskBackwards()"); 11182 11183 synchronized(this) { 11184 if (!checkAppSwitchAllowedLocked(Binder.getCallingPid(), 11185 Binder.getCallingUid(), -1, -1, "Task backwards")) { 11186 return; 11187 } 11188 final long origId = Binder.clearCallingIdentity(); 11189 moveTaskBackwardsLocked(task); 11190 Binder.restoreCallingIdentity(origId); 11191 } 11192 } 11193 11194 private final void moveTaskBackwardsLocked(int task) { 11195 Slog.e(TAG, "moveTaskBackwards not yet implemented!"); 11196 } 11197 11198 @Override 11199 public int createStackOnDisplay(int displayId) throws RemoteException { 11200 enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "createStackOnDisplay()"); 11201 synchronized (this) { 11202 final ActivityDisplay display = 11203 mStackSupervisor.getActivityDisplayOrCreateLocked(displayId); 11204 if (display == null) { 11205 return INVALID_STACK_ID; 11206 } 11207 // TODO(multi-display): Have the caller pass in the windowing mode and activity type. 11208 final ActivityStack stack = display.createStack( 11209 WINDOWING_MODE_FULLSCREEN_OR_SPLIT_SCREEN_SECONDARY, ACTIVITY_TYPE_STANDARD, 11210 ON_TOP); 11211 return (stack != null) ? stack.mStackId : INVALID_STACK_ID; 11212 } 11213 } 11214 11215 @Override 11216 public int getActivityDisplayId(IBinder activityToken) throws RemoteException { 11217 synchronized (this) { 11218 final ActivityStack stack = ActivityRecord.getStackLocked(activityToken); 11219 if (stack != null && stack.mDisplayId != INVALID_DISPLAY) { 11220 return stack.mDisplayId; 11221 } 11222 return DEFAULT_DISPLAY; 11223 } 11224 } 11225 11226 @Override 11227 public void exitFreeformMode(IBinder token) throws RemoteException { 11228 synchronized (this) { 11229 long ident = Binder.clearCallingIdentity(); 11230 try { 11231 final ActivityRecord r = ActivityRecord.forTokenLocked(token); 11232 if (r == null) { 11233 throw new IllegalArgumentException( 11234 "exitFreeformMode: No activity record matching token=" + token); 11235 } 11236 11237 final ActivityStack stack = r.getStack(); 11238 if (stack == null || !stack.inFreeformWindowingMode()) { 11239 throw new IllegalStateException( 11240 "exitFreeformMode: You can only go fullscreen from freeform."); 11241 } 11242 11243 stack.setWindowingMode(WINDOWING_MODE_FULLSCREEN); 11244 } finally { 11245 Binder.restoreCallingIdentity(ident); 11246 } 11247 } 11248 } 11249 11250 @Override 11251 public void setTaskWindowingMode(int taskId, int windowingMode, boolean toTop) { 11252 if (windowingMode == WINDOWING_MODE_SPLIT_SCREEN_PRIMARY) { 11253 setTaskWindowingModeSplitScreenPrimary(taskId, SPLIT_SCREEN_CREATE_MODE_TOP_OR_LEFT, 11254 toTop, ANIMATE, null /* initialBounds */, true /* showRecents */); 11255 return; 11256 } 11257 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS, "setTaskWindowingMode()"); 11258 synchronized (this) { 11259 final long ident = Binder.clearCallingIdentity(); 11260 try { 11261 final TaskRecord task = mStackSupervisor.anyTaskForIdLocked(taskId); 11262 if (task == null) { 11263 Slog.w(TAG, "setTaskWindowingMode: No task for id=" + taskId); 11264 return; 11265 } 11266 11267 if (DEBUG_STACK) Slog.d(TAG_STACK, "setTaskWindowingMode: moving task=" + taskId 11268 + " to windowingMode=" + windowingMode + " toTop=" + toTop); 11269 11270 if (!task.isActivityTypeStandardOrUndefined()) { 11271 throw new IllegalArgumentException("setTaskWindowingMode: Attempt to move" 11272 + " non-standard task " + taskId + " to windowing mode=" 11273 + windowingMode); 11274 } 11275 11276 final ActivityStack stack = task.getStack(); 11277 if (toTop) { 11278 stack.moveToFront("setTaskWindowingMode", task); 11279 } 11280 stack.setWindowingMode(windowingMode); 11281 } finally { 11282 Binder.restoreCallingIdentity(ident); 11283 } 11284 } 11285 } 11286 11287 /** 11288 * Moves the specified task to the primary-split-screen stack. 11289 * 11290 * @param taskId Id of task to move. 11291 * @param createMode The mode the primary split screen stack should be created in if it doesn't 11292 * exist already. See 11293 * {@link android.app.ActivityManager#SPLIT_SCREEN_CREATE_MODE_TOP_OR_LEFT} 11294 * and 11295 * {@link android.app.ActivityManager#SPLIT_SCREEN_CREATE_MODE_BOTTOM_OR_RIGHT} 11296 * @param toTop If the task and stack should be moved to the top. 11297 * @param animate Whether we should play an animation for the moving the task. 11298 * @param initialBounds If the primary stack gets created, it will use these bounds for the 11299 * stack. Pass {@code null} to use default bounds. 11300 * @param showRecents If the recents activity should be shown on the other side of the task 11301 * going into split-screen mode. 11302 */ 11303 @Override 11304 public boolean setTaskWindowingModeSplitScreenPrimary(int taskId, int createMode, boolean toTop, 11305 boolean animate, Rect initialBounds, boolean showRecents) { 11306 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS, 11307 "setTaskWindowingModeSplitScreenPrimary()"); 11308 synchronized (this) { 11309 long ident = Binder.clearCallingIdentity(); 11310 try { 11311 final TaskRecord task = mStackSupervisor.anyTaskForIdLocked(taskId); 11312 if (task == null) { 11313 Slog.w(TAG, "setTaskWindowingModeSplitScreenPrimary: No task for id=" + taskId); 11314 return false; 11315 } 11316 if (DEBUG_STACK) Slog.d(TAG_STACK, 11317 "setTaskWindowingModeSplitScreenPrimary: moving task=" + taskId 11318 + " to createMode=" + createMode + " toTop=" + toTop); 11319 if (!task.isActivityTypeStandardOrUndefined()) { 11320 throw new IllegalArgumentException("setTaskWindowingMode: Attempt to move" 11321 + " non-standard task " + taskId + " to split-screen windowing mode"); 11322 } 11323 11324 mWindowManager.setDockedStackCreateState(createMode, initialBounds); 11325 final int windowingMode = task.getWindowingMode(); 11326 final ActivityStack stack = task.getStack(); 11327 if (toTop) { 11328 stack.moveToFront("setTaskWindowingModeSplitScreenPrimary", task); 11329 } 11330 stack.setWindowingMode(WINDOWING_MODE_SPLIT_SCREEN_PRIMARY, animate, showRecents, 11331 false /* enteringSplitScreenMode */, false /* deferEnsuringVisibility */); 11332 return windowingMode != task.getWindowingMode(); 11333 } finally { 11334 Binder.restoreCallingIdentity(ident); 11335 } 11336 } 11337 } 11338 11339 @Override 11340 public void moveTaskToStack(int taskId, int stackId, boolean toTop) { 11341 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS, "moveTaskToStack()"); 11342 synchronized (this) { 11343 long ident = Binder.clearCallingIdentity(); 11344 try { 11345 final TaskRecord task = mStackSupervisor.anyTaskForIdLocked(taskId); 11346 if (task == null) { 11347 Slog.w(TAG, "moveTaskToStack: No task for id=" + taskId); 11348 return; 11349 } 11350 11351 if (DEBUG_STACK) Slog.d(TAG_STACK, "moveTaskToStack: moving task=" + taskId 11352 + " to stackId=" + stackId + " toTop=" + toTop); 11353 11354 final ActivityStack stack = mStackSupervisor.getStack(stackId); 11355 if (stack == null) { 11356 throw new IllegalStateException( 11357 "moveTaskToStack: No stack for stackId=" + stackId); 11358 } 11359 if (!stack.isActivityTypeStandardOrUndefined()) { 11360 throw new IllegalArgumentException("moveTaskToStack: Attempt to move task " 11361 + taskId + " to stack " + stackId); 11362 } 11363 if (stack.inSplitScreenPrimaryWindowingMode()) { 11364 mWindowManager.setDockedStackCreateState( 11365 SPLIT_SCREEN_CREATE_MODE_TOP_OR_LEFT, null /* initialBounds */); 11366 } 11367 task.reparent(stack, toTop, REPARENT_KEEP_STACK_AT_FRONT, ANIMATE, !DEFER_RESUME, 11368 "moveTaskToStack"); 11369 } finally { 11370 Binder.restoreCallingIdentity(ident); 11371 } 11372 } 11373 } 11374 11375 /** 11376 * Dismisses split-screen multi-window mode. 11377 * @param toTop If true the current primary split-screen stack will be placed or left on top. 11378 */ 11379 @Override 11380 public void dismissSplitScreenMode(boolean toTop) { 11381 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS, "dismissSplitScreenMode()"); 11382 final long ident = Binder.clearCallingIdentity(); 11383 try { 11384 synchronized (this) { 11385 final ActivityStack stack = 11386 mStackSupervisor.getDefaultDisplay().getSplitScreenPrimaryStack(); 11387 if (stack == null) { 11388 Slog.w(TAG, "dismissSplitScreenMode: primary split-screen stack not found."); 11389 return; 11390 } 11391 11392 if (toTop) { 11393 // Caller wants the current split-screen primary stack to be the top stack after 11394 // it goes fullscreen, so move it to the front. 11395 stack.moveToFront("dismissSplitScreenMode"); 11396 } else if (mStackSupervisor.isFocusedStack(stack)) { 11397 // In this case the current split-screen primary stack shouldn't be the top 11398 // stack after it goes fullscreen, but it current has focus, so we move the 11399 // focus to the top-most split-screen secondary stack next to it. 11400 final ActivityStack otherStack = stack.getDisplay().getTopStackInWindowingMode( 11401 WINDOWING_MODE_SPLIT_SCREEN_SECONDARY); 11402 if (otherStack != null) { 11403 otherStack.moveToFront("dismissSplitScreenMode_other"); 11404 } 11405 } 11406 11407 stack.setWindowingMode(WINDOWING_MODE_FULLSCREEN); 11408 } 11409 } finally { 11410 Binder.restoreCallingIdentity(ident); 11411 } 11412 } 11413 11414 /** 11415 * Dismisses Pip 11416 * @param animate True if the dismissal should be animated. 11417 * @param animationDuration The duration of the resize animation in milliseconds or -1 if the 11418 * default animation duration should be used. 11419 */ 11420 @Override 11421 public void dismissPip(boolean animate, int animationDuration) { 11422 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS, "dismissPip()"); 11423 final long ident = Binder.clearCallingIdentity(); 11424 try { 11425 synchronized (this) { 11426 final PinnedActivityStack stack = 11427 mStackSupervisor.getDefaultDisplay().getPinnedStack(); 11428 if (stack == null) { 11429 Slog.w(TAG, "dismissPip: pinned stack not found."); 11430 return; 11431 } 11432 if (stack.getWindowingMode() != WINDOWING_MODE_PINNED) { 11433 throw new IllegalArgumentException("Stack: " + stack 11434 + " doesn't support animated resize."); 11435 } 11436 if (animate) { 11437 stack.animateResizePinnedStack(null /* sourceHintBounds */, 11438 null /* destBounds */, animationDuration, false /* fromFullscreen */); 11439 } else { 11440 mStackSupervisor.moveTasksToFullscreenStackLocked(stack, true /* onTop */); 11441 } 11442 } 11443 } finally { 11444 Binder.restoreCallingIdentity(ident); 11445 } 11446 } 11447 11448 /** 11449 * Moves the top activity in the input stackId to the pinned stack. 11450 * 11451 * @param stackId Id of stack to move the top activity to pinned stack. 11452 * @param bounds Bounds to use for pinned stack. 11453 * 11454 * @return True if the top activity of the input stack was successfully moved to the pinned 11455 * stack. 11456 */ 11457 @Override 11458 public boolean moveTopActivityToPinnedStack(int stackId, Rect bounds) { 11459 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS, 11460 "moveTopActivityToPinnedStack()"); 11461 synchronized (this) { 11462 if (!mSupportsPictureInPicture) { 11463 throw new IllegalStateException("moveTopActivityToPinnedStack:" 11464 + "Device doesn't support picture-in-picture mode"); 11465 } 11466 11467 long ident = Binder.clearCallingIdentity(); 11468 try { 11469 return mStackSupervisor.moveTopStackActivityToPinnedStackLocked(stackId, bounds); 11470 } finally { 11471 Binder.restoreCallingIdentity(ident); 11472 } 11473 } 11474 } 11475 11476 @Override 11477 public void resizeStack(int stackId, Rect destBounds, boolean allowResizeInDockedMode, 11478 boolean preserveWindows, boolean animate, int animationDuration) { 11479 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS, "resizeStack()"); 11480 long ident = Binder.clearCallingIdentity(); 11481 try { 11482 synchronized (this) { 11483 if (animate) { 11484 final PinnedActivityStack stack = mStackSupervisor.getStack(stackId); 11485 if (stack == null) { 11486 Slog.w(TAG, "resizeStack: stackId " + stackId + " not found."); 11487 return; 11488 } 11489 if (stack.getWindowingMode() != WINDOWING_MODE_PINNED) { 11490 throw new IllegalArgumentException("Stack: " + stackId 11491 + " doesn't support animated resize."); 11492 } 11493 stack.animateResizePinnedStack(null /* sourceHintBounds */, destBounds, 11494 animationDuration, false /* fromFullscreen */); 11495 } else { 11496 final ActivityStack stack = mStackSupervisor.getStack(stackId); 11497 if (stack == null) { 11498 Slog.w(TAG, "resizeStack: stackId " + stackId + " not found."); 11499 return; 11500 } 11501 mStackSupervisor.resizeStackLocked(stack, destBounds, null /* tempTaskBounds */, 11502 null /* tempTaskInsetBounds */, preserveWindows, 11503 allowResizeInDockedMode, !DEFER_RESUME); 11504 } 11505 } 11506 } finally { 11507 Binder.restoreCallingIdentity(ident); 11508 } 11509 } 11510 11511 @Override 11512 public void resizeDockedStack(Rect dockedBounds, Rect tempDockedTaskBounds, 11513 Rect tempDockedTaskInsetBounds, 11514 Rect tempOtherTaskBounds, Rect tempOtherTaskInsetBounds) { 11515 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS, "resizeDockedStack()"); 11516 long ident = Binder.clearCallingIdentity(); 11517 try { 11518 synchronized (this) { 11519 mStackSupervisor.resizeDockedStackLocked(dockedBounds, tempDockedTaskBounds, 11520 tempDockedTaskInsetBounds, tempOtherTaskBounds, tempOtherTaskInsetBounds, 11521 PRESERVE_WINDOWS); 11522 } 11523 } finally { 11524 Binder.restoreCallingIdentity(ident); 11525 } 11526 } 11527 11528 @Override 11529 public void setSplitScreenResizing(boolean resizing) { 11530 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS, "setSplitScreenResizing()"); 11531 final long ident = Binder.clearCallingIdentity(); 11532 try { 11533 synchronized (this) { 11534 mStackSupervisor.setSplitScreenResizing(resizing); 11535 } 11536 } finally { 11537 Binder.restoreCallingIdentity(ident); 11538 } 11539 } 11540 11541 @Override 11542 public void resizePinnedStack(Rect pinnedBounds, Rect tempPinnedTaskBounds) { 11543 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS, "resizePinnedStack()"); 11544 final long ident = Binder.clearCallingIdentity(); 11545 try { 11546 synchronized (this) { 11547 mStackSupervisor.resizePinnedStackLocked(pinnedBounds, tempPinnedTaskBounds); 11548 } 11549 } finally { 11550 Binder.restoreCallingIdentity(ident); 11551 } 11552 } 11553 11554 /** 11555 * Try to place task to provided position. The final position might be different depending on 11556 * current user and stacks state. The task will be moved to target stack if it's currently in 11557 * different stack. 11558 */ 11559 @Override 11560 public void positionTaskInStack(int taskId, int stackId, int position) { 11561 enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "positionTaskInStack()"); 11562 synchronized (this) { 11563 long ident = Binder.clearCallingIdentity(); 11564 try { 11565 if (DEBUG_STACK) Slog.d(TAG_STACK, "positionTaskInStack: positioning task=" 11566 + taskId + " in stackId=" + stackId + " at position=" + position); 11567 final TaskRecord task = mStackSupervisor.anyTaskForIdLocked(taskId); 11568 if (task == null) { 11569 throw new IllegalArgumentException("positionTaskInStack: no task for id=" 11570 + taskId); 11571 } 11572 11573 final ActivityStack stack = mStackSupervisor.getStack(stackId); 11574 11575 if (stack == null) { 11576 throw new IllegalArgumentException("positionTaskInStack: no stack for id=" 11577 + stackId); 11578 } 11579 if (!stack.isActivityTypeStandardOrUndefined()) { 11580 throw new IllegalArgumentException("positionTaskInStack: Attempt to change" 11581 + " the position of task " + taskId + " in/to non-standard stack"); 11582 } 11583 11584 // TODO: Have the callers of this API call a separate reparent method if that is 11585 // what they intended to do vs. having this method also do reparenting. 11586 if (task.getStack() == stack) { 11587 // Change position in current stack. 11588 stack.positionChildAt(task, position); 11589 } else { 11590 // Reparent to new stack. 11591 task.reparent(stack, position, REPARENT_LEAVE_STACK_IN_PLACE, !ANIMATE, 11592 !DEFER_RESUME, "positionTaskInStack"); 11593 } 11594 } finally { 11595 Binder.restoreCallingIdentity(ident); 11596 } 11597 } 11598 } 11599 11600 @Override 11601 public List<StackInfo> getAllStackInfos() { 11602 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS, "getAllStackInfos()"); 11603 long ident = Binder.clearCallingIdentity(); 11604 try { 11605 synchronized (this) { 11606 return mStackSupervisor.getAllStackInfosLocked(); 11607 } 11608 } finally { 11609 Binder.restoreCallingIdentity(ident); 11610 } 11611 } 11612 11613 @Override 11614 public StackInfo getStackInfo(int windowingMode, int activityType) { 11615 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS, "getStackInfo()"); 11616 long ident = Binder.clearCallingIdentity(); 11617 try { 11618 synchronized (this) { 11619 return mStackSupervisor.getStackInfo(windowingMode, activityType); 11620 } 11621 } finally { 11622 Binder.restoreCallingIdentity(ident); 11623 } 11624 } 11625 11626 @Override 11627 public int getTaskForActivity(IBinder token, boolean onlyRoot) { 11628 synchronized(this) { 11629 return ActivityRecord.getTaskForActivityLocked(token, onlyRoot); 11630 } 11631 } 11632 11633 @Override 11634 public void updateDeviceOwner(String packageName) { 11635 final int callingUid = Binder.getCallingUid(); 11636 if (callingUid != 0 && callingUid != SYSTEM_UID) { 11637 throw new SecurityException("updateDeviceOwner called from non-system process"); 11638 } 11639 synchronized (this) { 11640 mDeviceOwnerName = packageName; 11641 } 11642 } 11643 11644 @Override 11645 public void updateLockTaskPackages(int userId, String[] packages) { 11646 final int callingUid = Binder.getCallingUid(); 11647 if (callingUid != 0 && callingUid != SYSTEM_UID) { 11648 enforceCallingPermission(android.Manifest.permission.UPDATE_LOCK_TASK_PACKAGES, 11649 "updateLockTaskPackages()"); 11650 } 11651 synchronized (this) { 11652 if (DEBUG_LOCKTASK) Slog.w(TAG_LOCKTASK, "Whitelisting " + userId + ":" + 11653 Arrays.toString(packages)); 11654 mLockTaskController.updateLockTaskPackages(userId, packages); 11655 } 11656 } 11657 11658 @Override 11659 public void updateLockTaskFeatures(int userId, int flags) { 11660 final int callingUid = Binder.getCallingUid(); 11661 if (callingUid != 0 && callingUid != SYSTEM_UID) { 11662 enforceCallingPermission(android.Manifest.permission.UPDATE_LOCK_TASK_PACKAGES, 11663 "updateLockTaskFeatures()"); 11664 } 11665 synchronized (this) { 11666 if (DEBUG_LOCKTASK) Slog.w(TAG_LOCKTASK, "Allowing features " + userId + ":0x" + 11667 Integer.toHexString(flags)); 11668 mLockTaskController.updateLockTaskFeatures(userId, flags); 11669 } 11670 } 11671 11672 private void startLockTaskModeLocked(@Nullable TaskRecord task, boolean isSystemCaller) { 11673 if (DEBUG_LOCKTASK) Slog.w(TAG_LOCKTASK, "startLockTaskModeLocked: " + task); 11674 if (task == null || task.mLockTaskAuth == LOCK_TASK_AUTH_DONT_LOCK) { 11675 return; 11676 } 11677 11678 final ActivityStack stack = mStackSupervisor.getFocusedStack(); 11679 if (stack == null || task != stack.topTask()) { 11680 throw new IllegalArgumentException("Invalid task, not in foreground"); 11681 } 11682 11683 // {@code isSystemCaller} is used to distinguish whether this request is initiated by the 11684 // system or a specific app. 11685 // * System-initiated requests will only start the pinned mode (screen pinning) 11686 // * App-initiated requests 11687 // - will put the device in fully locked mode (LockTask), if the app is whitelisted 11688 // - will start the pinned mode, otherwise 11689 final int callingUid = Binder.getCallingUid(); 11690 long ident = Binder.clearCallingIdentity(); 11691 try { 11692 // When a task is locked, dismiss the pinned stack if it exists 11693 mStackSupervisor.removeStacksInWindowingModes(WINDOWING_MODE_PINNED); 11694 11695 mLockTaskController.startLockTaskMode(task, isSystemCaller, callingUid); 11696 } finally { 11697 Binder.restoreCallingIdentity(ident); 11698 } 11699 } 11700 11701 @Override 11702 public void startLockTaskModeByToken(IBinder token) { 11703 synchronized (this) { 11704 final ActivityRecord r = ActivityRecord.forTokenLocked(token); 11705 if (r == null) { 11706 return; 11707 } 11708 startLockTaskModeLocked(r.getTask(), false /* isSystemCaller */); 11709 } 11710 } 11711 11712 @Override 11713 public void startSystemLockTaskMode(int taskId) throws RemoteException { 11714 enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "startSystemLockTaskMode"); 11715 // This makes inner call to look as if it was initiated by system. 11716 long ident = Binder.clearCallingIdentity(); 11717 try { 11718 synchronized (this) { 11719 final TaskRecord task = mStackSupervisor.anyTaskForIdLocked(taskId); 11720 11721 // When starting lock task mode the stack must be in front and focused 11722 task.getStack().moveToFront("startSystemLockTaskMode"); 11723 startLockTaskModeLocked(task, true /* isSystemCaller */); 11724 } 11725 } finally { 11726 Binder.restoreCallingIdentity(ident); 11727 } 11728 } 11729 11730 @Override 11731 public void stopLockTaskModeByToken(IBinder token) { 11732 synchronized (this) { 11733 final ActivityRecord r = ActivityRecord.forTokenLocked(token); 11734 if (r == null) { 11735 return; 11736 } 11737 stopLockTaskModeInternal(r.getTask(), false /* isSystemCaller */); 11738 } 11739 } 11740 11741 /** 11742 * This API should be called by SystemUI only when user perform certain action to dismiss 11743 * lock task mode. We should only dismiss pinned lock task mode in this case. 11744 */ 11745 @Override 11746 public void stopSystemLockTaskMode() throws RemoteException { 11747 enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "stopSystemLockTaskMode"); 11748 stopLockTaskModeInternal(null, true /* isSystemCaller */); 11749 } 11750 11751 private void stopLockTaskModeInternal(@Nullable TaskRecord task, boolean isSystemCaller) { 11752 final int callingUid = Binder.getCallingUid(); 11753 long ident = Binder.clearCallingIdentity(); 11754 try { 11755 synchronized (this) { 11756 mLockTaskController.stopLockTaskMode(task, isSystemCaller, callingUid); 11757 } 11758 // Launch in-call UI if a call is ongoing. This is necessary to allow stopping the lock 11759 // task and jumping straight into a call in the case of emergency call back. 11760 TelecomManager tm = (TelecomManager) mContext.getSystemService(Context.TELECOM_SERVICE); 11761 if (tm != null) { 11762 tm.showInCallScreen(false); 11763 } 11764 } finally { 11765 Binder.restoreCallingIdentity(ident); 11766 } 11767 } 11768 11769 @Override 11770 public boolean isInLockTaskMode() { 11771 return getLockTaskModeState() != LOCK_TASK_MODE_NONE; 11772 } 11773 11774 @Override 11775 public int getLockTaskModeState() { 11776 synchronized (this) { 11777 return mLockTaskController.getLockTaskModeState(); 11778 } 11779 } 11780 11781 @Override 11782 public void showLockTaskEscapeMessage(IBinder token) { 11783 synchronized (this) { 11784 final ActivityRecord r = ActivityRecord.forTokenLocked(token); 11785 if (r == null) { 11786 return; 11787 } 11788 mLockTaskController.showLockTaskToast(); 11789 } 11790 } 11791 11792 @Override 11793 public void setDisablePreviewScreenshots(IBinder token, boolean disable) 11794 throws RemoteException { 11795 synchronized (this) { 11796 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 11797 if (r == null) { 11798 Slog.w(TAG, "setDisablePreviewScreenshots: Unable to find activity for token=" 11799 + token); 11800 return; 11801 } 11802 final long origId = Binder.clearCallingIdentity(); 11803 try { 11804 r.setDisablePreviewScreenshots(disable); 11805 } finally { 11806 Binder.restoreCallingIdentity(origId); 11807 } 11808 } 11809 } 11810 11811 // ========================================================= 11812 // CONTENT PROVIDERS 11813 // ========================================================= 11814 11815 private final List<ProviderInfo> generateApplicationProvidersLocked(ProcessRecord app) { 11816 List<ProviderInfo> providers = null; 11817 try { 11818 providers = AppGlobals.getPackageManager() 11819 .queryContentProviders(app.processName, app.uid, 11820 STOCK_PM_FLAGS | PackageManager.GET_URI_PERMISSION_PATTERNS 11821 | MATCH_DEBUG_TRIAGED_MISSING, /*metadastaKey=*/ null) 11822 .getList(); 11823 } catch (RemoteException ex) { 11824 } 11825 if (DEBUG_MU) Slog.v(TAG_MU, 11826 "generateApplicationProvidersLocked, app.info.uid = " + app.uid); 11827 int userId = app.userId; 11828 if (providers != null) { 11829 int N = providers.size(); 11830 app.pubProviders.ensureCapacity(N + app.pubProviders.size()); 11831 for (int i=0; i<N; i++) { 11832 // TODO: keep logic in sync with installEncryptionUnawareProviders 11833 ProviderInfo cpi = 11834 (ProviderInfo)providers.get(i); 11835 boolean singleton = isSingleton(cpi.processName, cpi.applicationInfo, 11836 cpi.name, cpi.flags); 11837 if (singleton && UserHandle.getUserId(app.uid) != UserHandle.USER_SYSTEM) { 11838 // This is a singleton provider, but a user besides the 11839 // default user is asking to initialize a process it runs 11840 // in... well, no, it doesn't actually run in this process, 11841 // it runs in the process of the default user. Get rid of it. 11842 providers.remove(i); 11843 N--; 11844 i--; 11845 continue; 11846 } 11847 11848 ComponentName comp = new ComponentName(cpi.packageName, cpi.name); 11849 ContentProviderRecord cpr = mProviderMap.getProviderByClass(comp, userId); 11850 if (cpr == null) { 11851 cpr = new ContentProviderRecord(this, cpi, app.info, comp, singleton); 11852 mProviderMap.putProviderByClass(comp, cpr); 11853 } 11854 if (DEBUG_MU) Slog.v(TAG_MU, 11855 "generateApplicationProvidersLocked, cpi.uid = " + cpr.uid); 11856 app.pubProviders.put(cpi.name, cpr); 11857 if (!cpi.multiprocess || !"android".equals(cpi.packageName)) { 11858 // Don't add this if it is a platform component that is marked 11859 // to run in multiple processes, because this is actually 11860 // part of the framework so doesn't make sense to track as a 11861 // separate apk in the process. 11862 app.addPackage(cpi.applicationInfo.packageName, cpi.applicationInfo.versionCode, 11863 mProcessStats); 11864 } 11865 notifyPackageUse(cpi.applicationInfo.packageName, 11866 PackageManager.NOTIFY_PACKAGE_USE_CONTENT_PROVIDER); 11867 } 11868 } 11869 return providers; 11870 } 11871 11872 /** 11873 * Check if the calling UID has a possible chance at accessing the provider 11874 * at the given authority and user. 11875 */ 11876 public String checkContentProviderAccess(String authority, int userId) { 11877 if (userId == UserHandle.USER_ALL) { 11878 mContext.enforceCallingOrSelfPermission( 11879 Manifest.permission.INTERACT_ACROSS_USERS_FULL, TAG); 11880 userId = UserHandle.getCallingUserId(); 11881 } 11882 11883 ProviderInfo cpi = null; 11884 try { 11885 cpi = AppGlobals.getPackageManager().resolveContentProvider(authority, 11886 STOCK_PM_FLAGS | PackageManager.GET_URI_PERMISSION_PATTERNS 11887 | PackageManager.MATCH_DISABLED_COMPONENTS 11888 | PackageManager.MATCH_DIRECT_BOOT_AWARE 11889 | PackageManager.MATCH_DIRECT_BOOT_UNAWARE, 11890 userId); 11891 } catch (RemoteException ignored) { 11892 } 11893 if (cpi == null) { 11894 return "Failed to find provider " + authority + " for user " + userId 11895 + "; expected to find a valid ContentProvider for this authority"; 11896 } 11897 11898 ProcessRecord r = null; 11899 synchronized (mPidsSelfLocked) { 11900 r = mPidsSelfLocked.get(Binder.getCallingPid()); 11901 } 11902 if (r == null) { 11903 return "Failed to find PID " + Binder.getCallingPid(); 11904 } 11905 11906 synchronized (this) { 11907 return checkContentProviderPermissionLocked(cpi, r, userId, true); 11908 } 11909 } 11910 11911 /** 11912 * Check if {@link ProcessRecord} has a possible chance at accessing the 11913 * given {@link ProviderInfo}. Final permission checking is always done 11914 * in {@link ContentProvider}. 11915 */ 11916 private final String checkContentProviderPermissionLocked( 11917 ProviderInfo cpi, ProcessRecord r, int userId, boolean checkUser) { 11918 final int callingPid = (r != null) ? r.pid : Binder.getCallingPid(); 11919 final int callingUid = (r != null) ? r.uid : Binder.getCallingUid(); 11920 boolean checkedGrants = false; 11921 if (checkUser) { 11922 // Looking for cross-user grants before enforcing the typical cross-users permissions 11923 int tmpTargetUserId = mUserController.unsafeConvertIncomingUser(userId); 11924 if (tmpTargetUserId != UserHandle.getUserId(callingUid)) { 11925 if (checkAuthorityGrants(callingUid, cpi, tmpTargetUserId, checkUser)) { 11926 return null; 11927 } 11928 checkedGrants = true; 11929 } 11930 userId = mUserController.handleIncomingUser(callingPid, callingUid, userId, false, 11931 ALLOW_NON_FULL, "checkContentProviderPermissionLocked " + cpi.authority, null); 11932 if (userId != tmpTargetUserId) { 11933 // When we actually went to determine the final targer user ID, this ended 11934 // up different than our initial check for the authority. This is because 11935 // they had asked for USER_CURRENT_OR_SELF and we ended up switching to 11936 // SELF. So we need to re-check the grants again. 11937 checkedGrants = false; 11938 } 11939 } 11940 if (checkComponentPermission(cpi.readPermission, callingPid, callingUid, 11941 cpi.applicationInfo.uid, cpi.exported) 11942 == PackageManager.PERMISSION_GRANTED) { 11943 return null; 11944 } 11945 if (checkComponentPermission(cpi.writePermission, callingPid, callingUid, 11946 cpi.applicationInfo.uid, cpi.exported) 11947 == PackageManager.PERMISSION_GRANTED) { 11948 return null; 11949 } 11950 11951 PathPermission[] pps = cpi.pathPermissions; 11952 if (pps != null) { 11953 int i = pps.length; 11954 while (i > 0) { 11955 i--; 11956 PathPermission pp = pps[i]; 11957 String pprperm = pp.getReadPermission(); 11958 if (pprperm != null && checkComponentPermission(pprperm, callingPid, callingUid, 11959 cpi.applicationInfo.uid, cpi.exported) 11960 == PackageManager.PERMISSION_GRANTED) { 11961 return null; 11962 } 11963 String ppwperm = pp.getWritePermission(); 11964 if (ppwperm != null && checkComponentPermission(ppwperm, callingPid, callingUid, 11965 cpi.applicationInfo.uid, cpi.exported) 11966 == PackageManager.PERMISSION_GRANTED) { 11967 return null; 11968 } 11969 } 11970 } 11971 if (!checkedGrants && checkAuthorityGrants(callingUid, cpi, userId, checkUser)) { 11972 return null; 11973 } 11974 11975 final String suffix; 11976 if (!cpi.exported) { 11977 suffix = " that is not exported from UID " + cpi.applicationInfo.uid; 11978 } else if (android.Manifest.permission.MANAGE_DOCUMENTS.equals(cpi.readPermission)) { 11979 suffix = " requires that you obtain access using ACTION_OPEN_DOCUMENT or related APIs"; 11980 } else { 11981 suffix = " requires " + cpi.readPermission + " or " + cpi.writePermission; 11982 } 11983 final String msg = "Permission Denial: opening provider " + cpi.name 11984 + " from " + (r != null ? r : "(null)") + " (pid=" + callingPid 11985 + ", uid=" + callingUid + ")" + suffix; 11986 Slog.w(TAG, msg); 11987 return msg; 11988 } 11989 11990 /** 11991 * Returns if the ContentProvider has granted a uri to callingUid 11992 */ 11993 boolean checkAuthorityGrants(int callingUid, ProviderInfo cpi, int userId, boolean checkUser) { 11994 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get(callingUid); 11995 if (perms != null) { 11996 for (int i=perms.size()-1; i>=0; i--) { 11997 GrantUri grantUri = perms.keyAt(i); 11998 if (grantUri.sourceUserId == userId || !checkUser) { 11999 if (matchesProvider(grantUri.uri, cpi)) { 12000 return true; 12001 } 12002 } 12003 } 12004 } 12005 return false; 12006 } 12007 12008 /** 12009 * Returns true if the uri authority is one of the authorities specified in the provider. 12010 */ 12011 boolean matchesProvider(Uri uri, ProviderInfo cpi) { 12012 String uriAuth = uri.getAuthority(); 12013 String cpiAuth = cpi.authority; 12014 if (cpiAuth.indexOf(';') == -1) { 12015 return cpiAuth.equals(uriAuth); 12016 } 12017 String[] cpiAuths = cpiAuth.split(";"); 12018 int length = cpiAuths.length; 12019 for (int i = 0; i < length; i++) { 12020 if (cpiAuths[i].equals(uriAuth)) return true; 12021 } 12022 return false; 12023 } 12024 12025 ContentProviderConnection incProviderCountLocked(ProcessRecord r, 12026 final ContentProviderRecord cpr, IBinder externalProcessToken, boolean stable) { 12027 if (r != null) { 12028 for (int i=0; i<r.conProviders.size(); i++) { 12029 ContentProviderConnection conn = r.conProviders.get(i); 12030 if (conn.provider == cpr) { 12031 if (DEBUG_PROVIDER) Slog.v(TAG_PROVIDER, 12032 "Adding provider requested by " 12033 + r.processName + " from process " 12034 + cpr.info.processName + ": " + cpr.name.flattenToShortString() 12035 + " scnt=" + conn.stableCount + " uscnt=" + conn.unstableCount); 12036 if (stable) { 12037 conn.stableCount++; 12038 conn.numStableIncs++; 12039 } else { 12040 conn.unstableCount++; 12041 conn.numUnstableIncs++; 12042 } 12043 return conn; 12044 } 12045 } 12046 ContentProviderConnection conn = new ContentProviderConnection(cpr, r); 12047 if (stable) { 12048 conn.stableCount = 1; 12049 conn.numStableIncs = 1; 12050 } else { 12051 conn.unstableCount = 1; 12052 conn.numUnstableIncs = 1; 12053 } 12054 cpr.connections.add(conn); 12055 r.conProviders.add(conn); 12056 startAssociationLocked(r.uid, r.processName, r.curProcState, 12057 cpr.uid, cpr.name, cpr.info.processName); 12058 return conn; 12059 } 12060 cpr.addExternalProcessHandleLocked(externalProcessToken); 12061 return null; 12062 } 12063 12064 boolean decProviderCountLocked(ContentProviderConnection conn, 12065 ContentProviderRecord cpr, IBinder externalProcessToken, boolean stable) { 12066 if (conn != null) { 12067 cpr = conn.provider; 12068 if (DEBUG_PROVIDER) Slog.v(TAG_PROVIDER, 12069 "Removing provider requested by " 12070 + conn.client.processName + " from process " 12071 + cpr.info.processName + ": " + cpr.name.flattenToShortString() 12072 + " scnt=" + conn.stableCount + " uscnt=" + conn.unstableCount); 12073 if (stable) { 12074 conn.stableCount--; 12075 } else { 12076 conn.unstableCount--; 12077 } 12078 if (conn.stableCount == 0 && conn.unstableCount == 0) { 12079 cpr.connections.remove(conn); 12080 conn.client.conProviders.remove(conn); 12081 if (conn.client.setProcState < ActivityManager.PROCESS_STATE_LAST_ACTIVITY) { 12082 // The client is more important than last activity -- note the time this 12083 // is happening, so we keep the old provider process around a bit as last 12084 // activity to avoid thrashing it. 12085 if (cpr.proc != null) { 12086 cpr.proc.lastProviderTime = SystemClock.uptimeMillis(); 12087 } 12088 } 12089 stopAssociationLocked(conn.client.uid, conn.client.processName, cpr.uid, cpr.name); 12090 return true; 12091 } 12092 return false; 12093 } 12094 cpr.removeExternalProcessHandleLocked(externalProcessToken); 12095 return false; 12096 } 12097 12098 private void checkTime(long startTime, String where) { 12099 long now = SystemClock.uptimeMillis(); 12100 if ((now-startTime) > 50) { 12101 // If we are taking more than 50ms, log about it. 12102 Slog.w(TAG, "Slow operation: " + (now-startTime) + "ms so far, now at " + where); 12103 } 12104 } 12105 12106 private static final int[] PROCESS_STATE_STATS_FORMAT = new int[] { 12107 PROC_SPACE_TERM, 12108 PROC_SPACE_TERM|PROC_PARENS, 12109 PROC_SPACE_TERM|PROC_CHAR|PROC_OUT_LONG, // 3: process state 12110 }; 12111 12112 private final long[] mProcessStateStatsLongs = new long[1]; 12113 12114 private boolean isProcessAliveLocked(ProcessRecord proc) { 12115 if (proc.pid <= 0) { 12116 if (DEBUG_OOM_ADJ) Slog.d(TAG, "Process hasn't started yet: " + proc); 12117 return false; 12118 } 12119 if (proc.procStatFile == null) { 12120 proc.procStatFile = "/proc/" + proc.pid + "/stat"; 12121 } 12122 mProcessStateStatsLongs[0] = 0; 12123 if (!readProcFile(proc.procStatFile, PROCESS_STATE_STATS_FORMAT, null, 12124 mProcessStateStatsLongs, null)) { 12125 if (DEBUG_OOM_ADJ) Slog.d(TAG, "UNABLE TO RETRIEVE STATE FOR " + proc.procStatFile); 12126 return false; 12127 } 12128 final long state = mProcessStateStatsLongs[0]; 12129 if (DEBUG_OOM_ADJ) Slog.d(TAG, "RETRIEVED STATE FOR " + proc.procStatFile + ": " 12130 + (char)state); 12131 return state != 'Z' && state != 'X' && state != 'x' && state != 'K'; 12132 } 12133 12134 private ContentProviderHolder getContentProviderImpl(IApplicationThread caller, 12135 String name, IBinder token, boolean stable, int userId) { 12136 ContentProviderRecord cpr; 12137 ContentProviderConnection conn = null; 12138 ProviderInfo cpi = null; 12139 12140 synchronized(this) { 12141 long startTime = SystemClock.uptimeMillis(); 12142 12143 ProcessRecord r = null; 12144 if (caller != null) { 12145 r = getRecordForAppLocked(caller); 12146 if (r == null) { 12147 throw new SecurityException( 12148 "Unable to find app for caller " + caller 12149 + " (pid=" + Binder.getCallingPid() 12150 + ") when getting content provider " + name); 12151 } 12152 } 12153 12154 boolean checkCrossUser = true; 12155 12156 checkTime(startTime, "getContentProviderImpl: getProviderByName"); 12157 12158 // First check if this content provider has been published... 12159 cpr = mProviderMap.getProviderByName(name, userId); 12160 // If that didn't work, check if it exists for user 0 and then 12161 // verify that it's a singleton provider before using it. 12162 if (cpr == null && userId != UserHandle.USER_SYSTEM) { 12163 cpr = mProviderMap.getProviderByName(name, UserHandle.USER_SYSTEM); 12164 if (cpr != null) { 12165 cpi = cpr.info; 12166 if (isSingleton(cpi.processName, cpi.applicationInfo, 12167 cpi.name, cpi.flags) 12168 && isValidSingletonCall(r.uid, cpi.applicationInfo.uid)) { 12169 userId = UserHandle.USER_SYSTEM; 12170 checkCrossUser = false; 12171 } else { 12172 cpr = null; 12173 cpi = null; 12174 } 12175 } 12176 } 12177 12178 boolean providerRunning = cpr != null && cpr.proc != null && !cpr.proc.killed; 12179 if (providerRunning) { 12180 cpi = cpr.info; 12181 String msg; 12182 checkTime(startTime, "getContentProviderImpl: before checkContentProviderPermission"); 12183 if ((msg = checkContentProviderPermissionLocked(cpi, r, userId, checkCrossUser)) 12184 != null) { 12185 throw new SecurityException(msg); 12186 } 12187 checkTime(startTime, "getContentProviderImpl: after checkContentProviderPermission"); 12188 12189 if (r != null && cpr.canRunHere(r)) { 12190 // This provider has been published or is in the process 12191 // of being published... but it is also allowed to run 12192 // in the caller's process, so don't make a connection 12193 // and just let the caller instantiate its own instance. 12194 ContentProviderHolder holder = cpr.newHolder(null); 12195 // don't give caller the provider object, it needs 12196 // to make its own. 12197 holder.provider = null; 12198 return holder; 12199 } 12200 // Don't expose providers between normal apps and instant apps 12201 try { 12202 if (AppGlobals.getPackageManager() 12203 .resolveContentProvider(name, 0 /*flags*/, userId) == null) { 12204 return null; 12205 } 12206 } catch (RemoteException e) { 12207 } 12208 12209 final long origId = Binder.clearCallingIdentity(); 12210 12211 checkTime(startTime, "getContentProviderImpl: incProviderCountLocked"); 12212 12213 // In this case the provider instance already exists, so we can 12214 // return it right away. 12215 conn = incProviderCountLocked(r, cpr, token, stable); 12216 if (conn != null && (conn.stableCount+conn.unstableCount) == 1) { 12217 if (cpr.proc != null && r.setAdj <= ProcessList.PERCEPTIBLE_APP_ADJ) { 12218 // If this is a perceptible app accessing the provider, 12219 // make sure to count it as being accessed and thus 12220 // back up on the LRU list. This is good because 12221 // content providers are often expensive to start. 12222 checkTime(startTime, "getContentProviderImpl: before updateLruProcess"); 12223 updateLruProcessLocked(cpr.proc, false, null); 12224 checkTime(startTime, "getContentProviderImpl: after updateLruProcess"); 12225 } 12226 } 12227 12228 checkTime(startTime, "getContentProviderImpl: before updateOomAdj"); 12229 final int verifiedAdj = cpr.proc.verifiedAdj; 12230 boolean success = updateOomAdjLocked(cpr.proc, true); 12231 // XXX things have changed so updateOomAdjLocked doesn't actually tell us 12232 // if the process has been successfully adjusted. So to reduce races with 12233 // it, we will check whether the process still exists. Note that this doesn't 12234 // completely get rid of races with LMK killing the process, but should make 12235 // them much smaller. 12236 if (success && verifiedAdj != cpr.proc.setAdj && !isProcessAliveLocked(cpr.proc)) { 12237 success = false; 12238 } 12239 maybeUpdateProviderUsageStatsLocked(r, cpr.info.packageName, name); 12240 checkTime(startTime, "getContentProviderImpl: after updateOomAdj"); 12241 if (DEBUG_PROVIDER) Slog.i(TAG_PROVIDER, "Adjust success: " + success); 12242 // NOTE: there is still a race here where a signal could be 12243 // pending on the process even though we managed to update its 12244 // adj level. Not sure what to do about this, but at least 12245 // the race is now smaller. 12246 if (!success) { 12247 // Uh oh... it looks like the provider's process 12248 // has been killed on us. We need to wait for a new 12249 // process to be started, and make sure its death 12250 // doesn't kill our process. 12251 Slog.i(TAG, "Existing provider " + cpr.name.flattenToShortString() 12252 + " is crashing; detaching " + r); 12253 boolean lastRef = decProviderCountLocked(conn, cpr, token, stable); 12254 checkTime(startTime, "getContentProviderImpl: before appDied"); 12255 appDiedLocked(cpr.proc); 12256 checkTime(startTime, "getContentProviderImpl: after appDied"); 12257 if (!lastRef) { 12258 // This wasn't the last ref our process had on 12259 // the provider... we have now been killed, bail. 12260 return null; 12261 } 12262 providerRunning = false; 12263 conn = null; 12264 } else { 12265 cpr.proc.verifiedAdj = cpr.proc.setAdj; 12266 } 12267 12268 Binder.restoreCallingIdentity(origId); 12269 } 12270 12271 if (!providerRunning) { 12272 try { 12273 checkTime(startTime, "getContentProviderImpl: before resolveContentProvider"); 12274 cpi = AppGlobals.getPackageManager(). 12275 resolveContentProvider(name, 12276 STOCK_PM_FLAGS | PackageManager.GET_URI_PERMISSION_PATTERNS, userId); 12277 checkTime(startTime, "getContentProviderImpl: after resolveContentProvider"); 12278 } catch (RemoteException ex) { 12279 } 12280 if (cpi == null) { 12281 return null; 12282 } 12283 // If the provider is a singleton AND 12284 // (it's a call within the same user || the provider is a 12285 // privileged app) 12286 // Then allow connecting to the singleton provider 12287 boolean singleton = isSingleton(cpi.processName, cpi.applicationInfo, 12288 cpi.name, cpi.flags) 12289 && isValidSingletonCall(r.uid, cpi.applicationInfo.uid); 12290 if (singleton) { 12291 userId = UserHandle.USER_SYSTEM; 12292 } 12293 cpi.applicationInfo = getAppInfoForUser(cpi.applicationInfo, userId); 12294 checkTime(startTime, "getContentProviderImpl: got app info for user"); 12295 12296 String msg; 12297 checkTime(startTime, "getContentProviderImpl: before checkContentProviderPermission"); 12298 if ((msg = checkContentProviderPermissionLocked(cpi, r, userId, !singleton)) 12299 != null) { 12300 throw new SecurityException(msg); 12301 } 12302 checkTime(startTime, "getContentProviderImpl: after checkContentProviderPermission"); 12303 12304 if (!mProcessesReady 12305 && !cpi.processName.equals("system")) { 12306 // If this content provider does not run in the system 12307 // process, and the system is not yet ready to run other 12308 // processes, then fail fast instead of hanging. 12309 throw new IllegalArgumentException( 12310 "Attempt to launch content provider before system ready"); 12311 } 12312 12313 // If system providers are not installed yet we aggressively crash to avoid 12314 // creating multiple instance of these providers and then bad things happen! 12315 if (!mSystemProvidersInstalled && cpi.applicationInfo.isSystemApp() 12316 && "system".equals(cpi.processName)) { 12317 throw new IllegalStateException("Cannot access system provider: '" 12318 + cpi.authority + "' before system providers are installed!"); 12319 } 12320 12321 // Make sure that the user who owns this provider is running. If not, 12322 // we don't want to allow it to run. 12323 if (!mUserController.isUserRunning(userId, 0)) { 12324 Slog.w(TAG, "Unable to launch app " 12325 + cpi.applicationInfo.packageName + "/" 12326 + cpi.applicationInfo.uid + " for provider " 12327 + name + ": user " + userId + " is stopped"); 12328 return null; 12329 } 12330 12331 ComponentName comp = new ComponentName(cpi.packageName, cpi.name); 12332 checkTime(startTime, "getContentProviderImpl: before getProviderByClass"); 12333 cpr = mProviderMap.getProviderByClass(comp, userId); 12334 checkTime(startTime, "getContentProviderImpl: after getProviderByClass"); 12335 final boolean firstClass = cpr == null; 12336 if (firstClass) { 12337 final long ident = Binder.clearCallingIdentity(); 12338 12339 // If permissions need a review before any of the app components can run, 12340 // we return no provider and launch a review activity if the calling app 12341 // is in the foreground. 12342 if (mPermissionReviewRequired) { 12343 if (!requestTargetProviderPermissionsReviewIfNeededLocked(cpi, r, userId)) { 12344 return null; 12345 } 12346 } 12347 12348 try { 12349 checkTime(startTime, "getContentProviderImpl: before getApplicationInfo"); 12350 ApplicationInfo ai = 12351 AppGlobals.getPackageManager(). 12352 getApplicationInfo( 12353 cpi.applicationInfo.packageName, 12354 STOCK_PM_FLAGS, userId); 12355 checkTime(startTime, "getContentProviderImpl: after getApplicationInfo"); 12356 if (ai == null) { 12357 Slog.w(TAG, "No package info for content provider " 12358 + cpi.name); 12359 return null; 12360 } 12361 ai = getAppInfoForUser(ai, userId); 12362 cpr = new ContentProviderRecord(this, cpi, ai, comp, singleton); 12363 } catch (RemoteException ex) { 12364 // pm is in same process, this will never happen. 12365 } finally { 12366 Binder.restoreCallingIdentity(ident); 12367 } 12368 } 12369 12370 checkTime(startTime, "getContentProviderImpl: now have ContentProviderRecord"); 12371 12372 if (r != null && cpr.canRunHere(r)) { 12373 // If this is a multiprocess provider, then just return its 12374 // info and allow the caller to instantiate it. Only do 12375 // this if the provider is the same user as the caller's 12376 // process, or can run as root (so can be in any process). 12377 return cpr.newHolder(null); 12378 } 12379 12380 if (DEBUG_PROVIDER) Slog.w(TAG_PROVIDER, "LAUNCHING REMOTE PROVIDER (myuid " 12381 + (r != null ? r.uid : null) + " pruid " + cpr.appInfo.uid + "): " 12382 + cpr.info.name + " callers=" + Debug.getCallers(6)); 12383 12384 // This is single process, and our app is now connecting to it. 12385 // See if we are already in the process of launching this 12386 // provider. 12387 final int N = mLaunchingProviders.size(); 12388 int i; 12389 for (i = 0; i < N; i++) { 12390 if (mLaunchingProviders.get(i) == cpr) { 12391 break; 12392 } 12393 } 12394 12395 // If the provider is not already being launched, then get it 12396 // started. 12397 if (i >= N) { 12398 final long origId = Binder.clearCallingIdentity(); 12399 12400 try { 12401 // Content provider is now in use, its package can't be stopped. 12402 try { 12403 checkTime(startTime, "getContentProviderImpl: before set stopped state"); 12404 AppGlobals.getPackageManager().setPackageStoppedState( 12405 cpr.appInfo.packageName, false, userId); 12406 checkTime(startTime, "getContentProviderImpl: after set stopped state"); 12407 } catch (RemoteException e) { 12408 } catch (IllegalArgumentException e) { 12409 Slog.w(TAG, "Failed trying to unstop package " 12410 + cpr.appInfo.packageName + ": " + e); 12411 } 12412 12413 // Use existing process if already started 12414 checkTime(startTime, "getContentProviderImpl: looking for process record"); 12415 ProcessRecord proc = getProcessRecordLocked( 12416 cpi.processName, cpr.appInfo.uid, false); 12417 if (proc != null && proc.thread != null && !proc.killed) { 12418 if (DEBUG_PROVIDER) Slog.d(TAG_PROVIDER, 12419 "Installing in existing process " + proc); 12420 if (!proc.pubProviders.containsKey(cpi.name)) { 12421 checkTime(startTime, "getContentProviderImpl: scheduling install"); 12422 proc.pubProviders.put(cpi.name, cpr); 12423 try { 12424 proc.thread.scheduleInstallProvider(cpi); 12425 } catch (RemoteException e) { 12426 } 12427 } 12428 } else { 12429 checkTime(startTime, "getContentProviderImpl: before start process"); 12430 proc = startProcessLocked(cpi.processName, 12431 cpr.appInfo, false, 0, "content provider", 12432 new ComponentName(cpi.applicationInfo.packageName, 12433 cpi.name), false, false, false); 12434 checkTime(startTime, "getContentProviderImpl: after start process"); 12435 if (proc == null) { 12436 Slog.w(TAG, "Unable to launch app " 12437 + cpi.applicationInfo.packageName + "/" 12438 + cpi.applicationInfo.uid + " for provider " 12439 + name + ": process is bad"); 12440 return null; 12441 } 12442 } 12443 cpr.launchingApp = proc; 12444 mLaunchingProviders.add(cpr); 12445 } finally { 12446 Binder.restoreCallingIdentity(origId); 12447 } 12448 } 12449 12450 checkTime(startTime, "getContentProviderImpl: updating data structures"); 12451 12452 // Make sure the provider is published (the same provider class 12453 // may be published under multiple names). 12454 if (firstClass) { 12455 mProviderMap.putProviderByClass(comp, cpr); 12456 } 12457 12458 mProviderMap.putProviderByName(name, cpr); 12459 conn = incProviderCountLocked(r, cpr, token, stable); 12460 if (conn != null) { 12461 conn.waiting = true; 12462 } 12463 } 12464 checkTime(startTime, "getContentProviderImpl: done!"); 12465 12466 grantEphemeralAccessLocked(userId, null /*intent*/, 12467 cpi.applicationInfo.uid, UserHandle.getAppId(Binder.getCallingUid())); 12468 } 12469 12470 // Wait for the provider to be published... 12471 synchronized (cpr) { 12472 while (cpr.provider == null) { 12473 if (cpr.launchingApp == null) { 12474 Slog.w(TAG, "Unable to launch app " 12475 + cpi.applicationInfo.packageName + "/" 12476 + cpi.applicationInfo.uid + " for provider " 12477 + name + ": launching app became null"); 12478 EventLog.writeEvent(EventLogTags.AM_PROVIDER_LOST_PROCESS, 12479 UserHandle.getUserId(cpi.applicationInfo.uid), 12480 cpi.applicationInfo.packageName, 12481 cpi.applicationInfo.uid, name); 12482 return null; 12483 } 12484 try { 12485 if (DEBUG_MU) Slog.v(TAG_MU, 12486 "Waiting to start provider " + cpr 12487 + " launchingApp=" + cpr.launchingApp); 12488 if (conn != null) { 12489 conn.waiting = true; 12490 } 12491 cpr.wait(); 12492 } catch (InterruptedException ex) { 12493 } finally { 12494 if (conn != null) { 12495 conn.waiting = false; 12496 } 12497 } 12498 } 12499 } 12500 return cpr != null ? cpr.newHolder(conn) : null; 12501 } 12502 12503 private boolean requestTargetProviderPermissionsReviewIfNeededLocked(ProviderInfo cpi, 12504 ProcessRecord r, final int userId) { 12505 if (getPackageManagerInternalLocked().isPermissionsReviewRequired( 12506 cpi.packageName, userId)) { 12507 12508 final boolean callerForeground = r == null || r.setSchedGroup 12509 != ProcessList.SCHED_GROUP_BACKGROUND; 12510 12511 // Show a permission review UI only for starting from a foreground app 12512 if (!callerForeground) { 12513 Slog.w(TAG, "u" + userId + " Instantiating a provider in package" 12514 + cpi.packageName + " requires a permissions review"); 12515 return false; 12516 } 12517 12518 final Intent intent = new Intent(Intent.ACTION_REVIEW_PERMISSIONS); 12519 intent.addFlags(FLAG_ACTIVITY_NEW_TASK 12520 | Intent.FLAG_ACTIVITY_EXCLUDE_FROM_RECENTS); 12521 intent.putExtra(Intent.EXTRA_PACKAGE_NAME, cpi.packageName); 12522 12523 if (DEBUG_PERMISSIONS_REVIEW) { 12524 Slog.i(TAG, "u" + userId + " Launching permission review " 12525 + "for package " + cpi.packageName); 12526 } 12527 12528 final UserHandle userHandle = new UserHandle(userId); 12529 mHandler.post(new Runnable() { 12530 @Override 12531 public void run() { 12532 mContext.startActivityAsUser(intent, userHandle); 12533 } 12534 }); 12535 12536 return false; 12537 } 12538 12539 return true; 12540 } 12541 12542 /** 12543 * Returns the PackageManager. Used by classes hosted by {@link ActivityManagerService}. The 12544 * PackageManager could be unavailable at construction time and therefore needs to be accessed 12545 * on demand. 12546 */ 12547 IPackageManager getPackageManager() { 12548 return AppGlobals.getPackageManager(); 12549 } 12550 12551 ActivityStartController getActivityStartController() { 12552 return mActivityStartController; 12553 } 12554 12555 LockTaskController getLockTaskController() { 12556 return mLockTaskController; 12557 } 12558 12559 ClientLifecycleManager getLifecycleManager() { 12560 return mLifecycleManager; 12561 } 12562 12563 PackageManagerInternal getPackageManagerInternalLocked() { 12564 if (mPackageManagerInt == null) { 12565 mPackageManagerInt = LocalServices.getService(PackageManagerInternal.class); 12566 } 12567 return mPackageManagerInt; 12568 } 12569 12570 @Override 12571 public final ContentProviderHolder getContentProvider( 12572 IApplicationThread caller, String name, int userId, boolean stable) { 12573 enforceNotIsolatedCaller("getContentProvider"); 12574 if (caller == null) { 12575 String msg = "null IApplicationThread when getting content provider " 12576 + name; 12577 Slog.w(TAG, msg); 12578 throw new SecurityException(msg); 12579 } 12580 // The incoming user check is now handled in checkContentProviderPermissionLocked() to deal 12581 // with cross-user grant. 12582 return getContentProviderImpl(caller, name, null, stable, userId); 12583 } 12584 12585 public ContentProviderHolder getContentProviderExternal( 12586 String name, int userId, IBinder token) { 12587 enforceCallingPermission(android.Manifest.permission.ACCESS_CONTENT_PROVIDERS_EXTERNALLY, 12588 "Do not have permission in call getContentProviderExternal()"); 12589 userId = mUserController.handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 12590 userId, false, ALLOW_FULL_ONLY, "getContentProvider", null); 12591 return getContentProviderExternalUnchecked(name, token, userId); 12592 } 12593 12594 private ContentProviderHolder getContentProviderExternalUnchecked(String name, 12595 IBinder token, int userId) { 12596 return getContentProviderImpl(null, name, token, true, userId); 12597 } 12598 12599 /** 12600 * Drop a content provider from a ProcessRecord's bookkeeping 12601 */ 12602 public void removeContentProvider(IBinder connection, boolean stable) { 12603 enforceNotIsolatedCaller("removeContentProvider"); 12604 long ident = Binder.clearCallingIdentity(); 12605 try { 12606 synchronized (this) { 12607 ContentProviderConnection conn; 12608 try { 12609 conn = (ContentProviderConnection)connection; 12610 } catch (ClassCastException e) { 12611 String msg ="removeContentProvider: " + connection 12612 + " not a ContentProviderConnection"; 12613 Slog.w(TAG, msg); 12614 throw new IllegalArgumentException(msg); 12615 } 12616 if (conn == null) { 12617 throw new NullPointerException("connection is null"); 12618 } 12619 if (decProviderCountLocked(conn, null, null, stable)) { 12620 updateOomAdjLocked(); 12621 } 12622 } 12623 } finally { 12624 Binder.restoreCallingIdentity(ident); 12625 } 12626 } 12627 12628 public void removeContentProviderExternal(String name, IBinder token) { 12629 enforceCallingPermission(android.Manifest.permission.ACCESS_CONTENT_PROVIDERS_EXTERNALLY, 12630 "Do not have permission in call removeContentProviderExternal()"); 12631 int userId = UserHandle.getCallingUserId(); 12632 long ident = Binder.clearCallingIdentity(); 12633 try { 12634 removeContentProviderExternalUnchecked(name, token, userId); 12635 } finally { 12636 Binder.restoreCallingIdentity(ident); 12637 } 12638 } 12639 12640 private void removeContentProviderExternalUnchecked(String name, IBinder token, int userId) { 12641 synchronized (this) { 12642 ContentProviderRecord cpr = mProviderMap.getProviderByName(name, userId); 12643 if(cpr == null) { 12644 //remove from mProvidersByClass 12645 if(DEBUG_ALL) Slog.v(TAG, name+" content provider not found in providers list"); 12646 return; 12647 } 12648 12649 //update content provider record entry info 12650 ComponentName comp = new ComponentName(cpr.info.packageName, cpr.info.name); 12651 ContentProviderRecord localCpr = mProviderMap.getProviderByClass(comp, userId); 12652 if (localCpr.hasExternalProcessHandles()) { 12653 if (localCpr.removeExternalProcessHandleLocked(token)) { 12654 updateOomAdjLocked(); 12655 } else { 12656 Slog.e(TAG, "Attmpt to remove content provider " + localCpr 12657 + " with no external reference for token: " 12658 + token + "."); 12659 } 12660 } else { 12661 Slog.e(TAG, "Attmpt to remove content provider: " + localCpr 12662 + " with no external references."); 12663 } 12664 } 12665 } 12666 12667 public final void publishContentProviders(IApplicationThread caller, 12668 List<ContentProviderHolder> providers) { 12669 if (providers == null) { 12670 return; 12671 } 12672 12673 enforceNotIsolatedCaller("publishContentProviders"); 12674 synchronized (this) { 12675 final ProcessRecord r = getRecordForAppLocked(caller); 12676 if (DEBUG_MU) Slog.v(TAG_MU, "ProcessRecord uid = " + r.uid); 12677 if (r == null) { 12678 throw new SecurityException( 12679 "Unable to find app for caller " + caller 12680 + " (pid=" + Binder.getCallingPid() 12681 + ") when publishing content providers"); 12682 } 12683 12684 final long origId = Binder.clearCallingIdentity(); 12685 12686 final int N = providers.size(); 12687 for (int i = 0; i < N; i++) { 12688 ContentProviderHolder src = providers.get(i); 12689 if (src == null || src.info == null || src.provider == null) { 12690 continue; 12691 } 12692 ContentProviderRecord dst = r.pubProviders.get(src.info.name); 12693 if (DEBUG_MU) Slog.v(TAG_MU, "ContentProviderRecord uid = " + dst.uid); 12694 if (dst != null) { 12695 ComponentName comp = new ComponentName(dst.info.packageName, dst.info.name); 12696 mProviderMap.putProviderByClass(comp, dst); 12697 String names[] = dst.info.authority.split(";"); 12698 for (int j = 0; j < names.length; j++) { 12699 mProviderMap.putProviderByName(names[j], dst); 12700 } 12701 12702 int launchingCount = mLaunchingProviders.size(); 12703 int j; 12704 boolean wasInLaunchingProviders = false; 12705 for (j = 0; j < launchingCount; j++) { 12706 if (mLaunchingProviders.get(j) == dst) { 12707 mLaunchingProviders.remove(j); 12708 wasInLaunchingProviders = true; 12709 j--; 12710 launchingCount--; 12711 } 12712 } 12713 if (wasInLaunchingProviders) { 12714 mHandler.removeMessages(CONTENT_PROVIDER_PUBLISH_TIMEOUT_MSG, r); 12715 } 12716 synchronized (dst) { 12717 dst.provider = src.provider; 12718 dst.proc = r; 12719 dst.notifyAll(); 12720 } 12721 updateOomAdjLocked(r, true); 12722 maybeUpdateProviderUsageStatsLocked(r, src.info.packageName, 12723 src.info.authority); 12724 } 12725 } 12726 12727 Binder.restoreCallingIdentity(origId); 12728 } 12729 } 12730 12731 public boolean refContentProvider(IBinder connection, int stable, int unstable) { 12732 ContentProviderConnection conn; 12733 try { 12734 conn = (ContentProviderConnection)connection; 12735 } catch (ClassCastException e) { 12736 String msg ="refContentProvider: " + connection 12737 + " not a ContentProviderConnection"; 12738 Slog.w(TAG, msg); 12739 throw new IllegalArgumentException(msg); 12740 } 12741 if (conn == null) { 12742 throw new NullPointerException("connection is null"); 12743 } 12744 12745 synchronized (this) { 12746 if (stable > 0) { 12747 conn.numStableIncs += stable; 12748 } 12749 stable = conn.stableCount + stable; 12750 if (stable < 0) { 12751 throw new IllegalStateException("stableCount < 0: " + stable); 12752 } 12753 12754 if (unstable > 0) { 12755 conn.numUnstableIncs += unstable; 12756 } 12757 unstable = conn.unstableCount + unstable; 12758 if (unstable < 0) { 12759 throw new IllegalStateException("unstableCount < 0: " + unstable); 12760 } 12761 12762 if ((stable+unstable) <= 0) { 12763 throw new IllegalStateException("ref counts can't go to zero here: stable=" 12764 + stable + " unstable=" + unstable); 12765 } 12766 conn.stableCount = stable; 12767 conn.unstableCount = unstable; 12768 return !conn.dead; 12769 } 12770 } 12771 12772 public void unstableProviderDied(IBinder connection) { 12773 ContentProviderConnection conn; 12774 try { 12775 conn = (ContentProviderConnection)connection; 12776 } catch (ClassCastException e) { 12777 String msg ="refContentProvider: " + connection 12778 + " not a ContentProviderConnection"; 12779 Slog.w(TAG, msg); 12780 throw new IllegalArgumentException(msg); 12781 } 12782 if (conn == null) { 12783 throw new NullPointerException("connection is null"); 12784 } 12785 12786 // Safely retrieve the content provider associated with the connection. 12787 IContentProvider provider; 12788 synchronized (this) { 12789 provider = conn.provider.provider; 12790 } 12791 12792 if (provider == null) { 12793 // Um, yeah, we're way ahead of you. 12794 return; 12795 } 12796 12797 // Make sure the caller is being honest with us. 12798 if (provider.asBinder().pingBinder()) { 12799 // Er, no, still looks good to us. 12800 synchronized (this) { 12801 Slog.w(TAG, "unstableProviderDied: caller " + Binder.getCallingUid() 12802 + " says " + conn + " died, but we don't agree"); 12803 return; 12804 } 12805 } 12806 12807 // Well look at that! It's dead! 12808 synchronized (this) { 12809 if (conn.provider.provider != provider) { 12810 // But something changed... good enough. 12811 return; 12812 } 12813 12814 ProcessRecord proc = conn.provider.proc; 12815 if (proc == null || proc.thread == null) { 12816 // Seems like the process is already cleaned up. 12817 return; 12818 } 12819 12820 // As far as we're concerned, this is just like receiving a 12821 // death notification... just a bit prematurely. 12822 reportUidInfoMessageLocked(TAG, 12823 "Process " + proc.processName + " (pid " + proc.pid 12824 + ") early provider death", 12825 proc.info.uid); 12826 final long ident = Binder.clearCallingIdentity(); 12827 try { 12828 appDiedLocked(proc); 12829 } finally { 12830 Binder.restoreCallingIdentity(ident); 12831 } 12832 } 12833 } 12834 12835 @Override 12836 public void appNotRespondingViaProvider(IBinder connection) { 12837 enforceCallingPermission(REMOVE_TASKS, "appNotRespondingViaProvider()"); 12838 12839 final ContentProviderConnection conn = (ContentProviderConnection) connection; 12840 if (conn == null) { 12841 Slog.w(TAG, "ContentProviderConnection is null"); 12842 return; 12843 } 12844 12845 final ProcessRecord host = conn.provider.proc; 12846 if (host == null) { 12847 Slog.w(TAG, "Failed to find hosting ProcessRecord"); 12848 return; 12849 } 12850 12851 mHandler.post(new Runnable() { 12852 @Override 12853 public void run() { 12854 mAppErrors.appNotResponding(host, null, null, false, 12855 "ContentProvider not responding"); 12856 } 12857 }); 12858 } 12859 12860 public final void installSystemProviders() { 12861 List<ProviderInfo> providers; 12862 synchronized (this) { 12863 ProcessRecord app = mProcessNames.get("system", SYSTEM_UID); 12864 providers = generateApplicationProvidersLocked(app); 12865 if (providers != null) { 12866 for (int i=providers.size()-1; i>=0; i--) { 12867 ProviderInfo pi = (ProviderInfo)providers.get(i); 12868 if ((pi.applicationInfo.flags&ApplicationInfo.FLAG_SYSTEM) == 0) { 12869 Slog.w(TAG, "Not installing system proc provider " + pi.name 12870 + ": not system .apk"); 12871 providers.remove(i); 12872 } 12873 } 12874 } 12875 } 12876 if (providers != null) { 12877 mSystemThread.installSystemProviders(providers); 12878 } 12879 12880 synchronized (this) { 12881 mSystemProvidersInstalled = true; 12882 } 12883 12884 mConstants.start(mContext.getContentResolver()); 12885 mCoreSettingsObserver = new CoreSettingsObserver(this); 12886 mFontScaleSettingObserver = new FontScaleSettingObserver(); 12887 mDevelopmentSettingsObserver = new DevelopmentSettingsObserver(); 12888 GlobalSettingsToPropertiesMapper.start(mContext.getContentResolver()); 12889 12890 // Now that the settings provider is published we can consider sending 12891 // in a rescue party. 12892 RescueParty.onSettingsProviderPublished(mContext); 12893 12894 //mUsageStatsService.monitorPackages(); 12895 } 12896 12897 void startPersistentApps(int matchFlags) { 12898 if (mFactoryTest == FactoryTest.FACTORY_TEST_LOW_LEVEL) return; 12899 12900 synchronized (this) { 12901 try { 12902 final List<ApplicationInfo> apps = AppGlobals.getPackageManager() 12903 .getPersistentApplications(STOCK_PM_FLAGS | matchFlags).getList(); 12904 for (ApplicationInfo app : apps) { 12905 if (!"android".equals(app.packageName)) { 12906 addAppLocked(app, null, false, null /* ABI override */); 12907 } 12908 } 12909 } catch (RemoteException ex) { 12910 } 12911 } 12912 } 12913 12914 /** 12915 * When a user is unlocked, we need to install encryption-unaware providers 12916 * belonging to any running apps. 12917 */ 12918 void installEncryptionUnawareProviders(int userId) { 12919 // We're only interested in providers that are encryption unaware, and 12920 // we don't care about uninstalled apps, since there's no way they're 12921 // running at this point. 12922 final int matchFlags = GET_PROVIDERS | MATCH_DIRECT_BOOT_UNAWARE; 12923 12924 synchronized (this) { 12925 final int NP = mProcessNames.getMap().size(); 12926 for (int ip = 0; ip < NP; ip++) { 12927 final SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 12928 final int NA = apps.size(); 12929 for (int ia = 0; ia < NA; ia++) { 12930 final ProcessRecord app = apps.valueAt(ia); 12931 if (app.userId != userId || app.thread == null || app.unlocked) continue; 12932 12933 final int NG = app.pkgList.size(); 12934 for (int ig = 0; ig < NG; ig++) { 12935 try { 12936 final String pkgName = app.pkgList.keyAt(ig); 12937 final PackageInfo pkgInfo = AppGlobals.getPackageManager() 12938 .getPackageInfo(pkgName, matchFlags, userId); 12939 if (pkgInfo != null && !ArrayUtils.isEmpty(pkgInfo.providers)) { 12940 for (ProviderInfo pi : pkgInfo.providers) { 12941 // TODO: keep in sync with generateApplicationProvidersLocked 12942 final boolean processMatch = Objects.equals(pi.processName, 12943 app.processName) || pi.multiprocess; 12944 final boolean userMatch = isSingleton(pi.processName, 12945 pi.applicationInfo, pi.name, pi.flags) 12946 ? (app.userId == UserHandle.USER_SYSTEM) : true; 12947 if (processMatch && userMatch) { 12948 Log.v(TAG, "Installing " + pi); 12949 app.thread.scheduleInstallProvider(pi); 12950 } else { 12951 Log.v(TAG, "Skipping " + pi); 12952 } 12953 } 12954 } 12955 } catch (RemoteException ignored) { 12956 } 12957 } 12958 } 12959 } 12960 } 12961 } 12962 12963 /** 12964 * Allows apps to retrieve the MIME type of a URI. 12965 * If an app is in the same user as the ContentProvider, or if it is allowed to interact across 12966 * users, then it does not need permission to access the ContentProvider. 12967 * Either, it needs cross-user uri grants. 12968 * 12969 * CTS tests for this functionality can be run with "runtest cts-appsecurity". 12970 * 12971 * Test cases are at cts/tests/appsecurity-tests/test-apps/UsePermissionDiffCert/ 12972 * src/com/android/cts/usespermissiondiffcertapp/AccessPermissionWithDiffSigTest.java 12973 */ 12974 public String getProviderMimeType(Uri uri, int userId) { 12975 enforceNotIsolatedCaller("getProviderMimeType"); 12976 final String name = uri.getAuthority(); 12977 int callingUid = Binder.getCallingUid(); 12978 int callingPid = Binder.getCallingPid(); 12979 long ident = 0; 12980 boolean clearedIdentity = false; 12981 userId = mUserController.unsafeConvertIncomingUser(userId); 12982 if (canClearIdentity(callingPid, callingUid, userId)) { 12983 clearedIdentity = true; 12984 ident = Binder.clearCallingIdentity(); 12985 } 12986 ContentProviderHolder holder = null; 12987 try { 12988 holder = getContentProviderExternalUnchecked(name, null, userId); 12989 if (holder != null) { 12990 return holder.provider.getType(uri); 12991 } 12992 } catch (RemoteException e) { 12993 Log.w(TAG, "Content provider dead retrieving " + uri, e); 12994 return null; 12995 } catch (Exception e) { 12996 Log.w(TAG, "Exception while determining type of " + uri, e); 12997 return null; 12998 } finally { 12999 // We need to clear the identity to call removeContentProviderExternalUnchecked 13000 if (!clearedIdentity) { 13001 ident = Binder.clearCallingIdentity(); 13002 } 13003 try { 13004 if (holder != null) { 13005 removeContentProviderExternalUnchecked(name, null, userId); 13006 } 13007 } finally { 13008 Binder.restoreCallingIdentity(ident); 13009 } 13010 } 13011 13012 return null; 13013 } 13014 13015 private boolean canClearIdentity(int callingPid, int callingUid, int userId) { 13016 if (UserHandle.getUserId(callingUid) == userId) { 13017 return true; 13018 } 13019 if (checkComponentPermission(INTERACT_ACROSS_USERS, callingPid, 13020 callingUid, -1, true) == PackageManager.PERMISSION_GRANTED 13021 || checkComponentPermission(INTERACT_ACROSS_USERS_FULL, callingPid, 13022 callingUid, -1, true) == PackageManager.PERMISSION_GRANTED) { 13023 return true; 13024 } 13025 return false; 13026 } 13027 13028 // ========================================================= 13029 // GLOBAL MANAGEMENT 13030 // ========================================================= 13031 13032 @GuardedBy("this") 13033 final ProcessRecord newProcessRecordLocked(ApplicationInfo info, String customProcess, 13034 boolean isolated, int isolatedUid) { 13035 String proc = customProcess != null ? customProcess : info.processName; 13036 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 13037 final int userId = UserHandle.getUserId(info.uid); 13038 int uid = info.uid; 13039 if (isolated) { 13040 if (isolatedUid == 0) { 13041 int stepsLeft = LAST_ISOLATED_UID - FIRST_ISOLATED_UID + 1; 13042 while (true) { 13043 if (mNextIsolatedProcessUid < FIRST_ISOLATED_UID 13044 || mNextIsolatedProcessUid > LAST_ISOLATED_UID) { 13045 mNextIsolatedProcessUid = FIRST_ISOLATED_UID; 13046 } 13047 uid = UserHandle.getUid(userId, mNextIsolatedProcessUid); 13048 mNextIsolatedProcessUid++; 13049 if (mIsolatedProcesses.indexOfKey(uid) < 0) { 13050 // No process for this uid, use it. 13051 break; 13052 } 13053 stepsLeft--; 13054 if (stepsLeft <= 0) { 13055 return null; 13056 } 13057 } 13058 } else { 13059 // Special case for startIsolatedProcess (internal only), where 13060 // the uid of the isolated process is specified by the caller. 13061 uid = isolatedUid; 13062 } 13063 getPackageManagerInternalLocked().addIsolatedUid(uid, info.uid); 13064 13065 // Register the isolated UID with this application so BatteryStats knows to 13066 // attribute resource usage to the application. 13067 // 13068 // NOTE: This is done here before addProcessNameLocked, which will tell BatteryStats 13069 // about the process state of the isolated UID *before* it is registered with the 13070 // owning application. 13071 mBatteryStatsService.addIsolatedUid(uid, info.uid); 13072 } 13073 final ProcessRecord r = new ProcessRecord(this, stats, info, proc, uid); 13074 if (!mBooted && !mBooting 13075 && userId == UserHandle.USER_SYSTEM 13076 && (info.flags & PERSISTENT_MASK) == PERSISTENT_MASK) { 13077 // The system process is initialized to SCHED_GROUP_DEFAULT in init.rc. 13078 r.curSchedGroup = ProcessList.SCHED_GROUP_DEFAULT; 13079 r.setSchedGroup = ProcessList.SCHED_GROUP_DEFAULT; 13080 r.persistent = true; 13081 r.maxAdj = ProcessList.PERSISTENT_PROC_ADJ; 13082 } 13083 if (isolated && isolatedUid != 0) { 13084 // Special case for startIsolatedProcess (internal only) - assume the process 13085 // is required by the system server to prevent it being killed. 13086 r.maxAdj = ProcessList.PERSISTENT_SERVICE_ADJ; 13087 } 13088 addProcessNameLocked(r); 13089 return r; 13090 } 13091 13092 private boolean uidOnBackgroundWhitelist(final int uid) { 13093 final int appId = UserHandle.getAppId(uid); 13094 final int[] whitelist = mBackgroundAppIdWhitelist; 13095 final int N = whitelist.length; 13096 for (int i = 0; i < N; i++) { 13097 if (appId == whitelist[i]) { 13098 return true; 13099 } 13100 } 13101 return false; 13102 } 13103 13104 @Override 13105 public boolean isBackgroundRestricted(String packageName) { 13106 final int callingUid = Binder.getCallingUid(); 13107 final IPackageManager pm = AppGlobals.getPackageManager(); 13108 try { 13109 final int packageUid = pm.getPackageUid(packageName, MATCH_DEBUG_TRIAGED_MISSING, 13110 UserHandle.getUserId(callingUid)); 13111 if (packageUid != callingUid) { 13112 throw new IllegalArgumentException("Uid " + callingUid 13113 + " cannot query restriction state for package " + packageName); 13114 } 13115 } catch (RemoteException exc) { 13116 // Ignore. 13117 } 13118 return isBackgroundRestrictedNoCheck(callingUid, packageName); 13119 } 13120 13121 boolean isBackgroundRestrictedNoCheck(final int uid, final String packageName) { 13122 final int mode = mAppOpsService.checkOperation(AppOpsManager.OP_RUN_ANY_IN_BACKGROUND, 13123 uid, packageName); 13124 return mode != AppOpsManager.MODE_ALLOWED; 13125 } 13126 13127 @Override 13128 public void backgroundWhitelistUid(final int uid) { 13129 if (Binder.getCallingUid() != Process.SYSTEM_UID) { 13130 throw new SecurityException("Only the OS may call backgroundWhitelistUid()"); 13131 } 13132 13133 if (DEBUG_BACKGROUND_CHECK) { 13134 Slog.i(TAG, "Adding uid " + uid + " to bg uid whitelist"); 13135 } 13136 synchronized (this) { 13137 final int N = mBackgroundAppIdWhitelist.length; 13138 int[] newList = new int[N+1]; 13139 System.arraycopy(mBackgroundAppIdWhitelist, 0, newList, 0, N); 13140 newList[N] = UserHandle.getAppId(uid); 13141 mBackgroundAppIdWhitelist = newList; 13142 } 13143 } 13144 13145 @GuardedBy("this") 13146 final ProcessRecord addAppLocked(ApplicationInfo info, String customProcess, boolean isolated, 13147 String abiOverride) { 13148 return addAppLocked(info, customProcess, isolated, false /* disableHiddenApiChecks */, 13149 abiOverride); 13150 } 13151 13152 final ProcessRecord addAppLocked(ApplicationInfo info, String customProcess, boolean isolated, 13153 boolean disableHiddenApiChecks, String abiOverride) { 13154 ProcessRecord app; 13155 if (!isolated) { 13156 app = getProcessRecordLocked(customProcess != null ? customProcess : info.processName, 13157 info.uid, true); 13158 } else { 13159 app = null; 13160 } 13161 13162 if (app == null) { 13163 app = newProcessRecordLocked(info, customProcess, isolated, 0); 13164 updateLruProcessLocked(app, false, null); 13165 updateOomAdjLocked(); 13166 } 13167 13168 // This package really, really can not be stopped. 13169 try { 13170 AppGlobals.getPackageManager().setPackageStoppedState( 13171 info.packageName, false, UserHandle.getUserId(app.uid)); 13172 } catch (RemoteException e) { 13173 } catch (IllegalArgumentException e) { 13174 Slog.w(TAG, "Failed trying to unstop package " 13175 + info.packageName + ": " + e); 13176 } 13177 13178 if ((info.flags & PERSISTENT_MASK) == PERSISTENT_MASK) { 13179 app.persistent = true; 13180 app.maxAdj = ProcessList.PERSISTENT_PROC_ADJ; 13181 } 13182 if (app.thread == null && mPersistentStartingProcesses.indexOf(app) < 0) { 13183 mPersistentStartingProcesses.add(app); 13184 startProcessLocked(app, "added application", 13185 customProcess != null ? customProcess : app.processName, disableHiddenApiChecks, 13186 abiOverride); 13187 } 13188 13189 return app; 13190 } 13191 13192 public void unhandledBack() { 13193 enforceCallingPermission(android.Manifest.permission.FORCE_BACK, 13194 "unhandledBack()"); 13195 13196 synchronized(this) { 13197 final long origId = Binder.clearCallingIdentity(); 13198 try { 13199 getFocusedStack().unhandledBackLocked(); 13200 } finally { 13201 Binder.restoreCallingIdentity(origId); 13202 } 13203 } 13204 } 13205 13206 public ParcelFileDescriptor openContentUri(String uriString) throws RemoteException { 13207 enforceNotIsolatedCaller("openContentUri"); 13208 final int userId = UserHandle.getCallingUserId(); 13209 final Uri uri = Uri.parse(uriString); 13210 String name = uri.getAuthority(); 13211 ContentProviderHolder cph = getContentProviderExternalUnchecked(name, null, userId); 13212 ParcelFileDescriptor pfd = null; 13213 if (cph != null) { 13214 // We record the binder invoker's uid in thread-local storage before 13215 // going to the content provider to open the file. Later, in the code 13216 // that handles all permissions checks, we look for this uid and use 13217 // that rather than the Activity Manager's own uid. The effect is that 13218 // we do the check against the caller's permissions even though it looks 13219 // to the content provider like the Activity Manager itself is making 13220 // the request. 13221 Binder token = new Binder(); 13222 sCallerIdentity.set(new Identity( 13223 token, Binder.getCallingPid(), Binder.getCallingUid())); 13224 try { 13225 pfd = cph.provider.openFile(null, uri, "r", null, token); 13226 } catch (FileNotFoundException e) { 13227 // do nothing; pfd will be returned null 13228 } finally { 13229 // Ensure that whatever happens, we clean up the identity state 13230 sCallerIdentity.remove(); 13231 // Ensure we're done with the provider. 13232 removeContentProviderExternalUnchecked(name, null, userId); 13233 } 13234 } else { 13235 Slog.d(TAG, "Failed to get provider for authority '" + name + "'"); 13236 } 13237 return pfd; 13238 } 13239 13240 // Actually is sleeping or shutting down or whatever else in the future 13241 // is an inactive state. 13242 boolean isSleepingOrShuttingDownLocked() { 13243 return isSleepingLocked() || mShuttingDown; 13244 } 13245 13246 boolean isShuttingDownLocked() { 13247 return mShuttingDown; 13248 } 13249 13250 boolean isSleepingLocked() { 13251 return mSleeping; 13252 } 13253 13254 void reportGlobalUsageEventLocked(int event) { 13255 mUsageStatsService.reportEvent("android", mUserController.getCurrentUserId(), event); 13256 int[] profiles = mUserController.getCurrentProfileIds(); 13257 if (profiles != null) { 13258 for (int i = profiles.length - 1; i >= 0; i--) { 13259 mUsageStatsService.reportEvent((String)null, profiles[i], event); 13260 } 13261 } 13262 } 13263 13264 void reportCurWakefulnessUsageEventLocked() { 13265 reportGlobalUsageEventLocked(mWakefulness == PowerManagerInternal.WAKEFULNESS_AWAKE 13266 ? UsageEvents.Event.SCREEN_INTERACTIVE 13267 : UsageEvents.Event.SCREEN_NON_INTERACTIVE); 13268 } 13269 13270 void reportCurKeyguardUsageEventLocked() { 13271 reportGlobalUsageEventLocked(mKeyguardShown 13272 ? UsageEvents.Event.KEYGUARD_SHOWN 13273 : UsageEvents.Event.KEYGUARD_HIDDEN); 13274 } 13275 13276 void onWakefulnessChanged(int wakefulness) { 13277 synchronized(this) { 13278 boolean wasAwake = mWakefulness == PowerManagerInternal.WAKEFULNESS_AWAKE; 13279 boolean isAwake = wakefulness == PowerManagerInternal.WAKEFULNESS_AWAKE; 13280 mWakefulness = wakefulness; 13281 13282 if (wasAwake != isAwake) { 13283 // Also update state in a special way for running foreground services UI. 13284 mServices.updateScreenStateLocked(isAwake); 13285 reportCurWakefulnessUsageEventLocked(); 13286 mHandler.obtainMessage(DISPATCH_SCREEN_AWAKE_MSG, isAwake ? 1 : 0, 0) 13287 .sendToTarget(); 13288 } 13289 updateOomAdjLocked(); 13290 } 13291 } 13292 13293 @GuardedBy("this") 13294 void finishRunningVoiceLocked() { 13295 if (mRunningVoice != null) { 13296 mRunningVoice = null; 13297 mVoiceWakeLock.release(); 13298 updateSleepIfNeededLocked(); 13299 } 13300 } 13301 13302 void startTimeTrackingFocusedActivityLocked() { 13303 final ActivityRecord resumedActivity = mStackSupervisor.getResumedActivityLocked(); 13304 if (!mSleeping && mCurAppTimeTracker != null && resumedActivity != null) { 13305 mCurAppTimeTracker.start(resumedActivity.packageName); 13306 } 13307 } 13308 13309 @GuardedBy("this") 13310 void updateSleepIfNeededLocked() { 13311 final boolean shouldSleep = !mStackSupervisor.hasAwakeDisplay(); 13312 final boolean wasSleeping = mSleeping; 13313 13314 if (!shouldSleep) { 13315 // If wasSleeping is true, we need to wake up activity manager state from when 13316 // we started sleeping. In either case, we need to apply the sleep tokens, which 13317 // will wake up stacks or put them to sleep as appropriate. 13318 if (wasSleeping) { 13319 mSleeping = false; 13320 startTimeTrackingFocusedActivityLocked(); 13321 mTopProcessState = ActivityManager.PROCESS_STATE_TOP; 13322 mStackSupervisor.comeOutOfSleepIfNeededLocked(); 13323 } 13324 mStackSupervisor.applySleepTokensLocked(true /* applyToStacks */); 13325 if (wasSleeping) { 13326 updateOomAdjLocked(); 13327 } 13328 } else if (!mSleeping && shouldSleep) { 13329 mSleeping = true; 13330 if (mCurAppTimeTracker != null) { 13331 mCurAppTimeTracker.stop(); 13332 } 13333 mTopProcessState = ActivityManager.PROCESS_STATE_TOP_SLEEPING; 13334 mStackSupervisor.goingToSleepLocked(); 13335 updateResumedAppTrace(null /* resumed */); 13336 updateOomAdjLocked(); 13337 } 13338 } 13339 13340 /** Pokes the task persister. */ 13341 void notifyTaskPersisterLocked(TaskRecord task, boolean flush) { 13342 mRecentTasks.notifyTaskPersisterLocked(task, flush); 13343 } 13344 13345 /** 13346 * Notifies all listeners when the pinned stack animation starts. 13347 */ 13348 @Override 13349 public void notifyPinnedStackAnimationStarted() { 13350 mTaskChangeNotificationController.notifyPinnedStackAnimationStarted(); 13351 } 13352 13353 /** 13354 * Notifies all listeners when the pinned stack animation ends. 13355 */ 13356 @Override 13357 public void notifyPinnedStackAnimationEnded() { 13358 mTaskChangeNotificationController.notifyPinnedStackAnimationEnded(); 13359 } 13360 13361 @Override 13362 public void notifyCleartextNetwork(int uid, byte[] firstPacket) { 13363 mHandler.obtainMessage(NOTIFY_CLEARTEXT_NETWORK_MSG, uid, 0, firstPacket).sendToTarget(); 13364 } 13365 13366 @Override 13367 public boolean shutdown(int timeout) { 13368 if (checkCallingPermission(android.Manifest.permission.SHUTDOWN) 13369 != PackageManager.PERMISSION_GRANTED) { 13370 throw new SecurityException("Requires permission " 13371 + android.Manifest.permission.SHUTDOWN); 13372 } 13373 13374 boolean timedout = false; 13375 13376 synchronized(this) { 13377 mShuttingDown = true; 13378 mStackSupervisor.prepareForShutdownLocked(); 13379 updateEventDispatchingLocked(); 13380 timedout = mStackSupervisor.shutdownLocked(timeout); 13381 } 13382 13383 mAppOpsService.shutdown(); 13384 if (mUsageStatsService != null) { 13385 mUsageStatsService.prepareShutdown(); 13386 } 13387 mBatteryStatsService.shutdown(); 13388 synchronized (this) { 13389 mProcessStats.shutdownLocked(); 13390 notifyTaskPersisterLocked(null, true); 13391 } 13392 13393 return timedout; 13394 } 13395 13396 public final void activitySlept(IBinder token) { 13397 if (DEBUG_ALL) Slog.v(TAG, "Activity slept: token=" + token); 13398 13399 final long origId = Binder.clearCallingIdentity(); 13400 13401 synchronized (this) { 13402 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 13403 if (r != null) { 13404 mStackSupervisor.activitySleptLocked(r); 13405 } 13406 } 13407 13408 Binder.restoreCallingIdentity(origId); 13409 } 13410 13411 @GuardedBy("this") 13412 void startRunningVoiceLocked(IVoiceInteractionSession session, int targetUid) { 13413 Slog.d(TAG, "<<< startRunningVoiceLocked()"); 13414 mVoiceWakeLock.setWorkSource(new WorkSource(targetUid)); 13415 if (mRunningVoice == null || mRunningVoice.asBinder() != session.asBinder()) { 13416 boolean wasRunningVoice = mRunningVoice != null; 13417 mRunningVoice = session; 13418 if (!wasRunningVoice) { 13419 mVoiceWakeLock.acquire(); 13420 updateSleepIfNeededLocked(); 13421 } 13422 } 13423 } 13424 13425 private void updateEventDispatchingLocked() { 13426 mWindowManager.setEventDispatching(mBooted && !mShuttingDown); 13427 } 13428 13429 @Override 13430 public void setLockScreenShown(boolean keyguardShowing, boolean aodShowing, 13431 int secondaryDisplayShowing) { 13432 if (checkCallingPermission(android.Manifest.permission.DEVICE_POWER) 13433 != PackageManager.PERMISSION_GRANTED) { 13434 throw new SecurityException("Requires permission " 13435 + android.Manifest.permission.DEVICE_POWER); 13436 } 13437 13438 synchronized(this) { 13439 long ident = Binder.clearCallingIdentity(); 13440 if (mKeyguardShown != keyguardShowing) { 13441 mKeyguardShown = keyguardShowing; 13442 reportCurKeyguardUsageEventLocked(); 13443 } 13444 try { 13445 mKeyguardController.setKeyguardShown(keyguardShowing, aodShowing, 13446 secondaryDisplayShowing); 13447 } finally { 13448 Binder.restoreCallingIdentity(ident); 13449 } 13450 } 13451 13452 mHandler.obtainMessage(DISPATCH_SCREEN_KEYGUARD_MSG, keyguardShowing ? 1 : 0, 0) 13453 .sendToTarget(); 13454 } 13455 13456 @Override 13457 public void notifyLockedProfile(@UserIdInt int userId) { 13458 try { 13459 if (!AppGlobals.getPackageManager().isUidPrivileged(Binder.getCallingUid())) { 13460 throw new SecurityException("Only privileged app can call notifyLockedProfile"); 13461 } 13462 } catch (RemoteException ex) { 13463 throw new SecurityException("Fail to check is caller a privileged app", ex); 13464 } 13465 13466 synchronized (this) { 13467 final long ident = Binder.clearCallingIdentity(); 13468 try { 13469 if (mUserController.shouldConfirmCredentials(userId)) { 13470 if (mKeyguardController.isKeyguardLocked()) { 13471 // Showing launcher to avoid user entering credential twice. 13472 final int currentUserId = mUserController.getCurrentUserId(); 13473 startHomeActivityLocked(currentUserId, "notifyLockedProfile"); 13474 } 13475 mStackSupervisor.lockAllProfileTasks(userId); 13476 } 13477 } finally { 13478 Binder.restoreCallingIdentity(ident); 13479 } 13480 } 13481 } 13482 13483 @Override 13484 public void startConfirmDeviceCredentialIntent(Intent intent, Bundle options) { 13485 enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "startConfirmDeviceCredentialIntent"); 13486 synchronized (this) { 13487 final long ident = Binder.clearCallingIdentity(); 13488 try { 13489 intent.addFlags(FLAG_ACTIVITY_NEW_TASK | 13490 FLAG_ACTIVITY_EXCLUDE_FROM_RECENTS | 13491 FLAG_ACTIVITY_TASK_ON_HOME); 13492 ActivityOptions activityOptions = options != null 13493 ? new ActivityOptions(options) 13494 : ActivityOptions.makeBasic(); 13495 activityOptions.setLaunchTaskId( 13496 mStackSupervisor.getHomeActivity().getTask().taskId); 13497 mContext.startActivityAsUser(intent, activityOptions.toBundle(), 13498 UserHandle.CURRENT); 13499 } finally { 13500 Binder.restoreCallingIdentity(ident); 13501 } 13502 } 13503 } 13504 13505 @Override 13506 public void stopAppSwitches() { 13507 enforceCallerIsRecentsOrHasPermission(STOP_APP_SWITCHES, "stopAppSwitches"); 13508 synchronized(this) { 13509 mAppSwitchesAllowedTime = SystemClock.uptimeMillis() 13510 + APP_SWITCH_DELAY_TIME; 13511 mDidAppSwitch = false; 13512 mActivityStartController.schedulePendingActivityLaunches(APP_SWITCH_DELAY_TIME); 13513 } 13514 } 13515 13516 public void resumeAppSwitches() { 13517 enforceCallerIsRecentsOrHasPermission(STOP_APP_SWITCHES, "resumeAppSwitches"); 13518 synchronized(this) { 13519 // Note that we don't execute any pending app switches... we will 13520 // let those wait until either the timeout, or the next start 13521 // activity request. 13522 mAppSwitchesAllowedTime = 0; 13523 } 13524 } 13525 13526 boolean checkAllowAppSwitchUid(int uid) { 13527 ArrayMap<String, Integer> types = mAllowAppSwitchUids.get(UserHandle.getUserId(uid)); 13528 if (types != null) { 13529 for (int i = types.size() - 1; i >= 0; i--) { 13530 if (types.valueAt(i).intValue() == uid) { 13531 return true; 13532 } 13533 } 13534 } 13535 return false; 13536 } 13537 13538 boolean checkAppSwitchAllowedLocked(int sourcePid, int sourceUid, 13539 int callingPid, int callingUid, String name) { 13540 if (mAppSwitchesAllowedTime < SystemClock.uptimeMillis()) { 13541 return true; 13542 } 13543 13544 if (mRecentTasks.isCallerRecents(sourceUid)) { 13545 return true; 13546 } 13547 13548 int perm = checkComponentPermission(STOP_APP_SWITCHES, sourcePid, sourceUid, -1, true); 13549 if (perm == PackageManager.PERMISSION_GRANTED) { 13550 return true; 13551 } 13552 if (checkAllowAppSwitchUid(sourceUid)) { 13553 return true; 13554 } 13555 13556 // If the actual IPC caller is different from the logical source, then 13557 // also see if they are allowed to control app switches. 13558 if (callingUid != -1 && callingUid != sourceUid) { 13559 perm = checkComponentPermission(STOP_APP_SWITCHES, callingPid, callingUid, -1, true); 13560 if (perm == PackageManager.PERMISSION_GRANTED) { 13561 return true; 13562 } 13563 if (checkAllowAppSwitchUid(callingUid)) { 13564 return true; 13565 } 13566 } 13567 13568 Slog.w(TAG, name + " request from " + sourceUid + " stopped"); 13569 return false; 13570 } 13571 13572 public void setDebugApp(String packageName, boolean waitForDebugger, 13573 boolean persistent) { 13574 enforceCallingPermission(android.Manifest.permission.SET_DEBUG_APP, 13575 "setDebugApp()"); 13576 13577 long ident = Binder.clearCallingIdentity(); 13578 try { 13579 // Note that this is not really thread safe if there are multiple 13580 // callers into it at the same time, but that's not a situation we 13581 // care about. 13582 if (persistent) { 13583 final ContentResolver resolver = mContext.getContentResolver(); 13584 Settings.Global.putString( 13585 resolver, Settings.Global.DEBUG_APP, 13586 packageName); 13587 Settings.Global.putInt( 13588 resolver, Settings.Global.WAIT_FOR_DEBUGGER, 13589 waitForDebugger ? 1 : 0); 13590 } 13591 13592 synchronized (this) { 13593 if (!persistent) { 13594 mOrigDebugApp = mDebugApp; 13595 mOrigWaitForDebugger = mWaitForDebugger; 13596 } 13597 mDebugApp = packageName; 13598 mWaitForDebugger = waitForDebugger; 13599 mDebugTransient = !persistent; 13600 if (packageName != null) { 13601 forceStopPackageLocked(packageName, -1, false, false, true, true, 13602 false, UserHandle.USER_ALL, "set debug app"); 13603 } 13604 } 13605 } finally { 13606 Binder.restoreCallingIdentity(ident); 13607 } 13608 } 13609 13610 /** 13611 * Set or remove an agent to be run whenever an app with the given process name starts. 13612 * 13613 * This method will not check whether the given process name matches a debuggable app. That 13614 * would require scanning all current packages, and a rescan when new packages are installed 13615 * or updated. 13616 * 13617 * Instead, do the check when an application is started and matched to a stored agent. 13618 * 13619 * @param packageName the process name of the app. 13620 * @param agent the agent string to be used, or null to remove any previously set agent. 13621 */ 13622 @Override 13623 public void setAgentApp(@NonNull String packageName, @Nullable String agent) { 13624 synchronized (this) { 13625 // note: hijacking SET_ACTIVITY_WATCHER, but should be changed to 13626 // its own permission. 13627 if (checkCallingPermission( 13628 android.Manifest.permission.SET_ACTIVITY_WATCHER) != 13629 PackageManager.PERMISSION_GRANTED) { 13630 throw new SecurityException( 13631 "Requires permission " + android.Manifest.permission.SET_ACTIVITY_WATCHER); 13632 } 13633 13634 if (agent == null) { 13635 if (mAppAgentMap != null) { 13636 mAppAgentMap.remove(packageName); 13637 if (mAppAgentMap.isEmpty()) { 13638 mAppAgentMap = null; 13639 } 13640 } 13641 } else { 13642 if (mAppAgentMap == null) { 13643 mAppAgentMap = new HashMap<>(); 13644 } 13645 if (mAppAgentMap.size() >= 100) { 13646 // Limit the size of the map, to avoid OOMEs. 13647 Slog.e(TAG, "App agent map has too many entries, cannot add " + packageName 13648 + "/" + agent); 13649 return; 13650 } 13651 mAppAgentMap.put(packageName, agent); 13652 } 13653 } 13654 } 13655 13656 void setTrackAllocationApp(ApplicationInfo app, String processName) { 13657 synchronized (this) { 13658 boolean isDebuggable = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 13659 if (!isDebuggable) { 13660 if ((app.flags & ApplicationInfo.FLAG_DEBUGGABLE) == 0) { 13661 throw new SecurityException("Process not debuggable: " + app.packageName); 13662 } 13663 } 13664 13665 mTrackAllocationApp = processName; 13666 } 13667 } 13668 13669 void setProfileApp(ApplicationInfo app, String processName, ProfilerInfo profilerInfo) { 13670 synchronized (this) { 13671 boolean isDebuggable = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 13672 if (!isDebuggable) { 13673 if ((app.flags & ApplicationInfo.FLAG_DEBUGGABLE) == 0) { 13674 throw new SecurityException("Process not debuggable: " + app.packageName); 13675 } 13676 } 13677 mProfileApp = processName; 13678 13679 if (mProfilerInfo != null) { 13680 if (mProfilerInfo.profileFd != null) { 13681 try { 13682 mProfilerInfo.profileFd.close(); 13683 } catch (IOException e) { 13684 } 13685 } 13686 } 13687 mProfilerInfo = new ProfilerInfo(profilerInfo); 13688 mProfileType = 0; 13689 } 13690 } 13691 13692 void setNativeDebuggingAppLocked(ApplicationInfo app, String processName) { 13693 boolean isDebuggable = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 13694 if (!isDebuggable) { 13695 if ((app.flags & ApplicationInfo.FLAG_DEBUGGABLE) == 0) { 13696 throw new SecurityException("Process not debuggable: " + app.packageName); 13697 } 13698 } 13699 mNativeDebuggingApp = processName; 13700 } 13701 13702 @Override 13703 public void setAlwaysFinish(boolean enabled) { 13704 enforceCallingPermission(android.Manifest.permission.SET_ALWAYS_FINISH, 13705 "setAlwaysFinish()"); 13706 13707 long ident = Binder.clearCallingIdentity(); 13708 try { 13709 Settings.Global.putInt( 13710 mContext.getContentResolver(), 13711 Settings.Global.ALWAYS_FINISH_ACTIVITIES, enabled ? 1 : 0); 13712 13713 synchronized (this) { 13714 mAlwaysFinishActivities = enabled; 13715 } 13716 } finally { 13717 Binder.restoreCallingIdentity(ident); 13718 } 13719 } 13720 13721 @Override 13722 public void setActivityController(IActivityController controller, boolean imAMonkey) { 13723 enforceCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER, 13724 "setActivityController()"); 13725 synchronized (this) { 13726 mController = controller; 13727 mControllerIsAMonkey = imAMonkey; 13728 Watchdog.getInstance().setActivityController(controller); 13729 } 13730 } 13731 13732 @Override 13733 public void setUserIsMonkey(boolean userIsMonkey) { 13734 synchronized (this) { 13735 synchronized (mPidsSelfLocked) { 13736 final int callingPid = Binder.getCallingPid(); 13737 ProcessRecord proc = mPidsSelfLocked.get(callingPid); 13738 if (proc == null) { 13739 throw new SecurityException("Unknown process: " + callingPid); 13740 } 13741 if (proc.instr == null || proc.instr.mUiAutomationConnection == null) { 13742 throw new SecurityException("Only an instrumentation process " 13743 + "with a UiAutomation can call setUserIsMonkey"); 13744 } 13745 } 13746 mUserIsMonkey = userIsMonkey; 13747 } 13748 } 13749 13750 @Override 13751 public boolean isUserAMonkey() { 13752 synchronized (this) { 13753 // If there is a controller also implies the user is a monkey. 13754 return (mUserIsMonkey || (mController != null && mControllerIsAMonkey)); 13755 } 13756 } 13757 13758 /** 13759 * @deprecated This method is only used by a few internal components and it will soon be 13760 * replaced by a proper bug report API (which will be restricted to a few, pre-defined apps). 13761 * No new code should be calling it. 13762 */ 13763 @Deprecated 13764 @Override 13765 public void requestBugReport(int bugreportType) { 13766 String extraOptions = null; 13767 switch (bugreportType) { 13768 case ActivityManager.BUGREPORT_OPTION_FULL: 13769 // Default options. 13770 break; 13771 case ActivityManager.BUGREPORT_OPTION_INTERACTIVE: 13772 extraOptions = "bugreportplus"; 13773 break; 13774 case ActivityManager.BUGREPORT_OPTION_REMOTE: 13775 extraOptions = "bugreportremote"; 13776 break; 13777 case ActivityManager.BUGREPORT_OPTION_WEAR: 13778 extraOptions = "bugreportwear"; 13779 break; 13780 case ActivityManager.BUGREPORT_OPTION_TELEPHONY: 13781 extraOptions = "bugreporttelephony"; 13782 break; 13783 case ActivityManager.BUGREPORT_OPTION_WIFI: 13784 extraOptions = "bugreportwifi"; 13785 break; 13786 default: 13787 throw new IllegalArgumentException("Provided bugreport type is not correct, value: " 13788 + bugreportType); 13789 } 13790 // Always log caller, even if it does not have permission to dump. 13791 String type = extraOptions == null ? "bugreport" : extraOptions; 13792 Slog.i(TAG, type + " requested by UID " + Binder.getCallingUid()); 13793 13794 enforceCallingPermission(android.Manifest.permission.DUMP, "requestBugReport"); 13795 if (extraOptions != null) { 13796 SystemProperties.set("dumpstate.options", extraOptions); 13797 } 13798 SystemProperties.set("ctl.start", "bugreport"); 13799 } 13800 13801 /** 13802 * @deprecated This method is only used by a few internal components and it will soon be 13803 * replaced by a proper bug report API (which will be restricted to a few, pre-defined apps). 13804 * No new code should be calling it. 13805 */ 13806 @Deprecated 13807 private void requestBugReportWithDescription(String shareTitle, String shareDescription, 13808 int bugreportType) { 13809 if (!TextUtils.isEmpty(shareTitle)) { 13810 if (shareTitle.length() > MAX_BUGREPORT_TITLE_SIZE) { 13811 String errorStr = "shareTitle should be less than " + 13812 MAX_BUGREPORT_TITLE_SIZE + " characters"; 13813 throw new IllegalArgumentException(errorStr); 13814 } else { 13815 if (!TextUtils.isEmpty(shareDescription)) { 13816 int length; 13817 try { 13818 length = shareDescription.getBytes("UTF-8").length; 13819 } catch (UnsupportedEncodingException e) { 13820 String errorStr = "shareDescription: UnsupportedEncodingException"; 13821 throw new IllegalArgumentException(errorStr); 13822 } 13823 if (length > SystemProperties.PROP_VALUE_MAX) { 13824 String errorStr = "shareTitle should be less than " + 13825 SystemProperties.PROP_VALUE_MAX + " bytes"; 13826 throw new IllegalArgumentException(errorStr); 13827 } else { 13828 SystemProperties.set("dumpstate.options.description", shareDescription); 13829 } 13830 } 13831 SystemProperties.set("dumpstate.options.title", shareTitle); 13832 } 13833 } 13834 13835 Slog.d(TAG, "Bugreport notification title " + shareTitle 13836 + " description " + shareDescription); 13837 requestBugReport(bugreportType); 13838 } 13839 13840 /** 13841 * @deprecated This method is only used by a few internal components and it will soon be 13842 * replaced by a proper bug report API (which will be restricted to a few, pre-defined apps). 13843 * No new code should be calling it. 13844 */ 13845 @Deprecated 13846 @Override 13847 public void requestTelephonyBugReport(String shareTitle, String shareDescription) { 13848 requestBugReportWithDescription(shareTitle, shareDescription, 13849 ActivityManager.BUGREPORT_OPTION_TELEPHONY); 13850 } 13851 13852 /** 13853 * @deprecated This method is only used by a few internal components and it will soon be 13854 * replaced by a proper bug report API (which will be restricted to a few, pre-defined apps). 13855 * No new code should be calling it. 13856 */ 13857 @Deprecated 13858 @Override 13859 public void requestWifiBugReport(String shareTitle, String shareDescription) { 13860 requestBugReportWithDescription(shareTitle, shareDescription, 13861 ActivityManager.BUGREPORT_OPTION_WIFI); 13862 } 13863 13864 13865 public static long getInputDispatchingTimeoutLocked(ActivityRecord r) { 13866 return r != null ? getInputDispatchingTimeoutLocked(r.app) : KEY_DISPATCHING_TIMEOUT; 13867 } 13868 13869 public static long getInputDispatchingTimeoutLocked(ProcessRecord r) { 13870 if (r != null && (r.instr != null || r.usingWrapper)) { 13871 return INSTRUMENTATION_KEY_DISPATCHING_TIMEOUT; 13872 } 13873 return KEY_DISPATCHING_TIMEOUT; 13874 } 13875 13876 @Override 13877 public long inputDispatchingTimedOut(int pid, final boolean aboveSystem, String reason) { 13878 if (checkCallingPermission(android.Manifest.permission.FILTER_EVENTS) 13879 != PackageManager.PERMISSION_GRANTED) { 13880 throw new SecurityException("Requires permission " 13881 + android.Manifest.permission.FILTER_EVENTS); 13882 } 13883 ProcessRecord proc; 13884 long timeout; 13885 synchronized (this) { 13886 synchronized (mPidsSelfLocked) { 13887 proc = mPidsSelfLocked.get(pid); 13888 } 13889 timeout = getInputDispatchingTimeoutLocked(proc); 13890 } 13891 13892 if (inputDispatchingTimedOut(proc, null, null, aboveSystem, reason)) { 13893 return -1; 13894 } 13895 13896 return timeout; 13897 } 13898 13899 /** 13900 * Handle input dispatching timeouts. 13901 * Returns whether input dispatching should be aborted or not. 13902 */ 13903 public boolean inputDispatchingTimedOut(final ProcessRecord proc, 13904 final ActivityRecord activity, final ActivityRecord parent, 13905 final boolean aboveSystem, String reason) { 13906 if (checkCallingPermission(android.Manifest.permission.FILTER_EVENTS) 13907 != PackageManager.PERMISSION_GRANTED) { 13908 throw new SecurityException("Requires permission " 13909 + android.Manifest.permission.FILTER_EVENTS); 13910 } 13911 13912 final String annotation; 13913 if (reason == null) { 13914 annotation = "Input dispatching timed out"; 13915 } else { 13916 annotation = "Input dispatching timed out (" + reason + ")"; 13917 } 13918 13919 if (proc != null) { 13920 synchronized (this) { 13921 if (proc.debugging) { 13922 return false; 13923 } 13924 13925 if (proc.instr != null) { 13926 Bundle info = new Bundle(); 13927 info.putString("shortMsg", "keyDispatchingTimedOut"); 13928 info.putString("longMsg", annotation); 13929 finishInstrumentationLocked(proc, Activity.RESULT_CANCELED, info); 13930 return true; 13931 } 13932 } 13933 mHandler.post(new Runnable() { 13934 @Override 13935 public void run() { 13936 mAppErrors.appNotResponding(proc, activity, parent, aboveSystem, annotation); 13937 } 13938 }); 13939 } 13940 13941 return true; 13942 } 13943 13944 @Override 13945 public Bundle getAssistContextExtras(int requestType) { 13946 PendingAssistExtras pae = enqueueAssistContext(requestType, null, null, null, 13947 null, null, true /* focused */, true /* newSessionId */, 13948 UserHandle.getCallingUserId(), null, PENDING_ASSIST_EXTRAS_TIMEOUT, 0); 13949 if (pae == null) { 13950 return null; 13951 } 13952 synchronized (pae) { 13953 while (!pae.haveResult) { 13954 try { 13955 pae.wait(); 13956 } catch (InterruptedException e) { 13957 } 13958 } 13959 } 13960 synchronized (this) { 13961 buildAssistBundleLocked(pae, pae.result); 13962 mPendingAssistExtras.remove(pae); 13963 mUiHandler.removeCallbacks(pae); 13964 } 13965 return pae.extras; 13966 } 13967 13968 @Override 13969 public boolean isAssistDataAllowedOnCurrentActivity() { 13970 int userId; 13971 synchronized (this) { 13972 final ActivityStack focusedStack = getFocusedStack(); 13973 if (focusedStack == null || focusedStack.isActivityTypeAssistant()) { 13974 return false; 13975 } 13976 13977 final ActivityRecord activity = focusedStack.getTopActivity(); 13978 if (activity == null) { 13979 return false; 13980 } 13981 userId = activity.userId; 13982 } 13983 return !DevicePolicyCache.getInstance().getScreenCaptureDisabled(userId); 13984 } 13985 13986 @Override 13987 public boolean showAssistFromActivity(IBinder token, Bundle args) { 13988 long ident = Binder.clearCallingIdentity(); 13989 try { 13990 synchronized (this) { 13991 ActivityRecord caller = ActivityRecord.forTokenLocked(token); 13992 ActivityRecord top = getFocusedStack().getTopActivity(); 13993 if (top != caller) { 13994 Slog.w(TAG, "showAssistFromActivity failed: caller " + caller 13995 + " is not current top " + top); 13996 return false; 13997 } 13998 if (!top.nowVisible) { 13999 Slog.w(TAG, "showAssistFromActivity failed: caller " + caller 14000 + " is not visible"); 14001 return false; 14002 } 14003 } 14004 return mAssistUtils.showSessionForActiveService(args, SHOW_SOURCE_APPLICATION, null, 14005 token); 14006 } finally { 14007 Binder.restoreCallingIdentity(ident); 14008 } 14009 } 14010 14011 @Override 14012 public boolean requestAssistContextExtras(int requestType, IAssistDataReceiver receiver, 14013 Bundle receiverExtras, IBinder activityToken, boolean focused, boolean newSessionId) { 14014 return enqueueAssistContext(requestType, null, null, receiver, receiverExtras, 14015 activityToken, focused, newSessionId, UserHandle.getCallingUserId(), null, 14016 PENDING_ASSIST_EXTRAS_LONG_TIMEOUT, 0) != null; 14017 } 14018 14019 @Override 14020 public boolean requestAutofillData(IAssistDataReceiver receiver, Bundle receiverExtras, 14021 IBinder activityToken, int flags) { 14022 return enqueueAssistContext(ActivityManager.ASSIST_CONTEXT_AUTOFILL, null, null, 14023 receiver, receiverExtras, activityToken, true, true, UserHandle.getCallingUserId(), 14024 null, PENDING_AUTOFILL_ASSIST_STRUCTURE_TIMEOUT, flags) != null; 14025 } 14026 14027 private PendingAssistExtras enqueueAssistContext(int requestType, Intent intent, String hint, 14028 IAssistDataReceiver receiver, Bundle receiverExtras, IBinder activityToken, 14029 boolean focused, boolean newSessionId, int userHandle, Bundle args, long timeout, 14030 int flags) { 14031 enforceCallingPermission(android.Manifest.permission.GET_TOP_ACTIVITY_INFO, 14032 "enqueueAssistContext()"); 14033 14034 synchronized (this) { 14035 ActivityRecord activity = getFocusedStack().getTopActivity(); 14036 if (activity == null) { 14037 Slog.w(TAG, "getAssistContextExtras failed: no top activity"); 14038 return null; 14039 } 14040 if (activity.app == null || activity.app.thread == null) { 14041 Slog.w(TAG, "getAssistContextExtras failed: no process for " + activity); 14042 return null; 14043 } 14044 if (focused) { 14045 if (activityToken != null) { 14046 ActivityRecord caller = ActivityRecord.forTokenLocked(activityToken); 14047 if (activity != caller) { 14048 Slog.w(TAG, "enqueueAssistContext failed: caller " + caller 14049 + " is not current top " + activity); 14050 return null; 14051 } 14052 } 14053 } else { 14054 activity = ActivityRecord.forTokenLocked(activityToken); 14055 if (activity == null) { 14056 Slog.w(TAG, "enqueueAssistContext failed: activity for token=" + activityToken 14057 + " couldn't be found"); 14058 return null; 14059 } 14060 if (activity.app == null || activity.app.thread == null) { 14061 Slog.w(TAG, "enqueueAssistContext failed: no process for " + activity); 14062 return null; 14063 } 14064 } 14065 14066 PendingAssistExtras pae; 14067 Bundle extras = new Bundle(); 14068 if (args != null) { 14069 extras.putAll(args); 14070 } 14071 extras.putString(Intent.EXTRA_ASSIST_PACKAGE, activity.packageName); 14072 extras.putInt(Intent.EXTRA_ASSIST_UID, activity.app.uid); 14073 14074 pae = new PendingAssistExtras(activity, extras, intent, hint, receiver, receiverExtras, 14075 userHandle); 14076 pae.isHome = activity.isActivityTypeHome(); 14077 14078 // Increment the sessionId if necessary 14079 if (newSessionId) { 14080 mViSessionId++; 14081 } 14082 try { 14083 activity.app.thread.requestAssistContextExtras(activity.appToken, pae, requestType, 14084 mViSessionId, flags); 14085 mPendingAssistExtras.add(pae); 14086 mUiHandler.postDelayed(pae, timeout); 14087 } catch (RemoteException e) { 14088 Slog.w(TAG, "getAssistContextExtras failed: crash calling " + activity); 14089 return null; 14090 } 14091 return pae; 14092 } 14093 } 14094 14095 void pendingAssistExtrasTimedOut(PendingAssistExtras pae) { 14096 IAssistDataReceiver receiver; 14097 synchronized (this) { 14098 mPendingAssistExtras.remove(pae); 14099 receiver = pae.receiver; 14100 } 14101 if (receiver != null) { 14102 // Caller wants result sent back to them. 14103 Bundle sendBundle = new Bundle(); 14104 // At least return the receiver extras 14105 sendBundle.putBundle(ASSIST_KEY_RECEIVER_EXTRAS, pae.receiverExtras); 14106 try { 14107 pae.receiver.onHandleAssistData(sendBundle); 14108 } catch (RemoteException e) { 14109 } 14110 } 14111 } 14112 14113 private void buildAssistBundleLocked(PendingAssistExtras pae, Bundle result) { 14114 if (result != null) { 14115 pae.extras.putBundle(Intent.EXTRA_ASSIST_CONTEXT, result); 14116 } 14117 if (pae.hint != null) { 14118 pae.extras.putBoolean(pae.hint, true); 14119 } 14120 } 14121 14122 /** Called from an app when assist data is ready. */ 14123 @Override 14124 public void reportAssistContextExtras(IBinder token, Bundle extras, AssistStructure structure, 14125 AssistContent content, Uri referrer) { 14126 PendingAssistExtras pae = (PendingAssistExtras)token; 14127 synchronized (pae) { 14128 pae.result = extras; 14129 pae.structure = structure; 14130 pae.content = content; 14131 if (referrer != null) { 14132 pae.extras.putParcelable(Intent.EXTRA_REFERRER, referrer); 14133 } 14134 if (structure != null) { 14135 structure.setHomeActivity(pae.isHome); 14136 } 14137 pae.haveResult = true; 14138 pae.notifyAll(); 14139 if (pae.intent == null && pae.receiver == null) { 14140 // Caller is just waiting for the result. 14141 return; 14142 } 14143 } 14144 // We are now ready to launch the assist activity. 14145 IAssistDataReceiver sendReceiver = null; 14146 Bundle sendBundle = null; 14147 synchronized (this) { 14148 buildAssistBundleLocked(pae, extras); 14149 boolean exists = mPendingAssistExtras.remove(pae); 14150 mUiHandler.removeCallbacks(pae); 14151 if (!exists) { 14152 // Timed out. 14153 return; 14154 } 14155 14156 if ((sendReceiver=pae.receiver) != null) { 14157 // Caller wants result sent back to them. 14158 sendBundle = new Bundle(); 14159 sendBundle.putBundle(ASSIST_KEY_DATA, pae.extras); 14160 sendBundle.putParcelable(ASSIST_KEY_STRUCTURE, pae.structure); 14161 sendBundle.putParcelable(ASSIST_KEY_CONTENT, pae.content); 14162 sendBundle.putBundle(ASSIST_KEY_RECEIVER_EXTRAS, pae.receiverExtras); 14163 } 14164 } 14165 if (sendReceiver != null) { 14166 try { 14167 sendReceiver.onHandleAssistData(sendBundle); 14168 } catch (RemoteException e) { 14169 } 14170 return; 14171 } 14172 14173 final long ident = Binder.clearCallingIdentity(); 14174 try { 14175 if (TextUtils.equals(pae.intent.getAction(), 14176 android.service.voice.VoiceInteractionService.SERVICE_INTERFACE)) { 14177 pae.intent.putExtras(pae.extras); 14178 mContext.startServiceAsUser(pae.intent, new UserHandle(pae.userHandle)); 14179 } else { 14180 pae.intent.replaceExtras(pae.extras); 14181 pae.intent.setFlags(FLAG_ACTIVITY_NEW_TASK 14182 | Intent.FLAG_ACTIVITY_SINGLE_TOP 14183 | Intent.FLAG_ACTIVITY_CLEAR_TOP); 14184 closeSystemDialogs("assist"); 14185 14186 try { 14187 mContext.startActivityAsUser(pae.intent, new UserHandle(pae.userHandle)); 14188 } catch (ActivityNotFoundException e) { 14189 Slog.w(TAG, "No activity to handle assist action.", e); 14190 } 14191 } 14192 } finally { 14193 Binder.restoreCallingIdentity(ident); 14194 } 14195 } 14196 14197 public boolean launchAssistIntent(Intent intent, int requestType, String hint, int userHandle, 14198 Bundle args) { 14199 return enqueueAssistContext(requestType, intent, hint, null, null, null, 14200 true /* focused */, true /* newSessionId */, userHandle, args, 14201 PENDING_ASSIST_EXTRAS_TIMEOUT, 0) != null; 14202 } 14203 14204 public void registerProcessObserver(IProcessObserver observer) { 14205 enforceCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER, 14206 "registerProcessObserver()"); 14207 synchronized (this) { 14208 mProcessObservers.register(observer); 14209 } 14210 } 14211 14212 @Override 14213 public void unregisterProcessObserver(IProcessObserver observer) { 14214 synchronized (this) { 14215 mProcessObservers.unregister(observer); 14216 } 14217 } 14218 14219 @Override 14220 public int getUidProcessState(int uid, String callingPackage) { 14221 if (!hasUsageStatsPermission(callingPackage)) { 14222 enforceCallingPermission(android.Manifest.permission.PACKAGE_USAGE_STATS, 14223 "getUidProcessState"); 14224 } 14225 14226 synchronized (this) { 14227 UidRecord uidRec = mActiveUids.get(uid); 14228 return uidRec != null ? uidRec.curProcState : ActivityManager.PROCESS_STATE_NONEXISTENT; 14229 } 14230 } 14231 14232 @Override 14233 public void registerUidObserver(IUidObserver observer, int which, int cutpoint, 14234 String callingPackage) { 14235 if (!hasUsageStatsPermission(callingPackage)) { 14236 enforceCallingPermission(android.Manifest.permission.PACKAGE_USAGE_STATS, 14237 "registerUidObserver"); 14238 } 14239 synchronized (this) { 14240 mUidObservers.register(observer, new UidObserverRegistration(Binder.getCallingUid(), 14241 callingPackage, which, cutpoint)); 14242 } 14243 } 14244 14245 @Override 14246 public void unregisterUidObserver(IUidObserver observer) { 14247 synchronized (this) { 14248 mUidObservers.unregister(observer); 14249 } 14250 } 14251 14252 @Override 14253 public boolean isUidActive(int uid, String callingPackage) { 14254 if (!hasUsageStatsPermission(callingPackage)) { 14255 enforceCallingPermission(android.Manifest.permission.PACKAGE_USAGE_STATS, 14256 "isUidActive"); 14257 } 14258 synchronized (this) { 14259 return isUidActiveLocked(uid); 14260 } 14261 } 14262 14263 boolean isUidActiveLocked(int uid) { 14264 final UidRecord uidRecord = mActiveUids.get(uid); 14265 return uidRecord != null && !uidRecord.setIdle; 14266 } 14267 14268 @Override 14269 public boolean convertFromTranslucent(IBinder token) { 14270 final long origId = Binder.clearCallingIdentity(); 14271 try { 14272 synchronized (this) { 14273 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 14274 if (r == null) { 14275 return false; 14276 } 14277 final boolean translucentChanged = r.changeWindowTranslucency(true); 14278 if (translucentChanged) { 14279 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0, !PRESERVE_WINDOWS); 14280 } 14281 mWindowManager.setAppFullscreen(token, true); 14282 return translucentChanged; 14283 } 14284 } finally { 14285 Binder.restoreCallingIdentity(origId); 14286 } 14287 } 14288 14289 @Override 14290 public boolean convertToTranslucent(IBinder token, Bundle options) { 14291 SafeActivityOptions safeOptions = SafeActivityOptions.fromBundle(options); 14292 final long origId = Binder.clearCallingIdentity(); 14293 try { 14294 synchronized (this) { 14295 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 14296 if (r == null) { 14297 return false; 14298 } 14299 final TaskRecord task = r.getTask(); 14300 int index = task.mActivities.lastIndexOf(r); 14301 if (index > 0) { 14302 ActivityRecord under = task.mActivities.get(index - 1); 14303 under.returningOptions = safeOptions != null ? safeOptions.getOptions(r) : null; 14304 } 14305 final boolean translucentChanged = r.changeWindowTranslucency(false); 14306 if (translucentChanged) { 14307 r.getStack().convertActivityToTranslucent(r); 14308 } 14309 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0, !PRESERVE_WINDOWS); 14310 mWindowManager.setAppFullscreen(token, false); 14311 return translucentChanged; 14312 } 14313 } finally { 14314 Binder.restoreCallingIdentity(origId); 14315 } 14316 } 14317 14318 @Override 14319 public Bundle getActivityOptions(IBinder token) { 14320 final long origId = Binder.clearCallingIdentity(); 14321 try { 14322 synchronized (this) { 14323 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 14324 if (r != null) { 14325 final ActivityOptions activityOptions = r.takeOptionsLocked(); 14326 return activityOptions == null ? null : activityOptions.toBundle(); 14327 } 14328 return null; 14329 } 14330 } finally { 14331 Binder.restoreCallingIdentity(origId); 14332 } 14333 } 14334 14335 @Override 14336 public void setImmersive(IBinder token, boolean immersive) { 14337 synchronized(this) { 14338 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 14339 if (r == null) { 14340 throw new IllegalArgumentException(); 14341 } 14342 r.immersive = immersive; 14343 14344 // update associated state if we're frontmost 14345 if (r == mStackSupervisor.getResumedActivityLocked()) { 14346 if (DEBUG_IMMERSIVE) Slog.d(TAG_IMMERSIVE, "Frontmost changed immersion: "+ r); 14347 applyUpdateLockStateLocked(r); 14348 } 14349 } 14350 } 14351 14352 @Override 14353 public boolean isImmersive(IBinder token) { 14354 synchronized (this) { 14355 ActivityRecord r = ActivityRecord.isInStackLocked(token); 14356 if (r == null) { 14357 throw new IllegalArgumentException(); 14358 } 14359 return r.immersive; 14360 } 14361 } 14362 14363 @Override 14364 public void setVrThread(int tid) { 14365 enforceSystemHasVrFeature(); 14366 synchronized (this) { 14367 synchronized (mPidsSelfLocked) { 14368 final int pid = Binder.getCallingPid(); 14369 final ProcessRecord proc = mPidsSelfLocked.get(pid); 14370 mVrController.setVrThreadLocked(tid, pid, proc); 14371 } 14372 } 14373 } 14374 14375 @Override 14376 public void setPersistentVrThread(int tid) { 14377 if (checkCallingPermission(permission.RESTRICTED_VR_ACCESS) != PERMISSION_GRANTED) { 14378 final String msg = "Permission Denial: setPersistentVrThread() from pid=" 14379 + Binder.getCallingPid() 14380 + ", uid=" + Binder.getCallingUid() 14381 + " requires " + permission.RESTRICTED_VR_ACCESS; 14382 Slog.w(TAG, msg); 14383 throw new SecurityException(msg); 14384 } 14385 enforceSystemHasVrFeature(); 14386 synchronized (this) { 14387 synchronized (mPidsSelfLocked) { 14388 final int pid = Binder.getCallingPid(); 14389 final ProcessRecord proc = mPidsSelfLocked.get(pid); 14390 mVrController.setPersistentVrThreadLocked(tid, pid, proc); 14391 } 14392 } 14393 } 14394 14395 /** 14396 * Schedule the given thread a normal scheduling priority. 14397 * 14398 * @param tid the tid of the thread to adjust the scheduling of. 14399 * @param suppressLogs {@code true} if any error logging should be disabled. 14400 * 14401 * @return {@code true} if this succeeded. 14402 */ 14403 static boolean scheduleAsRegularPriority(int tid, boolean suppressLogs) { 14404 try { 14405 Process.setThreadScheduler(tid, Process.SCHED_OTHER, 0); 14406 return true; 14407 } catch (IllegalArgumentException e) { 14408 if (!suppressLogs) { 14409 Slog.w(TAG, "Failed to set scheduling policy, thread does not exist:\n" + e); 14410 } 14411 } catch (SecurityException e) { 14412 if (!suppressLogs) { 14413 Slog.w(TAG, "Failed to set scheduling policy, not allowed:\n" + e); 14414 } 14415 } 14416 return false; 14417 } 14418 14419 /** 14420 * Schedule the given thread an FIFO scheduling priority. 14421 * 14422 * @param tid the tid of the thread to adjust the scheduling of. 14423 * @param suppressLogs {@code true} if any error logging should be disabled. 14424 * 14425 * @return {@code true} if this succeeded. 14426 */ 14427 static boolean scheduleAsFifoPriority(int tid, boolean suppressLogs) { 14428 try { 14429 Process.setThreadScheduler(tid, Process.SCHED_FIFO | Process.SCHED_RESET_ON_FORK, 1); 14430 return true; 14431 } catch (IllegalArgumentException e) { 14432 if (!suppressLogs) { 14433 Slog.w(TAG, "Failed to set scheduling policy, thread does not exist:\n" + e); 14434 } 14435 } catch (SecurityException e) { 14436 if (!suppressLogs) { 14437 Slog.w(TAG, "Failed to set scheduling policy, not allowed:\n" + e); 14438 } 14439 } 14440 return false; 14441 } 14442 14443 /** 14444 * Check that we have the features required for VR-related API calls, and throw an exception if 14445 * not. 14446 */ 14447 private void enforceSystemHasVrFeature() { 14448 if (!mContext.getPackageManager().hasSystemFeature( 14449 PackageManager.FEATURE_VR_MODE_HIGH_PERFORMANCE)) { 14450 throw new UnsupportedOperationException("VR mode not supported on this device!"); 14451 } 14452 } 14453 14454 @Override 14455 public void setRenderThread(int tid) { 14456 synchronized (this) { 14457 ProcessRecord proc; 14458 int pid = Binder.getCallingPid(); 14459 if (pid == Process.myPid()) { 14460 demoteSystemServerRenderThread(tid); 14461 return; 14462 } 14463 synchronized (mPidsSelfLocked) { 14464 proc = mPidsSelfLocked.get(pid); 14465 if (proc != null && proc.renderThreadTid == 0 && tid > 0) { 14466 // ensure the tid belongs to the process 14467 if (!isThreadInProcess(pid, tid)) { 14468 throw new IllegalArgumentException( 14469 "Render thread does not belong to process"); 14470 } 14471 proc.renderThreadTid = tid; 14472 if (DEBUG_OOM_ADJ) { 14473 Slog.d("UI_FIFO", "Set RenderThread tid " + tid + " for pid " + pid); 14474 } 14475 // promote to FIFO now 14476 if (proc.curSchedGroup == ProcessList.SCHED_GROUP_TOP_APP) { 14477 if (DEBUG_OOM_ADJ) Slog.d("UI_FIFO", "Promoting " + tid + "out of band"); 14478 if (mUseFifoUiScheduling) { 14479 setThreadScheduler(proc.renderThreadTid, 14480 SCHED_FIFO | SCHED_RESET_ON_FORK, 1); 14481 } else { 14482 setThreadPriority(proc.renderThreadTid, TOP_APP_PRIORITY_BOOST); 14483 } 14484 } 14485 } else { 14486 if (DEBUG_OOM_ADJ) { 14487 Slog.d("UI_FIFO", "Didn't set thread from setRenderThread? " + 14488 "PID: " + pid + ", TID: " + tid + " FIFO: " + 14489 mUseFifoUiScheduling); 14490 } 14491 } 14492 } 14493 } 14494 } 14495 14496 /** 14497 * We only use RenderThread in system_server to store task snapshots to the disk, which should 14498 * happen in the background. Thus, demote render thread from system_server to a lower priority. 14499 * 14500 * @param tid the tid of the RenderThread 14501 */ 14502 private void demoteSystemServerRenderThread(int tid) { 14503 setThreadPriority(tid, Process.THREAD_PRIORITY_BACKGROUND); 14504 } 14505 14506 @Override 14507 public int setVrMode(IBinder token, boolean enabled, ComponentName packageName) { 14508 enforceSystemHasVrFeature(); 14509 14510 final VrManagerInternal vrService = LocalServices.getService(VrManagerInternal.class); 14511 14512 ActivityRecord r; 14513 synchronized (this) { 14514 r = ActivityRecord.isInStackLocked(token); 14515 } 14516 14517 if (r == null) { 14518 throw new IllegalArgumentException(); 14519 } 14520 14521 int err; 14522 if ((err = vrService.hasVrPackage(packageName, r.userId)) != 14523 VrManagerInternal.NO_ERROR) { 14524 return err; 14525 } 14526 14527 // Clear the binder calling uid since this path may call moveToTask(). 14528 final long callingId = Binder.clearCallingIdentity(); 14529 try { 14530 synchronized(this) { 14531 r.requestedVrComponent = (enabled) ? packageName : null; 14532 14533 // Update associated state if this activity is currently focused 14534 if (r == mStackSupervisor.getResumedActivityLocked()) { 14535 applyUpdateVrModeLocked(r); 14536 } 14537 return 0; 14538 } 14539 } finally { 14540 Binder.restoreCallingIdentity(callingId); 14541 } 14542 } 14543 14544 @Override 14545 public boolean isVrModePackageEnabled(ComponentName packageName) { 14546 enforceSystemHasVrFeature(); 14547 14548 final VrManagerInternal vrService = LocalServices.getService(VrManagerInternal.class); 14549 14550 return vrService.hasVrPackage(packageName, UserHandle.getCallingUserId()) == 14551 VrManagerInternal.NO_ERROR; 14552 } 14553 14554 public boolean isTopActivityImmersive() { 14555 enforceNotIsolatedCaller("startActivity"); 14556 synchronized (this) { 14557 ActivityRecord r = getFocusedStack().topRunningActivityLocked(); 14558 return (r != null) ? r.immersive : false; 14559 } 14560 } 14561 14562 /** 14563 * @return whether the system should disable UI modes incompatible with VR mode. 14564 */ 14565 boolean shouldDisableNonVrUiLocked() { 14566 return mVrController.shouldDisableNonVrUiLocked(); 14567 } 14568 14569 @Override 14570 public boolean isTopOfTask(IBinder token) { 14571 synchronized (this) { 14572 ActivityRecord r = ActivityRecord.isInStackLocked(token); 14573 if (r == null) { 14574 throw new IllegalArgumentException(); 14575 } 14576 return r.getTask().getTopActivity() == r; 14577 } 14578 } 14579 14580 @Override 14581 public void setHasTopUi(boolean hasTopUi) throws RemoteException { 14582 if (checkCallingPermission(permission.INTERNAL_SYSTEM_WINDOW) != PERMISSION_GRANTED) { 14583 String msg = "Permission Denial: setHasTopUi() from pid=" 14584 + Binder.getCallingPid() 14585 + ", uid=" + Binder.getCallingUid() 14586 + " requires " + permission.INTERNAL_SYSTEM_WINDOW; 14587 Slog.w(TAG, msg); 14588 throw new SecurityException(msg); 14589 } 14590 final int pid = Binder.getCallingPid(); 14591 final long origId = Binder.clearCallingIdentity(); 14592 try { 14593 synchronized (this) { 14594 boolean changed = false; 14595 ProcessRecord pr; 14596 synchronized (mPidsSelfLocked) { 14597 pr = mPidsSelfLocked.get(pid); 14598 if (pr == null) { 14599 Slog.w(TAG, "setHasTopUi called on unknown pid: " + pid); 14600 return; 14601 } 14602 if (pr.hasTopUi != hasTopUi) { 14603 if (DEBUG_OOM_ADJ) { 14604 Slog.d(TAG, "Setting hasTopUi=" + hasTopUi + " for pid=" + pid); 14605 } 14606 pr.hasTopUi = hasTopUi; 14607 changed = true; 14608 } 14609 } 14610 if (changed) { 14611 updateOomAdjLocked(pr, true); 14612 } 14613 } 14614 } finally { 14615 Binder.restoreCallingIdentity(origId); 14616 } 14617 } 14618 14619 void setRunningRemoteAnimation(int pid, boolean runningRemoteAnimation) { 14620 if (pid == Process.myPid()) { 14621 Slog.wtf(TAG, "system can't run remote animation"); 14622 return; 14623 } 14624 synchronized (ActivityManagerService.this) { 14625 final ProcessRecord pr; 14626 synchronized (mPidsSelfLocked) { 14627 pr = mPidsSelfLocked.get(pid); 14628 if (pr == null) { 14629 Slog.w(TAG, "setRunningRemoteAnimation called on unknown pid: " + pid); 14630 return; 14631 } 14632 } 14633 if (pr.runningRemoteAnimation == runningRemoteAnimation) { 14634 return; 14635 } 14636 pr.runningRemoteAnimation = runningRemoteAnimation; 14637 if (DEBUG_OOM_ADJ) { 14638 Slog.i(TAG, "Setting runningRemoteAnimation=" + pr.runningRemoteAnimation 14639 + " for pid=" + pid); 14640 } 14641 updateOomAdjLocked(pr, true); 14642 } 14643 } 14644 14645 public final void enterSafeMode() { 14646 synchronized(this) { 14647 // It only makes sense to do this before the system is ready 14648 // and started launching other packages. 14649 if (!mSystemReady) { 14650 try { 14651 AppGlobals.getPackageManager().enterSafeMode(); 14652 } catch (RemoteException e) { 14653 } 14654 } 14655 14656 mSafeMode = true; 14657 } 14658 } 14659 14660 public final void showSafeModeOverlay() { 14661 View v = LayoutInflater.from(mContext).inflate( 14662 com.android.internal.R.layout.safe_mode, null); 14663 WindowManager.LayoutParams lp = new WindowManager.LayoutParams(); 14664 lp.type = WindowManager.LayoutParams.TYPE_SECURE_SYSTEM_OVERLAY; 14665 lp.width = WindowManager.LayoutParams.WRAP_CONTENT; 14666 lp.height = WindowManager.LayoutParams.WRAP_CONTENT; 14667 lp.gravity = Gravity.BOTTOM | Gravity.START; 14668 lp.format = v.getBackground().getOpacity(); 14669 lp.flags = WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE 14670 | WindowManager.LayoutParams.FLAG_NOT_TOUCHABLE; 14671 lp.privateFlags |= WindowManager.LayoutParams.PRIVATE_FLAG_SHOW_FOR_ALL_USERS; 14672 ((WindowManager)mContext.getSystemService( 14673 Context.WINDOW_SERVICE)).addView(v, lp); 14674 } 14675 14676 @Override 14677 public void noteWakeupAlarm(IIntentSender sender, WorkSource workSource, int sourceUid, 14678 String sourcePkg, String tag) { 14679 if (workSource != null && workSource.isEmpty()) { 14680 workSource = null; 14681 } 14682 14683 if (sourceUid <= 0 && workSource == null) { 14684 // Try and derive a UID to attribute things to based on the caller. 14685 if (sender != null) { 14686 if (!(sender instanceof PendingIntentRecord)) { 14687 return; 14688 } 14689 14690 final PendingIntentRecord rec = (PendingIntentRecord) sender; 14691 final int callerUid = Binder.getCallingUid(); 14692 sourceUid = rec.uid == callerUid ? SYSTEM_UID : rec.uid; 14693 } else { 14694 // TODO(narayan): Should we throw an exception in this case ? It means that we 14695 // haven't been able to derive a UID to attribute things to. 14696 return; 14697 } 14698 } 14699 14700 if (DEBUG_POWER) { 14701 Slog.w(TAG, "noteWakupAlarm[ sourcePkg=" + sourcePkg + ", sourceUid=" + sourceUid 14702 + ", workSource=" + workSource + ", tag=" + tag + "]"); 14703 } 14704 14705 mBatteryStatsService.noteWakupAlarm(sourcePkg, sourceUid, workSource, tag); 14706 } 14707 14708 @Override 14709 public void noteAlarmStart(IIntentSender sender, WorkSource workSource, int sourceUid, 14710 String tag) { 14711 if (workSource != null && workSource.isEmpty()) { 14712 workSource = null; 14713 } 14714 14715 if (sourceUid <= 0 && workSource == null) { 14716 // Try and derive a UID to attribute things to based on the caller. 14717 if (sender != null) { 14718 if (!(sender instanceof PendingIntentRecord)) { 14719 return; 14720 } 14721 14722 final PendingIntentRecord rec = (PendingIntentRecord) sender; 14723 final int callerUid = Binder.getCallingUid(); 14724 sourceUid = rec.uid == callerUid ? SYSTEM_UID : rec.uid; 14725 } else { 14726 // TODO(narayan): Should we throw an exception in this case ? It means that we 14727 // haven't been able to derive a UID to attribute things to. 14728 return; 14729 } 14730 } 14731 14732 if (DEBUG_POWER) { 14733 Slog.w(TAG, "noteAlarmStart[sourceUid=" + sourceUid + ", workSource=" + workSource + 14734 ", tag=" + tag + "]"); 14735 } 14736 14737 mBatteryStatsService.noteAlarmStart(tag, workSource, sourceUid); 14738 } 14739 14740 @Override 14741 public void noteAlarmFinish(IIntentSender sender, WorkSource workSource, int sourceUid, 14742 String tag) { 14743 if (workSource != null && workSource.isEmpty()) { 14744 workSource = null; 14745 } 14746 14747 if (sourceUid <= 0 && workSource == null) { 14748 // Try and derive a UID to attribute things to based on the caller. 14749 if (sender != null) { 14750 if (!(sender instanceof PendingIntentRecord)) { 14751 return; 14752 } 14753 14754 final PendingIntentRecord rec = (PendingIntentRecord) sender; 14755 final int callerUid = Binder.getCallingUid(); 14756 sourceUid = rec.uid == callerUid ? SYSTEM_UID : rec.uid; 14757 } else { 14758 // TODO(narayan): Should we throw an exception in this case ? It means that we 14759 // haven't been able to derive a UID to attribute things to. 14760 return; 14761 } 14762 } 14763 14764 if (DEBUG_POWER) { 14765 Slog.w(TAG, "noteAlarmFinish[sourceUid=" + sourceUid + ", workSource=" + workSource + 14766 ", tag=" + tag + "]"); 14767 } 14768 14769 mBatteryStatsService.noteAlarmFinish(tag, workSource, sourceUid); 14770 } 14771 14772 public boolean killPids(int[] pids, String pReason, boolean secure) { 14773 if (Binder.getCallingUid() != SYSTEM_UID) { 14774 throw new SecurityException("killPids only available to the system"); 14775 } 14776 String reason = (pReason == null) ? "Unknown" : pReason; 14777 // XXX Note: don't acquire main activity lock here, because the window 14778 // manager calls in with its locks held. 14779 14780 boolean killed = false; 14781 synchronized (mPidsSelfLocked) { 14782 int worstType = 0; 14783 for (int i=0; i<pids.length; i++) { 14784 ProcessRecord proc = mPidsSelfLocked.get(pids[i]); 14785 if (proc != null) { 14786 int type = proc.setAdj; 14787 if (type > worstType) { 14788 worstType = type; 14789 } 14790 } 14791 } 14792 14793 // If the worst oom_adj is somewhere in the cached proc LRU range, 14794 // then constrain it so we will kill all cached procs. 14795 if (worstType < ProcessList.CACHED_APP_MAX_ADJ 14796 && worstType > ProcessList.CACHED_APP_MIN_ADJ) { 14797 worstType = ProcessList.CACHED_APP_MIN_ADJ; 14798 } 14799 14800 // If this is not a secure call, don't let it kill processes that 14801 // are important. 14802 if (!secure && worstType < ProcessList.SERVICE_ADJ) { 14803 worstType = ProcessList.SERVICE_ADJ; 14804 } 14805 14806 Slog.w(TAG, "Killing processes " + reason + " at adjustment " + worstType); 14807 for (int i=0; i<pids.length; i++) { 14808 ProcessRecord proc = mPidsSelfLocked.get(pids[i]); 14809 if (proc == null) { 14810 continue; 14811 } 14812 int adj = proc.setAdj; 14813 if (adj >= worstType && !proc.killedByAm) { 14814 proc.kill(reason, true); 14815 killed = true; 14816 } 14817 } 14818 } 14819 return killed; 14820 } 14821 14822 @Override 14823 public void killUid(int appId, int userId, String reason) { 14824 enforceCallingPermission(Manifest.permission.KILL_UID, "killUid"); 14825 synchronized (this) { 14826 final long identity = Binder.clearCallingIdentity(); 14827 try { 14828 killPackageProcessesLocked(null, appId, userId, 14829 ProcessList.PERSISTENT_PROC_ADJ, false, true, true, true, 14830 reason != null ? reason : "kill uid"); 14831 } finally { 14832 Binder.restoreCallingIdentity(identity); 14833 } 14834 } 14835 } 14836 14837 @Override 14838 public boolean killProcessesBelowForeground(String reason) { 14839 if (Binder.getCallingUid() != SYSTEM_UID) { 14840 throw new SecurityException("killProcessesBelowForeground() only available to system"); 14841 } 14842 14843 return killProcessesBelowAdj(ProcessList.FOREGROUND_APP_ADJ, reason); 14844 } 14845 14846 private boolean killProcessesBelowAdj(int belowAdj, String reason) { 14847 if (Binder.getCallingUid() != SYSTEM_UID) { 14848 throw new SecurityException("killProcessesBelowAdj() only available to system"); 14849 } 14850 14851 boolean killed = false; 14852 synchronized (mPidsSelfLocked) { 14853 final int size = mPidsSelfLocked.size(); 14854 for (int i = 0; i < size; i++) { 14855 final int pid = mPidsSelfLocked.keyAt(i); 14856 final ProcessRecord proc = mPidsSelfLocked.valueAt(i); 14857 if (proc == null) continue; 14858 14859 final int adj = proc.setAdj; 14860 if (adj > belowAdj && !proc.killedByAm) { 14861 proc.kill(reason, true); 14862 killed = true; 14863 } 14864 } 14865 } 14866 return killed; 14867 } 14868 14869 @Override 14870 public void hang(final IBinder who, boolean allowRestart) { 14871 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 14872 != PackageManager.PERMISSION_GRANTED) { 14873 throw new SecurityException("Requires permission " 14874 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 14875 } 14876 14877 final IBinder.DeathRecipient death = new DeathRecipient() { 14878 @Override 14879 public void binderDied() { 14880 synchronized (this) { 14881 notifyAll(); 14882 } 14883 } 14884 }; 14885 14886 try { 14887 who.linkToDeath(death, 0); 14888 } catch (RemoteException e) { 14889 Slog.w(TAG, "hang: given caller IBinder is already dead."); 14890 return; 14891 } 14892 14893 synchronized (this) { 14894 Watchdog.getInstance().setAllowRestart(allowRestart); 14895 Slog.i(TAG, "Hanging system process at request of pid " + Binder.getCallingPid()); 14896 synchronized (death) { 14897 while (who.isBinderAlive()) { 14898 try { 14899 death.wait(); 14900 } catch (InterruptedException e) { 14901 } 14902 } 14903 } 14904 Watchdog.getInstance().setAllowRestart(true); 14905 } 14906 } 14907 14908 @Override 14909 public void restart() { 14910 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 14911 != PackageManager.PERMISSION_GRANTED) { 14912 throw new SecurityException("Requires permission " 14913 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 14914 } 14915 14916 Log.i(TAG, "Sending shutdown broadcast..."); 14917 14918 BroadcastReceiver br = new BroadcastReceiver() { 14919 @Override public void onReceive(Context context, Intent intent) { 14920 // Now the broadcast is done, finish up the low-level shutdown. 14921 Log.i(TAG, "Shutting down activity manager..."); 14922 shutdown(10000); 14923 Log.i(TAG, "Shutdown complete, restarting!"); 14924 killProcess(myPid()); 14925 System.exit(10); 14926 } 14927 }; 14928 14929 // First send the high-level shut down broadcast. 14930 Intent intent = new Intent(Intent.ACTION_SHUTDOWN); 14931 intent.addFlags(Intent.FLAG_RECEIVER_FOREGROUND); 14932 intent.putExtra(Intent.EXTRA_SHUTDOWN_USERSPACE_ONLY, true); 14933 /* For now we are not doing a clean shutdown, because things seem to get unhappy. 14934 mContext.sendOrderedBroadcastAsUser(intent, 14935 UserHandle.ALL, null, br, mHandler, 0, null, null); 14936 */ 14937 br.onReceive(mContext, intent); 14938 } 14939 14940 private long getLowRamTimeSinceIdle(long now) { 14941 return mLowRamTimeSinceLastIdle + (mLowRamStartTime > 0 ? (now-mLowRamStartTime) : 0); 14942 } 14943 14944 @Override 14945 public void performIdleMaintenance() { 14946 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 14947 != PackageManager.PERMISSION_GRANTED) { 14948 throw new SecurityException("Requires permission " 14949 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 14950 } 14951 14952 synchronized (this) { 14953 final long now = SystemClock.uptimeMillis(); 14954 final long timeSinceLastIdle = now - mLastIdleTime; 14955 final long lowRamSinceLastIdle = getLowRamTimeSinceIdle(now); 14956 mLastIdleTime = now; 14957 mLowRamTimeSinceLastIdle = 0; 14958 if (mLowRamStartTime != 0) { 14959 mLowRamStartTime = now; 14960 } 14961 14962 StringBuilder sb = new StringBuilder(128); 14963 sb.append("Idle maintenance over "); 14964 TimeUtils.formatDuration(timeSinceLastIdle, sb); 14965 sb.append(" low RAM for "); 14966 TimeUtils.formatDuration(lowRamSinceLastIdle, sb); 14967 Slog.i(TAG, sb.toString()); 14968 14969 // If at least 1/3 of our time since the last idle period has been spent 14970 // with RAM low, then we want to kill processes. 14971 boolean doKilling = lowRamSinceLastIdle > (timeSinceLastIdle/3); 14972 14973 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 14974 ProcessRecord proc = mLruProcesses.get(i); 14975 if (proc.notCachedSinceIdle) { 14976 if (proc.setProcState >= ActivityManager.PROCESS_STATE_BOUND_FOREGROUND_SERVICE 14977 && proc.setProcState <= ActivityManager.PROCESS_STATE_SERVICE) { 14978 if (doKilling && proc.initialIdlePss != 0 14979 && proc.lastPss > ((proc.initialIdlePss*3)/2)) { 14980 sb = new StringBuilder(128); 14981 sb.append("Kill"); 14982 sb.append(proc.processName); 14983 sb.append(" in idle maint: pss="); 14984 sb.append(proc.lastPss); 14985 sb.append(", swapPss="); 14986 sb.append(proc.lastSwapPss); 14987 sb.append(", initialPss="); 14988 sb.append(proc.initialIdlePss); 14989 sb.append(", period="); 14990 TimeUtils.formatDuration(timeSinceLastIdle, sb); 14991 sb.append(", lowRamPeriod="); 14992 TimeUtils.formatDuration(lowRamSinceLastIdle, sb); 14993 Slog.wtfQuiet(TAG, sb.toString()); 14994 proc.kill("idle maint (pss " + proc.lastPss 14995 + " from " + proc.initialIdlePss + ")", true); 14996 } 14997 } 14998 } else if (proc.setProcState < ActivityManager.PROCESS_STATE_HOME 14999 && proc.setProcState >= ActivityManager.PROCESS_STATE_PERSISTENT) { 15000 proc.notCachedSinceIdle = true; 15001 proc.initialIdlePss = 0; 15002 proc.nextPssTime = ProcessList.computeNextPssTime(proc.setProcState, null, 15003 mTestPssMode, isSleepingLocked(), now); 15004 } 15005 } 15006 } 15007 } 15008 15009 @Override 15010 public void sendIdleJobTrigger() { 15011 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 15012 != PackageManager.PERMISSION_GRANTED) { 15013 throw new SecurityException("Requires permission " 15014 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 15015 } 15016 15017 final long ident = Binder.clearCallingIdentity(); 15018 try { 15019 Intent intent = new Intent(ACTION_TRIGGER_IDLE) 15020 .setPackage("android") 15021 .addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 15022 broadcastIntent(null, intent, null, null, 0, null, null, null, 15023 OP_NONE, null, false, false, UserHandle.USER_ALL); 15024 } finally { 15025 Binder.restoreCallingIdentity(ident); 15026 } 15027 } 15028 15029 private void retrieveSettings() { 15030 final ContentResolver resolver = mContext.getContentResolver(); 15031 final boolean freeformWindowManagement = 15032 mContext.getPackageManager().hasSystemFeature(FEATURE_FREEFORM_WINDOW_MANAGEMENT) 15033 || Settings.Global.getInt( 15034 resolver, DEVELOPMENT_ENABLE_FREEFORM_WINDOWS_SUPPORT, 0) != 0; 15035 15036 final boolean supportsMultiWindow = ActivityManager.supportsMultiWindow(mContext); 15037 final boolean supportsPictureInPicture = supportsMultiWindow && 15038 mContext.getPackageManager().hasSystemFeature(FEATURE_PICTURE_IN_PICTURE); 15039 final boolean supportsSplitScreenMultiWindow = 15040 ActivityManager.supportsSplitScreenMultiWindow(mContext); 15041 final boolean supportsMultiDisplay = mContext.getPackageManager() 15042 .hasSystemFeature(FEATURE_ACTIVITIES_ON_SECONDARY_DISPLAYS); 15043 final String debugApp = Settings.Global.getString(resolver, DEBUG_APP); 15044 final boolean waitForDebugger = Settings.Global.getInt(resolver, WAIT_FOR_DEBUGGER, 0) != 0; 15045 final boolean alwaysFinishActivities = 15046 Settings.Global.getInt(resolver, ALWAYS_FINISH_ACTIVITIES, 0) != 0; 15047 final boolean forceRtl = Settings.Global.getInt(resolver, DEVELOPMENT_FORCE_RTL, 0) != 0; 15048 final boolean forceResizable = Settings.Global.getInt( 15049 resolver, DEVELOPMENT_FORCE_RESIZABLE_ACTIVITIES, 0) != 0; 15050 final long waitForNetworkTimeoutMs = Settings.Global.getLong(resolver, 15051 NETWORK_ACCESS_TIMEOUT_MS, NETWORK_ACCESS_TIMEOUT_DEFAULT_MS); 15052 final boolean supportsLeanbackOnly = 15053 mContext.getPackageManager().hasSystemFeature(FEATURE_LEANBACK_ONLY); 15054 mHiddenApiBlacklist.registerObserver(); 15055 15056 // Transfer any global setting for forcing RTL layout, into a System Property 15057 SystemProperties.set(DEVELOPMENT_FORCE_RTL, forceRtl ? "1":"0"); 15058 15059 final Configuration configuration = new Configuration(); 15060 Settings.System.getConfiguration(resolver, configuration); 15061 if (forceRtl) { 15062 // This will take care of setting the correct layout direction flags 15063 configuration.setLayoutDirection(configuration.locale); 15064 } 15065 15066 synchronized (this) { 15067 mDebugApp = mOrigDebugApp = debugApp; 15068 mWaitForDebugger = mOrigWaitForDebugger = waitForDebugger; 15069 mAlwaysFinishActivities = alwaysFinishActivities; 15070 mSupportsLeanbackOnly = supportsLeanbackOnly; 15071 mForceResizableActivities = forceResizable; 15072 final boolean multiWindowFormEnabled = freeformWindowManagement 15073 || supportsSplitScreenMultiWindow 15074 || supportsPictureInPicture 15075 || supportsMultiDisplay; 15076 if ((supportsMultiWindow || forceResizable) && multiWindowFormEnabled) { 15077 mSupportsMultiWindow = true; 15078 mSupportsFreeformWindowManagement = freeformWindowManagement; 15079 mSupportsSplitScreenMultiWindow = supportsSplitScreenMultiWindow; 15080 mSupportsPictureInPicture = supportsPictureInPicture; 15081 mSupportsMultiDisplay = supportsMultiDisplay; 15082 } else { 15083 mSupportsMultiWindow = false; 15084 mSupportsFreeformWindowManagement = false; 15085 mSupportsSplitScreenMultiWindow = false; 15086 mSupportsPictureInPicture = false; 15087 mSupportsMultiDisplay = false; 15088 } 15089 mWindowManager.setForceResizableTasks(mForceResizableActivities); 15090 mWindowManager.setSupportsPictureInPicture(mSupportsPictureInPicture); 15091 // This happens before any activities are started, so we can change global configuration 15092 // in-place. 15093 updateConfigurationLocked(configuration, null, true); 15094 final Configuration globalConfig = getGlobalConfiguration(); 15095 if (DEBUG_CONFIGURATION) Slog.v(TAG_CONFIGURATION, "Initial config: " + globalConfig); 15096 15097 // Load resources only after the current configuration has been set. 15098 final Resources res = mContext.getResources(); 15099 mThumbnailWidth = res.getDimensionPixelSize( 15100 com.android.internal.R.dimen.thumbnail_width); 15101 mThumbnailHeight = res.getDimensionPixelSize( 15102 com.android.internal.R.dimen.thumbnail_height); 15103 mAppErrors.loadAppsNotReportingCrashesFromConfigLocked(res.getString( 15104 com.android.internal.R.string.config_appsNotReportingCrashes)); 15105 mUserController.mUserSwitchUiEnabled = !res.getBoolean( 15106 com.android.internal.R.bool.config_customUserSwitchUi); 15107 mUserController.mMaxRunningUsers = res.getInteger( 15108 com.android.internal.R.integer.config_multiuserMaxRunningUsers); 15109 15110 if ((globalConfig.uiMode & UI_MODE_TYPE_TELEVISION) == UI_MODE_TYPE_TELEVISION) { 15111 mFullscreenThumbnailScale = (float) res 15112 .getInteger(com.android.internal.R.integer.thumbnail_width_tv) / 15113 (float) globalConfig.screenWidthDp; 15114 } else { 15115 mFullscreenThumbnailScale = res.getFraction( 15116 com.android.internal.R.fraction.thumbnail_fullscreen_scale, 1, 1); 15117 } 15118 mWaitForNetworkTimeoutMs = waitForNetworkTimeoutMs; 15119 } 15120 } 15121 15122 public void systemReady(final Runnable goingCallback, TimingsTraceLog traceLog) { 15123 traceLog.traceBegin("PhaseActivityManagerReady"); 15124 synchronized(this) { 15125 if (mSystemReady) { 15126 // If we're done calling all the receivers, run the next "boot phase" passed in 15127 // by the SystemServer 15128 if (goingCallback != null) { 15129 goingCallback.run(); 15130 } 15131 return; 15132 } 15133 15134 mHasHeavyWeightFeature = mContext.getPackageManager().hasSystemFeature( 15135 PackageManager.FEATURE_CANT_SAVE_STATE); 15136 mLocalDeviceIdleController 15137 = LocalServices.getService(DeviceIdleController.LocalService.class); 15138 mAssistUtils = new AssistUtils(mContext); 15139 mVrController.onSystemReady(); 15140 // Make sure we have the current profile info, since it is needed for security checks. 15141 mUserController.onSystemReady(); 15142 mRecentTasks.onSystemReadyLocked(); 15143 mAppOpsService.systemReady(); 15144 mSystemReady = true; 15145 } 15146 15147 try { 15148 sTheRealBuildSerial = IDeviceIdentifiersPolicyService.Stub.asInterface( 15149 ServiceManager.getService(Context.DEVICE_IDENTIFIERS_SERVICE)) 15150 .getSerial(); 15151 } catch (RemoteException e) {} 15152 15153 ArrayList<ProcessRecord> procsToKill = null; 15154 synchronized(mPidsSelfLocked) { 15155 for (int i=mPidsSelfLocked.size()-1; i>=0; i--) { 15156 ProcessRecord proc = mPidsSelfLocked.valueAt(i); 15157 if (!isAllowedWhileBooting(proc.info)){ 15158 if (procsToKill == null) { 15159 procsToKill = new ArrayList<ProcessRecord>(); 15160 } 15161 procsToKill.add(proc); 15162 } 15163 } 15164 } 15165 15166 synchronized(this) { 15167 if (procsToKill != null) { 15168 for (int i=procsToKill.size()-1; i>=0; i--) { 15169 ProcessRecord proc = procsToKill.get(i); 15170 Slog.i(TAG, "Removing system update proc: " + proc); 15171 removeProcessLocked(proc, true, false, "system update done"); 15172 } 15173 } 15174 15175 // Now that we have cleaned up any update processes, we 15176 // are ready to start launching real processes and know that 15177 // we won't trample on them any more. 15178 mProcessesReady = true; 15179 } 15180 15181 Slog.i(TAG, "System now ready"); 15182 EventLog.writeEvent(EventLogTags.BOOT_PROGRESS_AMS_READY, 15183 SystemClock.uptimeMillis()); 15184 15185 synchronized(this) { 15186 // Make sure we have no pre-ready processes sitting around. 15187 15188 if (mFactoryTest == FactoryTest.FACTORY_TEST_LOW_LEVEL) { 15189 ResolveInfo ri = mContext.getPackageManager() 15190 .resolveActivity(new Intent(Intent.ACTION_FACTORY_TEST), 15191 STOCK_PM_FLAGS); 15192 CharSequence errorMsg = null; 15193 if (ri != null) { 15194 ActivityInfo ai = ri.activityInfo; 15195 ApplicationInfo app = ai.applicationInfo; 15196 if ((app.flags&ApplicationInfo.FLAG_SYSTEM) != 0) { 15197 mTopAction = Intent.ACTION_FACTORY_TEST; 15198 mTopData = null; 15199 mTopComponent = new ComponentName(app.packageName, 15200 ai.name); 15201 } else { 15202 errorMsg = mContext.getResources().getText( 15203 com.android.internal.R.string.factorytest_not_system); 15204 } 15205 } else { 15206 errorMsg = mContext.getResources().getText( 15207 com.android.internal.R.string.factorytest_no_action); 15208 } 15209 if (errorMsg != null) { 15210 mTopAction = null; 15211 mTopData = null; 15212 mTopComponent = null; 15213 Message msg = Message.obtain(); 15214 msg.what = SHOW_FACTORY_ERROR_UI_MSG; 15215 msg.getData().putCharSequence("msg", errorMsg); 15216 mUiHandler.sendMessage(msg); 15217 } 15218 } 15219 } 15220 15221 retrieveSettings(); 15222 final int currentUserId = mUserController.getCurrentUserId(); 15223 synchronized (this) { 15224 readGrantedUriPermissionsLocked(); 15225 } 15226 15227 final PowerManagerInternal pmi = LocalServices.getService(PowerManagerInternal.class); 15228 if (pmi != null) { 15229 pmi.registerLowPowerModeObserver(ServiceType.FORCE_BACKGROUND_CHECK, 15230 state -> updateForceBackgroundCheck(state.batterySaverEnabled)); 15231 updateForceBackgroundCheck( 15232 pmi.getLowPowerState(ServiceType.FORCE_BACKGROUND_CHECK).batterySaverEnabled); 15233 } else { 15234 Slog.wtf(TAG, "PowerManagerInternal not found."); 15235 } 15236 15237 if (goingCallback != null) goingCallback.run(); 15238 traceLog.traceBegin("ActivityManagerStartApps"); 15239 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_USER_RUNNING_START, 15240 Integer.toString(currentUserId), currentUserId); 15241 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_USER_FOREGROUND_START, 15242 Integer.toString(currentUserId), currentUserId); 15243 mSystemServiceManager.startUser(currentUserId); 15244 15245 synchronized (this) { 15246 // Only start up encryption-aware persistent apps; once user is 15247 // unlocked we'll come back around and start unaware apps 15248 startPersistentApps(PackageManager.MATCH_DIRECT_BOOT_AWARE); 15249 15250 // Start up initial activity. 15251 mBooting = true; 15252 // Enable home activity for system user, so that the system can always boot. We don't 15253 // do this when the system user is not setup since the setup wizard should be the one 15254 // to handle home activity in this case. 15255 if (UserManager.isSplitSystemUser() && 15256 Settings.Secure.getInt(mContext.getContentResolver(), 15257 Settings.Secure.USER_SETUP_COMPLETE, 0) != 0) { 15258 ComponentName cName = new ComponentName(mContext, SystemUserHomeActivity.class); 15259 try { 15260 AppGlobals.getPackageManager().setComponentEnabledSetting(cName, 15261 PackageManager.COMPONENT_ENABLED_STATE_ENABLED, 0, 15262 UserHandle.USER_SYSTEM); 15263 } catch (RemoteException e) { 15264 throw e.rethrowAsRuntimeException(); 15265 } 15266 } 15267 startHomeActivityLocked(currentUserId, "systemReady"); 15268 15269 try { 15270 if (AppGlobals.getPackageManager().hasSystemUidErrors()) { 15271 Slog.e(TAG, "UIDs on the system are inconsistent, you need to wipe your" 15272 + " data partition or your device will be unstable."); 15273 mUiHandler.obtainMessage(SHOW_UID_ERROR_UI_MSG).sendToTarget(); 15274 } 15275 } catch (RemoteException e) { 15276 } 15277 15278 if (!Build.isBuildConsistent()) { 15279 Slog.e(TAG, "Build fingerprint is not consistent, warning user"); 15280 mUiHandler.obtainMessage(SHOW_FINGERPRINT_ERROR_UI_MSG).sendToTarget(); 15281 } 15282 15283 long ident = Binder.clearCallingIdentity(); 15284 try { 15285 Intent intent = new Intent(Intent.ACTION_USER_STARTED); 15286 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 15287 | Intent.FLAG_RECEIVER_FOREGROUND); 15288 intent.putExtra(Intent.EXTRA_USER_HANDLE, currentUserId); 15289 broadcastIntentLocked(null, null, intent, 15290 null, null, 0, null, null, null, OP_NONE, 15291 null, false, false, MY_PID, SYSTEM_UID, 15292 currentUserId); 15293 intent = new Intent(Intent.ACTION_USER_STARTING); 15294 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 15295 intent.putExtra(Intent.EXTRA_USER_HANDLE, currentUserId); 15296 broadcastIntentLocked(null, null, intent, 15297 null, new IIntentReceiver.Stub() { 15298 @Override 15299 public void performReceive(Intent intent, int resultCode, String data, 15300 Bundle extras, boolean ordered, boolean sticky, int sendingUser) 15301 throws RemoteException { 15302 } 15303 }, 0, null, null, 15304 new String[] {INTERACT_ACROSS_USERS}, OP_NONE, 15305 null, true, false, MY_PID, SYSTEM_UID, UserHandle.USER_ALL); 15306 } catch (Throwable t) { 15307 Slog.wtf(TAG, "Failed sending first user broadcasts", t); 15308 } finally { 15309 Binder.restoreCallingIdentity(ident); 15310 } 15311 mStackSupervisor.resumeFocusedStackTopActivityLocked(); 15312 mUserController.sendUserSwitchBroadcasts(-1, currentUserId); 15313 15314 BinderInternal.nSetBinderProxyCountWatermarks(6000,5500); 15315 BinderInternal.nSetBinderProxyCountEnabled(true); 15316 BinderInternal.setBinderProxyCountCallback( 15317 new BinderInternal.BinderProxyLimitListener() { 15318 @Override 15319 public void onLimitReached(int uid) { 15320 Slog.wtf(TAG, "Uid " + uid + " sent too many Binders to uid " 15321 + Process.myUid()); 15322 if (uid == Process.SYSTEM_UID) { 15323 Slog.i(TAG, "Skipping kill (uid is SYSTEM)"); 15324 } else { 15325 killUid(UserHandle.getAppId(uid), UserHandle.getUserId(uid), 15326 "Too many Binders sent to SYSTEM"); 15327 } 15328 } 15329 }, mHandler); 15330 15331 traceLog.traceEnd(); // ActivityManagerStartApps 15332 traceLog.traceEnd(); // PhaseActivityManagerReady 15333 } 15334 } 15335 15336 private void updateForceBackgroundCheck(boolean enabled) { 15337 synchronized (this) { 15338 if (mForceBackgroundCheck != enabled) { 15339 mForceBackgroundCheck = enabled; 15340 15341 if (DEBUG_BACKGROUND_CHECK) { 15342 Slog.i(TAG, "Force background check " + (enabled ? "enabled" : "disabled")); 15343 } 15344 15345 if (mForceBackgroundCheck) { 15346 // Stop background services for idle UIDs. 15347 doStopUidForIdleUidsLocked(); 15348 } 15349 } 15350 } 15351 } 15352 15353 void killAppAtUsersRequest(ProcessRecord app, Dialog fromDialog) { 15354 synchronized (this) { 15355 mAppErrors.killAppAtUserRequestLocked(app, fromDialog); 15356 } 15357 } 15358 15359 void skipCurrentReceiverLocked(ProcessRecord app) { 15360 for (BroadcastQueue queue : mBroadcastQueues) { 15361 queue.skipCurrentReceiverLocked(app); 15362 } 15363 } 15364 15365 /** 15366 * Used by {@link com.android.internal.os.RuntimeInit} to report when an application crashes. 15367 * The application process will exit immediately after this call returns. 15368 * @param app object of the crashing app, null for the system server 15369 * @param crashInfo describing the exception 15370 */ 15371 public void handleApplicationCrash(IBinder app, 15372 ApplicationErrorReport.ParcelableCrashInfo crashInfo) { 15373 ProcessRecord r = findAppProcess(app, "Crash"); 15374 final String processName = app == null ? "system_server" 15375 : (r == null ? "unknown" : r.processName); 15376 15377 handleApplicationCrashInner("crash", r, processName, crashInfo); 15378 } 15379 15380 /* Native crash reporting uses this inner version because it needs to be somewhat 15381 * decoupled from the AM-managed cleanup lifecycle 15382 */ 15383 void handleApplicationCrashInner(String eventType, ProcessRecord r, String processName, 15384 ApplicationErrorReport.CrashInfo crashInfo) { 15385 EventLog.writeEvent(EventLogTags.AM_CRASH, Binder.getCallingPid(), 15386 UserHandle.getUserId(Binder.getCallingUid()), processName, 15387 r == null ? -1 : r.info.flags, 15388 crashInfo.exceptionClassName, 15389 crashInfo.exceptionMessage, 15390 crashInfo.throwFileName, 15391 crashInfo.throwLineNumber); 15392 15393 StatsLog.write(StatsLog.APP_CRASH_OCCURRED, 15394 Binder.getCallingUid(), 15395 eventType, 15396 processName, 15397 Binder.getCallingPid(), 15398 (r != null && r.info != null) ? r.info.packageName : "", 15399 (r != null && r.info != null) ? (r.info.isInstantApp() 15400 ? StatsLog.APP_CRASH_OCCURRED__IS_INSTANT_APP__TRUE 15401 : StatsLog.APP_CRASH_OCCURRED__IS_INSTANT_APP__FALSE) 15402 : StatsLog.APP_CRASH_OCCURRED__IS_INSTANT_APP__UNAVAILABLE, 15403 r != null ? (r.isInterestingToUserLocked() 15404 ? StatsLog.APP_CRASH_OCCURRED__FOREGROUND_STATE__FOREGROUND 15405 : StatsLog.APP_CRASH_OCCURRED__FOREGROUND_STATE__BACKGROUND) 15406 : StatsLog.APP_CRASH_OCCURRED__FOREGROUND_STATE__UNKNOWN 15407 ); 15408 15409 addErrorToDropBox(eventType, r, processName, null, null, null, null, null, crashInfo); 15410 15411 mAppErrors.crashApplication(r, crashInfo); 15412 } 15413 15414 public void handleApplicationStrictModeViolation( 15415 IBinder app, 15416 int violationMask, 15417 StrictMode.ViolationInfo info) { 15418 // We're okay if the ProcessRecord is missing; it probably means that 15419 // we're reporting a violation from the system process itself. 15420 final ProcessRecord r = findAppProcess(app, "StrictMode"); 15421 15422 if ((violationMask & StrictMode.PENALTY_DROPBOX) != 0) { 15423 Integer stackFingerprint = info.hashCode(); 15424 boolean logIt = true; 15425 synchronized (mAlreadyLoggedViolatedStacks) { 15426 if (mAlreadyLoggedViolatedStacks.contains(stackFingerprint)) { 15427 logIt = false; 15428 // TODO: sub-sample into EventLog for these, with 15429 // the info.durationMillis? Then we'd get 15430 // the relative pain numbers, without logging all 15431 // the stack traces repeatedly. We'd want to do 15432 // likewise in the client code, which also does 15433 // dup suppression, before the Binder call. 15434 } else { 15435 if (mAlreadyLoggedViolatedStacks.size() >= MAX_DUP_SUPPRESSED_STACKS) { 15436 mAlreadyLoggedViolatedStacks.clear(); 15437 } 15438 mAlreadyLoggedViolatedStacks.add(stackFingerprint); 15439 } 15440 } 15441 if (logIt) { 15442 logStrictModeViolationToDropBox(r, info); 15443 } 15444 } 15445 15446 if ((violationMask & StrictMode.PENALTY_DIALOG) != 0) { 15447 AppErrorResult result = new AppErrorResult(); 15448 synchronized (this) { 15449 final long origId = Binder.clearCallingIdentity(); 15450 15451 Message msg = Message.obtain(); 15452 msg.what = SHOW_STRICT_MODE_VIOLATION_UI_MSG; 15453 HashMap<String, Object> data = new HashMap<String, Object>(); 15454 data.put("result", result); 15455 data.put("app", r); 15456 data.put("violationMask", violationMask); 15457 data.put("info", info); 15458 msg.obj = data; 15459 mUiHandler.sendMessage(msg); 15460 15461 Binder.restoreCallingIdentity(origId); 15462 } 15463 int res = result.get(); 15464 Slog.w(TAG, "handleApplicationStrictModeViolation; res=" + res); 15465 } 15466 } 15467 15468 // Depending on the policy in effect, there could be a bunch of 15469 // these in quick succession so we try to batch these together to 15470 // minimize disk writes, number of dropbox entries, and maximize 15471 // compression, by having more fewer, larger records. 15472 private void logStrictModeViolationToDropBox( 15473 ProcessRecord process, 15474 StrictMode.ViolationInfo info) { 15475 if (info == null) { 15476 return; 15477 } 15478 final boolean isSystemApp = process == null || 15479 (process.info.flags & (ApplicationInfo.FLAG_SYSTEM | 15480 ApplicationInfo.FLAG_UPDATED_SYSTEM_APP)) != 0; 15481 final String processName = process == null ? "unknown" : process.processName; 15482 final DropBoxManager dbox = (DropBoxManager) 15483 mContext.getSystemService(Context.DROPBOX_SERVICE); 15484 15485 // Exit early if the dropbox isn't configured to accept this report type. 15486 final String dropboxTag = processClass(process) + "_strictmode"; 15487 if (dbox == null || !dbox.isTagEnabled(dropboxTag)) return; 15488 15489 final StringBuilder sb = new StringBuilder(1024); 15490 synchronized (sb) { 15491 appendDropBoxProcessHeaders(process, processName, sb); 15492 sb.append("Build: ").append(Build.FINGERPRINT).append("\n"); 15493 sb.append("System-App: ").append(isSystemApp).append("\n"); 15494 sb.append("Uptime-Millis: ").append(info.violationUptimeMillis).append("\n"); 15495 if (info.violationNumThisLoop != 0) { 15496 sb.append("Loop-Violation-Number: ").append(info.violationNumThisLoop).append("\n"); 15497 } 15498 if (info.numAnimationsRunning != 0) { 15499 sb.append("Animations-Running: ").append(info.numAnimationsRunning).append("\n"); 15500 } 15501 if (info.broadcastIntentAction != null) { 15502 sb.append("Broadcast-Intent-Action: ").append(info.broadcastIntentAction).append("\n"); 15503 } 15504 if (info.durationMillis != -1) { 15505 sb.append("Duration-Millis: ").append(info.durationMillis).append("\n"); 15506 } 15507 if (info.numInstances != -1) { 15508 sb.append("Instance-Count: ").append(info.numInstances).append("\n"); 15509 } 15510 if (info.tags != null) { 15511 for (String tag : info.tags) { 15512 sb.append("Span-Tag: ").append(tag).append("\n"); 15513 } 15514 } 15515 sb.append("\n"); 15516 sb.append(info.getStackTrace()); 15517 sb.append("\n"); 15518 if (info.getViolationDetails() != null) { 15519 sb.append(info.getViolationDetails()); 15520 sb.append("\n"); 15521 } 15522 } 15523 15524 final String res = sb.toString(); 15525 IoThread.getHandler().post(() -> { 15526 dbox.addText(dropboxTag, res); 15527 }); 15528 } 15529 15530 /** 15531 * Used by {@link Log} via {@link com.android.internal.os.RuntimeInit} to report serious errors. 15532 * @param app object of the crashing app, null for the system server 15533 * @param tag reported by the caller 15534 * @param system whether this wtf is coming from the system 15535 * @param crashInfo describing the context of the error 15536 * @return true if the process should exit immediately (WTF is fatal) 15537 */ 15538 public boolean handleApplicationWtf(final IBinder app, final String tag, boolean system, 15539 final ApplicationErrorReport.ParcelableCrashInfo crashInfo) { 15540 final int callingUid = Binder.getCallingUid(); 15541 final int callingPid = Binder.getCallingPid(); 15542 15543 if (system) { 15544 // If this is coming from the system, we could very well have low-level 15545 // system locks held, so we want to do this all asynchronously. And we 15546 // never want this to become fatal, so there is that too. 15547 mHandler.post(new Runnable() { 15548 @Override public void run() { 15549 handleApplicationWtfInner(callingUid, callingPid, app, tag, crashInfo); 15550 } 15551 }); 15552 return false; 15553 } 15554 15555 final ProcessRecord r = handleApplicationWtfInner(callingUid, callingPid, app, tag, 15556 crashInfo); 15557 15558 final boolean isFatal = Build.IS_ENG || Settings.Global 15559 .getInt(mContext.getContentResolver(), Settings.Global.WTF_IS_FATAL, 0) != 0; 15560 final boolean isSystem = (r == null) || r.persistent; 15561 15562 if (isFatal && !isSystem) { 15563 mAppErrors.crashApplication(r, crashInfo); 15564 return true; 15565 } else { 15566 return false; 15567 } 15568 } 15569 15570 ProcessRecord handleApplicationWtfInner(int callingUid, int callingPid, IBinder app, String tag, 15571 final ApplicationErrorReport.CrashInfo crashInfo) { 15572 final ProcessRecord r = findAppProcess(app, "WTF"); 15573 final String processName = app == null ? "system_server" 15574 : (r == null ? "unknown" : r.processName); 15575 15576 EventLog.writeEvent(EventLogTags.AM_WTF, UserHandle.getUserId(callingUid), callingPid, 15577 processName, r == null ? -1 : r.info.flags, tag, crashInfo.exceptionMessage); 15578 15579 StatsLog.write(StatsLog.WTF_OCCURRED, callingUid, tag, processName, 15580 callingPid); 15581 15582 addErrorToDropBox("wtf", r, processName, null, null, tag, null, null, crashInfo); 15583 15584 return r; 15585 } 15586 15587 /** 15588 * @param app object of some object (as stored in {@link com.android.internal.os.RuntimeInit}) 15589 * @return the corresponding {@link ProcessRecord} object, or null if none could be found 15590 */ 15591 private ProcessRecord findAppProcess(IBinder app, String reason) { 15592 if (app == null) { 15593 return null; 15594 } 15595 15596 synchronized (this) { 15597 final int NP = mProcessNames.getMap().size(); 15598 for (int ip=0; ip<NP; ip++) { 15599 SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 15600 final int NA = apps.size(); 15601 for (int ia=0; ia<NA; ia++) { 15602 ProcessRecord p = apps.valueAt(ia); 15603 if (p.thread != null && p.thread.asBinder() == app) { 15604 return p; 15605 } 15606 } 15607 } 15608 15609 Slog.w(TAG, "Can't find mystery application for " + reason 15610 + " from pid=" + Binder.getCallingPid() 15611 + " uid=" + Binder.getCallingUid() + ": " + app); 15612 return null; 15613 } 15614 } 15615 15616 /** 15617 * Utility function for addErrorToDropBox and handleStrictModeViolation's logging 15618 * to append various headers to the dropbox log text. 15619 */ 15620 private void appendDropBoxProcessHeaders(ProcessRecord process, String processName, 15621 StringBuilder sb) { 15622 // Watchdog thread ends up invoking this function (with 15623 // a null ProcessRecord) to add the stack file to dropbox. 15624 // Do not acquire a lock on this (am) in such cases, as it 15625 // could cause a potential deadlock, if and when watchdog 15626 // is invoked due to unavailability of lock on am and it 15627 // would prevent watchdog from killing system_server. 15628 if (process == null) { 15629 sb.append("Process: ").append(processName).append("\n"); 15630 return; 15631 } 15632 // Note: ProcessRecord 'process' is guarded by the service 15633 // instance. (notably process.pkgList, which could otherwise change 15634 // concurrently during execution of this method) 15635 synchronized (this) { 15636 sb.append("Process: ").append(processName).append("\n"); 15637 sb.append("PID: ").append(process.pid).append("\n"); 15638 int flags = process.info.flags; 15639 IPackageManager pm = AppGlobals.getPackageManager(); 15640 sb.append("Flags: 0x").append(Integer.toHexString(flags)).append("\n"); 15641 for (int ip=0; ip<process.pkgList.size(); ip++) { 15642 String pkg = process.pkgList.keyAt(ip); 15643 sb.append("Package: ").append(pkg); 15644 try { 15645 PackageInfo pi = pm.getPackageInfo(pkg, 0, UserHandle.getCallingUserId()); 15646 if (pi != null) { 15647 sb.append(" v").append(pi.getLongVersionCode()); 15648 if (pi.versionName != null) { 15649 sb.append(" (").append(pi.versionName).append(")"); 15650 } 15651 } 15652 } catch (RemoteException e) { 15653 Slog.e(TAG, "Error getting package info: " + pkg, e); 15654 } 15655 sb.append("\n"); 15656 } 15657 if (process.info.isInstantApp()) { 15658 sb.append("Instant-App: true\n"); 15659 } 15660 } 15661 } 15662 15663 private static String processClass(ProcessRecord process) { 15664 if (process == null || process.pid == MY_PID) { 15665 return "system_server"; 15666 } else if ((process.info.flags & ApplicationInfo.FLAG_SYSTEM) != 0) { 15667 return "system_app"; 15668 } else { 15669 return "data_app"; 15670 } 15671 } 15672 15673 private volatile long mWtfClusterStart; 15674 private volatile int mWtfClusterCount; 15675 15676 /** 15677 * Write a description of an error (crash, WTF, ANR) to the drop box. 15678 * @param eventType to include in the drop box tag ("crash", "wtf", etc.) 15679 * @param process which caused the error, null means the system server 15680 * @param activity which triggered the error, null if unknown 15681 * @param parent activity related to the error, null if unknown 15682 * @param subject line related to the error, null if absent 15683 * @param report in long form describing the error, null if absent 15684 * @param dataFile text file to include in the report, null if none 15685 * @param crashInfo giving an application stack trace, null if absent 15686 */ 15687 public void addErrorToDropBox(String eventType, 15688 ProcessRecord process, String processName, ActivityRecord activity, 15689 ActivityRecord parent, String subject, 15690 final String report, final File dataFile, 15691 final ApplicationErrorReport.CrashInfo crashInfo) { 15692 // NOTE -- this must never acquire the ActivityManagerService lock, 15693 // otherwise the watchdog may be prevented from resetting the system. 15694 15695 // Bail early if not published yet 15696 if (ServiceManager.getService(Context.DROPBOX_SERVICE) == null) return; 15697 final DropBoxManager dbox = mContext.getSystemService(DropBoxManager.class); 15698 15699 // Exit early if the dropbox isn't configured to accept this report type. 15700 final String dropboxTag = processClass(process) + "_" + eventType; 15701 if (dbox == null || !dbox.isTagEnabled(dropboxTag)) return; 15702 15703 // Rate-limit how often we're willing to do the heavy lifting below to 15704 // collect and record logs; currently 5 logs per 10 second period. 15705 final long now = SystemClock.elapsedRealtime(); 15706 if (now - mWtfClusterStart > 10 * DateUtils.SECOND_IN_MILLIS) { 15707 mWtfClusterStart = now; 15708 mWtfClusterCount = 1; 15709 } else { 15710 if (mWtfClusterCount++ >= 5) return; 15711 } 15712 15713 final StringBuilder sb = new StringBuilder(1024); 15714 appendDropBoxProcessHeaders(process, processName, sb); 15715 if (process != null) { 15716 sb.append("Foreground: ") 15717 .append(process.isInterestingToUserLocked() ? "Yes" : "No") 15718 .append("\n"); 15719 } 15720 if (activity != null) { 15721 sb.append("Activity: ").append(activity.shortComponentName).append("\n"); 15722 } 15723 if (parent != null && parent.app != null && parent.app.pid != process.pid) { 15724 sb.append("Parent-Process: ").append(parent.app.processName).append("\n"); 15725 } 15726 if (parent != null && parent != activity) { 15727 sb.append("Parent-Activity: ").append(parent.shortComponentName).append("\n"); 15728 } 15729 if (subject != null) { 15730 sb.append("Subject: ").append(subject).append("\n"); 15731 } 15732 sb.append("Build: ").append(Build.FINGERPRINT).append("\n"); 15733 if (Debug.isDebuggerConnected()) { 15734 sb.append("Debugger: Connected\n"); 15735 } 15736 sb.append("\n"); 15737 15738 // Do the rest in a worker thread to avoid blocking the caller on I/O 15739 // (After this point, we shouldn't access AMS internal data structures.) 15740 Thread worker = new Thread("Error dump: " + dropboxTag) { 15741 @Override 15742 public void run() { 15743 if (report != null) { 15744 sb.append(report); 15745 } 15746 15747 String setting = Settings.Global.ERROR_LOGCAT_PREFIX + dropboxTag; 15748 int lines = Settings.Global.getInt(mContext.getContentResolver(), setting, 0); 15749 int maxDataFileSize = DROPBOX_MAX_SIZE - sb.length() 15750 - lines * RESERVED_BYTES_PER_LOGCAT_LINE; 15751 15752 if (dataFile != null && maxDataFileSize > 0) { 15753 try { 15754 sb.append(FileUtils.readTextFile(dataFile, maxDataFileSize, 15755 "\n\n[[TRUNCATED]]")); 15756 } catch (IOException e) { 15757 Slog.e(TAG, "Error reading " + dataFile, e); 15758 } 15759 } 15760 if (crashInfo != null && crashInfo.stackTrace != null) { 15761 sb.append(crashInfo.stackTrace); 15762 } 15763 15764 if (lines > 0) { 15765 sb.append("\n"); 15766 15767 // Merge several logcat streams, and take the last N lines 15768 InputStreamReader input = null; 15769 try { 15770 java.lang.Process logcat = new ProcessBuilder( 15771 "/system/bin/timeout", "-k", "15s", "10s", 15772 "/system/bin/logcat", "-v", "threadtime", "-b", "events", "-b", "system", 15773 "-b", "main", "-b", "crash", "-t", String.valueOf(lines)) 15774 .redirectErrorStream(true).start(); 15775 15776 try { logcat.getOutputStream().close(); } catch (IOException e) {} 15777 try { logcat.getErrorStream().close(); } catch (IOException e) {} 15778 input = new InputStreamReader(logcat.getInputStream()); 15779 15780 int num; 15781 char[] buf = new char[8192]; 15782 while ((num = input.read(buf)) > 0) sb.append(buf, 0, num); 15783 } catch (IOException e) { 15784 Slog.e(TAG, "Error running logcat", e); 15785 } finally { 15786 if (input != null) try { input.close(); } catch (IOException e) {} 15787 } 15788 } 15789 15790 dbox.addText(dropboxTag, sb.toString()); 15791 } 15792 }; 15793 15794 if (process == null) { 15795 // If process is null, we are being called from some internal code 15796 // and may be about to die -- run this synchronously. 15797 final int oldMask = StrictMode.allowThreadDiskWritesMask(); 15798 try { 15799 worker.run(); 15800 } finally { 15801 StrictMode.setThreadPolicyMask(oldMask); 15802 } 15803 } else { 15804 worker.start(); 15805 } 15806 } 15807 15808 @Override 15809 public List<ActivityManager.ProcessErrorStateInfo> getProcessesInErrorState() { 15810 enforceNotIsolatedCaller("getProcessesInErrorState"); 15811 // assume our apps are happy - lazy create the list 15812 List<ActivityManager.ProcessErrorStateInfo> errList = null; 15813 15814 final boolean allUsers = ActivityManager.checkUidPermission(INTERACT_ACROSS_USERS_FULL, 15815 Binder.getCallingUid()) == PackageManager.PERMISSION_GRANTED; 15816 int userId = UserHandle.getUserId(Binder.getCallingUid()); 15817 15818 synchronized (this) { 15819 15820 // iterate across all processes 15821 for (int i=mLruProcesses.size()-1; i>=0; i--) { 15822 ProcessRecord app = mLruProcesses.get(i); 15823 if (!allUsers && app.userId != userId) { 15824 continue; 15825 } 15826 if ((app.thread != null) && (app.crashing || app.notResponding)) { 15827 // This one's in trouble, so we'll generate a report for it 15828 // crashes are higher priority (in case there's a crash *and* an anr) 15829 ActivityManager.ProcessErrorStateInfo report = null; 15830 if (app.crashing) { 15831 report = app.crashingReport; 15832 } else if (app.notResponding) { 15833 report = app.notRespondingReport; 15834 } 15835 15836 if (report != null) { 15837 if (errList == null) { 15838 errList = new ArrayList<ActivityManager.ProcessErrorStateInfo>(1); 15839 } 15840 errList.add(report); 15841 } else { 15842 Slog.w(TAG, "Missing app error report, app = " + app.processName + 15843 " crashing = " + app.crashing + 15844 " notResponding = " + app.notResponding); 15845 } 15846 } 15847 } 15848 } 15849 15850 return errList; 15851 } 15852 15853 static int procStateToImportance(int procState, int memAdj, 15854 ActivityManager.RunningAppProcessInfo currApp, 15855 int clientTargetSdk) { 15856 int imp = ActivityManager.RunningAppProcessInfo.procStateToImportanceForTargetSdk( 15857 procState, clientTargetSdk); 15858 if (imp == ActivityManager.RunningAppProcessInfo.IMPORTANCE_BACKGROUND) { 15859 currApp.lru = memAdj; 15860 } else { 15861 currApp.lru = 0; 15862 } 15863 return imp; 15864 } 15865 15866 private void fillInProcMemInfo(ProcessRecord app, 15867 ActivityManager.RunningAppProcessInfo outInfo, 15868 int clientTargetSdk) { 15869 outInfo.pid = app.pid; 15870 outInfo.uid = app.info.uid; 15871 if (mHeavyWeightProcess == app) { 15872 outInfo.flags |= ActivityManager.RunningAppProcessInfo.FLAG_CANT_SAVE_STATE; 15873 } 15874 if (app.persistent) { 15875 outInfo.flags |= ActivityManager.RunningAppProcessInfo.FLAG_PERSISTENT; 15876 } 15877 if (app.activities.size() > 0) { 15878 outInfo.flags |= ActivityManager.RunningAppProcessInfo.FLAG_HAS_ACTIVITIES; 15879 } 15880 outInfo.lastTrimLevel = app.trimMemoryLevel; 15881 int adj = app.curAdj; 15882 int procState = app.curProcState; 15883 outInfo.importance = procStateToImportance(procState, adj, outInfo, clientTargetSdk); 15884 outInfo.importanceReasonCode = app.adjTypeCode; 15885 outInfo.processState = app.curProcState; 15886 } 15887 15888 @Override 15889 public List<ActivityManager.RunningAppProcessInfo> getRunningAppProcesses() { 15890 enforceNotIsolatedCaller("getRunningAppProcesses"); 15891 15892 final int callingUid = Binder.getCallingUid(); 15893 final int clientTargetSdk = mPackageManagerInt.getUidTargetSdkVersion(callingUid); 15894 15895 // Lazy instantiation of list 15896 List<ActivityManager.RunningAppProcessInfo> runList = null; 15897 final boolean allUsers = ActivityManager.checkUidPermission(INTERACT_ACROSS_USERS_FULL, 15898 callingUid) == PackageManager.PERMISSION_GRANTED; 15899 final int userId = UserHandle.getUserId(callingUid); 15900 final boolean allUids = isGetTasksAllowed( 15901 "getRunningAppProcesses", Binder.getCallingPid(), callingUid); 15902 15903 synchronized (this) { 15904 // Iterate across all processes 15905 for (int i = mLruProcesses.size() - 1; i >= 0; i--) { 15906 ProcessRecord app = mLruProcesses.get(i); 15907 if ((!allUsers && app.userId != userId) 15908 || (!allUids && app.uid != callingUid)) { 15909 continue; 15910 } 15911 if ((app.thread != null) && (!app.crashing && !app.notResponding)) { 15912 // Generate process state info for running application 15913 ActivityManager.RunningAppProcessInfo currApp = 15914 new ActivityManager.RunningAppProcessInfo(app.processName, 15915 app.pid, app.getPackageList()); 15916 fillInProcMemInfo(app, currApp, clientTargetSdk); 15917 if (app.adjSource instanceof ProcessRecord) { 15918 currApp.importanceReasonPid = ((ProcessRecord)app.adjSource).pid; 15919 currApp.importanceReasonImportance = 15920 ActivityManager.RunningAppProcessInfo.procStateToImportance( 15921 app.adjSourceProcState); 15922 } else if (app.adjSource instanceof ActivityRecord) { 15923 ActivityRecord r = (ActivityRecord)app.adjSource; 15924 if (r.app != null) currApp.importanceReasonPid = r.app.pid; 15925 } 15926 if (app.adjTarget instanceof ComponentName) { 15927 currApp.importanceReasonComponent = (ComponentName)app.adjTarget; 15928 } 15929 //Slog.v(TAG, "Proc " + app.processName + ": imp=" + currApp.importance 15930 // + " lru=" + currApp.lru); 15931 if (runList == null) { 15932 runList = new ArrayList<>(); 15933 } 15934 runList.add(currApp); 15935 } 15936 } 15937 } 15938 return runList; 15939 } 15940 15941 @Override 15942 public List<ApplicationInfo> getRunningExternalApplications() { 15943 enforceNotIsolatedCaller("getRunningExternalApplications"); 15944 List<ActivityManager.RunningAppProcessInfo> runningApps = getRunningAppProcesses(); 15945 List<ApplicationInfo> retList = new ArrayList<ApplicationInfo>(); 15946 if (runningApps != null && runningApps.size() > 0) { 15947 Set<String> extList = new HashSet<String>(); 15948 for (ActivityManager.RunningAppProcessInfo app : runningApps) { 15949 if (app.pkgList != null) { 15950 for (String pkg : app.pkgList) { 15951 extList.add(pkg); 15952 } 15953 } 15954 } 15955 IPackageManager pm = AppGlobals.getPackageManager(); 15956 for (String pkg : extList) { 15957 try { 15958 ApplicationInfo info = pm.getApplicationInfo(pkg, 0, UserHandle.getCallingUserId()); 15959 if ((info.flags & ApplicationInfo.FLAG_EXTERNAL_STORAGE) != 0) { 15960 retList.add(info); 15961 } 15962 } catch (RemoteException e) { 15963 } 15964 } 15965 } 15966 return retList; 15967 } 15968 15969 @Override 15970 public void getMyMemoryState(ActivityManager.RunningAppProcessInfo outState) { 15971 if (outState == null) { 15972 throw new IllegalArgumentException("outState is null"); 15973 } 15974 enforceNotIsolatedCaller("getMyMemoryState"); 15975 15976 final int callingUid = Binder.getCallingUid(); 15977 final int clientTargetSdk = mPackageManagerInt.getUidTargetSdkVersion(callingUid); 15978 15979 synchronized (this) { 15980 ProcessRecord proc; 15981 synchronized (mPidsSelfLocked) { 15982 proc = mPidsSelfLocked.get(Binder.getCallingPid()); 15983 } 15984 if (proc != null) { 15985 fillInProcMemInfo(proc, outState, clientTargetSdk); 15986 } 15987 } 15988 } 15989 15990 @Override 15991 public int getMemoryTrimLevel() { 15992 enforceNotIsolatedCaller("getMyMemoryState"); 15993 synchronized (this) { 15994 return mLastMemoryLevel; 15995 } 15996 } 15997 15998 @Override 15999 public void onShellCommand(FileDescriptor in, FileDescriptor out, 16000 FileDescriptor err, String[] args, ShellCallback callback, 16001 ResultReceiver resultReceiver) { 16002 (new ActivityManagerShellCommand(this, false)).exec( 16003 this, in, out, err, args, callback, resultReceiver); 16004 } 16005 16006 SleepToken acquireSleepToken(String tag, int displayId) { 16007 synchronized (this) { 16008 final SleepToken token = mStackSupervisor.createSleepTokenLocked(tag, displayId); 16009 updateSleepIfNeededLocked(); 16010 return token; 16011 } 16012 } 16013 16014 @Override 16015 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 16016 PriorityDump.dump(mPriorityDumper, fd, pw, args); 16017 } 16018 16019 /** 16020 * Wrapper function to print out debug data filtered by specified arguments. 16021 */ 16022 private void doDump(FileDescriptor fd, PrintWriter pw, String[] args, boolean useProto) { 16023 if (!DumpUtils.checkDumpAndUsageStatsPermission(mContext, TAG, pw)) return; 16024 16025 boolean dumpAll = false; 16026 boolean dumpClient = false; 16027 boolean dumpCheckin = false; 16028 boolean dumpCheckinFormat = false; 16029 boolean dumpNormalPriority = false; 16030 boolean dumpVisibleStacksOnly = false; 16031 boolean dumpFocusedStackOnly = false; 16032 String dumpPackage = null; 16033 16034 int opti = 0; 16035 while (opti < args.length) { 16036 String opt = args[opti]; 16037 if (opt == null || opt.length() <= 0 || opt.charAt(0) != '-') { 16038 break; 16039 } 16040 opti++; 16041 if ("-a".equals(opt)) { 16042 dumpAll = true; 16043 } else if ("-c".equals(opt)) { 16044 dumpClient = true; 16045 } else if ("-v".equals(opt)) { 16046 dumpVisibleStacksOnly = true; 16047 } else if ("-f".equals(opt)) { 16048 dumpFocusedStackOnly = true; 16049 } else if ("-p".equals(opt)) { 16050 if (opti < args.length) { 16051 dumpPackage = args[opti]; 16052 opti++; 16053 } else { 16054 pw.println("Error: -p option requires package argument"); 16055 return; 16056 } 16057 dumpClient = true; 16058 } else if ("--checkin".equals(opt)) { 16059 dumpCheckin = dumpCheckinFormat = true; 16060 } else if ("-C".equals(opt)) { 16061 dumpCheckinFormat = true; 16062 } else if ("--normal-priority".equals(opt)) { 16063 dumpNormalPriority = true; 16064 } else if ("-h".equals(opt)) { 16065 ActivityManagerShellCommand.dumpHelp(pw, true); 16066 return; 16067 } else { 16068 pw.println("Unknown argument: " + opt + "; use -h for help"); 16069 } 16070 } 16071 16072 long origId = Binder.clearCallingIdentity(); 16073 16074 if (useProto) { 16075 final ProtoOutputStream proto = new ProtoOutputStream(fd); 16076 String cmd = opti < args.length ? args[opti] : ""; 16077 opti++; 16078 16079 if ("activities".equals(cmd) || "a".equals(cmd)) { 16080 // output proto is ActivityManagerServiceDumpActivitiesProto 16081 synchronized (this) { 16082 writeActivitiesToProtoLocked(proto); 16083 } 16084 } else if ("broadcasts".equals(cmd) || "b".equals(cmd)) { 16085 // output proto is ActivityManagerServiceDumpBroadcastsProto 16086 synchronized (this) { 16087 writeBroadcastsToProtoLocked(proto); 16088 } 16089 } else if ("provider".equals(cmd)) { 16090 String[] newArgs; 16091 String name; 16092 if (opti >= args.length) { 16093 name = null; 16094 newArgs = EMPTY_STRING_ARRAY; 16095 } else { 16096 name = args[opti]; 16097 opti++; 16098 newArgs = new String[args.length - opti]; 16099 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 16100 args.length - opti); 16101 } 16102 if (!dumpProviderProto(fd, pw, name, newArgs)) { 16103 pw.println("No providers match: " + name); 16104 pw.println("Use -h for help."); 16105 } 16106 } else if ("service".equals(cmd)) { 16107 // output proto is ActivityManagerServiceDumpServicesProto 16108 mServices.writeToProto(proto, ActivityManagerServiceDumpServicesProto.ACTIVE_SERVICES); 16109 } else if ("processes".equals(cmd) || "p".equals(cmd)) { 16110 if (opti < args.length) { 16111 dumpPackage = args[opti]; 16112 opti++; 16113 } 16114 // output proto is ProcessProto 16115 synchronized (this) { 16116 writeProcessesToProtoLocked(proto, dumpPackage); 16117 } 16118 } else { 16119 // default option, dump everything, output is ActivityManagerServiceProto 16120 synchronized (this) { 16121 long activityToken = proto.start(ActivityManagerServiceProto.ACTIVITIES); 16122 writeActivitiesToProtoLocked(proto); 16123 proto.end(activityToken); 16124 16125 long broadcastToken = proto.start(ActivityManagerServiceProto.BROADCASTS); 16126 writeBroadcastsToProtoLocked(proto); 16127 proto.end(broadcastToken); 16128 16129 long serviceToken = proto.start(ActivityManagerServiceProto.SERVICES); 16130 mServices.writeToProto(proto, ActivityManagerServiceDumpServicesProto.ACTIVE_SERVICES); 16131 proto.end(serviceToken); 16132 16133 long processToken = proto.start(ActivityManagerServiceProto.PROCESSES); 16134 writeProcessesToProtoLocked(proto, dumpPackage); 16135 proto.end(processToken); 16136 } 16137 } 16138 proto.flush(); 16139 Binder.restoreCallingIdentity(origId); 16140 return; 16141 } 16142 16143 int dumpAppId = getAppId(dumpPackage); 16144 boolean more = false; 16145 // Is the caller requesting to dump a particular piece of data? 16146 if (opti < args.length) { 16147 String cmd = args[opti]; 16148 opti++; 16149 if ("activities".equals(cmd) || "a".equals(cmd)) { 16150 synchronized (this) { 16151 dumpActivitiesLocked(fd, pw, args, opti, true, dumpClient, dumpPackage); 16152 } 16153 } else if ("lastanr".equals(cmd)) { 16154 synchronized (this) { 16155 dumpLastANRLocked(pw); 16156 } 16157 } else if ("starter".equals(cmd)) { 16158 synchronized (this) { 16159 dumpActivityStarterLocked(pw, dumpPackage); 16160 } 16161 } else if ("containers".equals(cmd)) { 16162 synchronized (this) { 16163 dumpActivityContainersLocked(pw); 16164 } 16165 } else if ("recents".equals(cmd) || "r".equals(cmd)) { 16166 synchronized (this) { 16167 if (mRecentTasks != null) { 16168 mRecentTasks.dump(pw, true /* dumpAll */, dumpPackage); 16169 } 16170 } 16171 } else if ("binder-proxies".equals(cmd)) { 16172 if (opti >= args.length) { 16173 dumpBinderProxiesCounts(pw, BinderInternal.nGetBinderProxyPerUidCounts(), 16174 "Counts of Binder Proxies held by SYSTEM"); 16175 } else { 16176 String uid = args[opti]; 16177 opti++; 16178 // Ensure Binder Proxy Count is as up to date as possible 16179 System.gc(); 16180 System.runFinalization(); 16181 System.gc(); 16182 pw.println(BinderInternal.nGetBinderProxyCount(Integer.parseInt(uid))); 16183 } 16184 } else if ("broadcasts".equals(cmd) || "b".equals(cmd)) { 16185 if (opti < args.length) { 16186 dumpPackage = args[opti]; 16187 opti++; 16188 } 16189 synchronized (this) { 16190 dumpBroadcastsLocked(fd, pw, args, opti, true, dumpPackage); 16191 } 16192 } else if ("broadcast-stats".equals(cmd)) { 16193 if (opti < args.length) { 16194 dumpPackage = args[opti]; 16195 opti++; 16196 } 16197 synchronized (this) { 16198 if (dumpCheckinFormat) { 16199 dumpBroadcastStatsCheckinLocked(fd, pw, args, opti, dumpCheckin, 16200 dumpPackage); 16201 } else { 16202 dumpBroadcastStatsLocked(fd, pw, args, opti, true, dumpPackage); 16203 } 16204 } 16205 } else if ("intents".equals(cmd) || "i".equals(cmd)) { 16206 if (opti < args.length) { 16207 dumpPackage = args[opti]; 16208 opti++; 16209 } 16210 synchronized (this) { 16211 dumpPendingIntentsLocked(fd, pw, args, opti, true, dumpPackage); 16212 } 16213 } else if ("processes".equals(cmd) || "p".equals(cmd)) { 16214 if (opti < args.length) { 16215 dumpPackage = args[opti]; 16216 opti++; 16217 } 16218 synchronized (this) { 16219 dumpProcessesLocked(fd, pw, args, opti, true, dumpPackage, dumpAppId); 16220 } 16221 } else if ("oom".equals(cmd) || "o".equals(cmd)) { 16222 synchronized (this) { 16223 dumpOomLocked(fd, pw, args, opti, true); 16224 } 16225 } else if ("permissions".equals(cmd) || "perm".equals(cmd)) { 16226 synchronized (this) { 16227 dumpPermissionsLocked(fd, pw, args, opti, true, null); 16228 } 16229 } else if ("provider".equals(cmd)) { 16230 String[] newArgs; 16231 String name; 16232 if (opti >= args.length) { 16233 name = null; 16234 newArgs = EMPTY_STRING_ARRAY; 16235 } else { 16236 name = args[opti]; 16237 opti++; 16238 newArgs = new String[args.length - opti]; 16239 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, args.length - opti); 16240 } 16241 if (!dumpProvider(fd, pw, name, newArgs, 0, dumpAll)) { 16242 pw.println("No providers match: " + name); 16243 pw.println("Use -h for help."); 16244 } 16245 } else if ("providers".equals(cmd) || "prov".equals(cmd)) { 16246 synchronized (this) { 16247 dumpProvidersLocked(fd, pw, args, opti, true, null); 16248 } 16249 } else if ("service".equals(cmd)) { 16250 String[] newArgs; 16251 String name; 16252 if (opti >= args.length) { 16253 name = null; 16254 newArgs = EMPTY_STRING_ARRAY; 16255 } else { 16256 name = args[opti]; 16257 opti++; 16258 newArgs = new String[args.length - opti]; 16259 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 16260 args.length - opti); 16261 } 16262 if (!mServices.dumpService(fd, pw, name, newArgs, 0, dumpAll)) { 16263 pw.println("No services match: " + name); 16264 pw.println("Use -h for help."); 16265 } 16266 } else if ("package".equals(cmd)) { 16267 String[] newArgs; 16268 if (opti >= args.length) { 16269 pw.println("package: no package name specified"); 16270 pw.println("Use -h for help."); 16271 } else { 16272 dumpPackage = args[opti]; 16273 opti++; 16274 newArgs = new String[args.length - opti]; 16275 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 16276 args.length - opti); 16277 args = newArgs; 16278 opti = 0; 16279 more = true; 16280 } 16281 } else if ("associations".equals(cmd) || "as".equals(cmd)) { 16282 synchronized (this) { 16283 dumpAssociationsLocked(fd, pw, args, opti, true, dumpClient, dumpPackage); 16284 } 16285 } else if ("settings".equals(cmd)) { 16286 synchronized (this) { 16287 mConstants.dump(pw); 16288 } 16289 } else if ("services".equals(cmd) || "s".equals(cmd)) { 16290 if (dumpClient) { 16291 ActiveServices.ServiceDumper dumper; 16292 synchronized (this) { 16293 dumper = mServices.newServiceDumperLocked(fd, pw, args, opti, true, 16294 dumpPackage); 16295 } 16296 dumper.dumpWithClient(); 16297 } else { 16298 synchronized (this) { 16299 mServices.newServiceDumperLocked(fd, pw, args, opti, true, 16300 dumpPackage).dumpLocked(); 16301 } 16302 } 16303 } else if ("locks".equals(cmd)) { 16304 LockGuard.dump(fd, pw, args); 16305 } else { 16306 // Dumping a single activity? 16307 if (!dumpActivity(fd, pw, cmd, args, opti, dumpAll, dumpVisibleStacksOnly, 16308 dumpFocusedStackOnly)) { 16309 ActivityManagerShellCommand shell = new ActivityManagerShellCommand(this, true); 16310 int res = shell.exec(this, null, fd, null, args, null, 16311 new ResultReceiver(null)); 16312 if (res < 0) { 16313 pw.println("Bad activity command, or no activities match: " + cmd); 16314 pw.println("Use -h for help."); 16315 } 16316 } 16317 } 16318 if (!more) { 16319 Binder.restoreCallingIdentity(origId); 16320 return; 16321 } 16322 } 16323 16324 // No piece of data specified, dump everything. 16325 if (dumpCheckinFormat) { 16326 dumpBroadcastStatsCheckinLocked(fd, pw, args, opti, dumpCheckin, dumpPackage); 16327 } else if (dumpClient) { 16328 ActiveServices.ServiceDumper sdumper; 16329 synchronized (this) { 16330 mConstants.dump(pw); 16331 pw.println(); 16332 if (dumpAll) { 16333 pw.println("-------------------------------------------------------------------------------"); 16334 } 16335 dumpPendingIntentsLocked(fd, pw, args, opti, dumpAll, dumpPackage); 16336 pw.println(); 16337 if (dumpAll) { 16338 pw.println("-------------------------------------------------------------------------------"); 16339 } 16340 dumpBroadcastsLocked(fd, pw, args, opti, dumpAll, dumpPackage); 16341 pw.println(); 16342 if (dumpAll) { 16343 pw.println("-------------------------------------------------------------------------------"); 16344 } 16345 if (dumpAll || dumpPackage != null) { 16346 dumpBroadcastStatsLocked(fd, pw, args, opti, dumpAll, dumpPackage); 16347 pw.println(); 16348 if (dumpAll) { 16349 pw.println("-------------------------------------------------------------------------------"); 16350 } 16351 } 16352 dumpProvidersLocked(fd, pw, args, opti, dumpAll, dumpPackage); 16353 pw.println(); 16354 if (dumpAll) { 16355 pw.println("-------------------------------------------------------------------------------"); 16356 } 16357 dumpPermissionsLocked(fd, pw, args, opti, dumpAll, dumpPackage); 16358 pw.println(); 16359 if (dumpAll) { 16360 pw.println("-------------------------------------------------------------------------------"); 16361 } 16362 sdumper = mServices.newServiceDumperLocked(fd, pw, args, opti, dumpAll, 16363 dumpPackage); 16364 } 16365 sdumper.dumpWithClient(); 16366 pw.println(); 16367 synchronized (this) { 16368 if (dumpAll) { 16369 pw.println("-------------------------------------------------------------------------------"); 16370 } 16371 if (mRecentTasks != null) { 16372 mRecentTasks.dump(pw, dumpAll, dumpPackage); 16373 } 16374 pw.println(); 16375 if (dumpAll) { 16376 pw.println("-------------------------------------------------------------------------------"); 16377 } 16378 dumpLastANRLocked(pw); 16379 pw.println(); 16380 if (dumpAll) { 16381 pw.println("-------------------------------------------------------------------------------"); 16382 } 16383 dumpActivityStarterLocked(pw, dumpPackage); 16384 pw.println(); 16385 if (dumpAll) { 16386 pw.println("-------------------------------------------------------------------------------"); 16387 } 16388 dumpActivityContainersLocked(pw); 16389 pw.println(); 16390 if (dumpAll) { 16391 pw.println("-------------------------------------------------------------------------------"); 16392 } 16393 dumpActivitiesLocked(fd, pw, args, opti, dumpAll, dumpClient, dumpPackage); 16394 if (mAssociations.size() > 0) { 16395 pw.println(); 16396 if (dumpAll) { 16397 pw.println("-------------------------------------------------------------------------------"); 16398 } 16399 dumpAssociationsLocked(fd, pw, args, opti, dumpAll, dumpClient, dumpPackage); 16400 } 16401 pw.println(); 16402 if (dumpAll) { 16403 pw.println("-------------------------------------------------------------------------------"); 16404 } 16405 dumpProcessesLocked(fd, pw, args, opti, dumpAll, dumpPackage, dumpAppId); 16406 } 16407 16408 } else { 16409 synchronized (this) { 16410 mConstants.dump(pw); 16411 pw.println(); 16412 if (dumpAll) { 16413 pw.println("-------------------------------------------------------------------------------"); 16414 } 16415 dumpPendingIntentsLocked(fd, pw, args, opti, dumpAll, dumpPackage); 16416 pw.println(); 16417 if (dumpAll) { 16418 pw.println("-------------------------------------------------------------------------------"); 16419 } 16420 dumpBroadcastsLocked(fd, pw, args, opti, dumpAll, dumpPackage); 16421 pw.println(); 16422 if (dumpAll) { 16423 pw.println("-------------------------------------------------------------------------------"); 16424 } 16425 if (dumpAll || dumpPackage != null) { 16426 dumpBroadcastStatsLocked(fd, pw, args, opti, dumpAll, dumpPackage); 16427 pw.println(); 16428 if (dumpAll) { 16429 pw.println("-------------------------------------------------------------------------------"); 16430 } 16431 } 16432 dumpProvidersLocked(fd, pw, args, opti, dumpAll, dumpPackage); 16433 pw.println(); 16434 if (dumpAll) { 16435 pw.println("-------------------------------------------------------------------------------"); 16436 } 16437 dumpPermissionsLocked(fd, pw, args, opti, dumpAll, dumpPackage); 16438 pw.println(); 16439 if (dumpAll) { 16440 pw.println("-------------------------------------------------------------------------------"); 16441 } 16442 mServices.newServiceDumperLocked(fd, pw, args, opti, dumpAll, dumpPackage) 16443 .dumpLocked(); 16444 pw.println(); 16445 if (dumpAll) { 16446 pw.println("-------------------------------------------------------------------------------"); 16447 } 16448 if (mRecentTasks != null) { 16449 mRecentTasks.dump(pw, dumpAll, dumpPackage); 16450 } 16451 pw.println(); 16452 if (dumpAll) { 16453 pw.println("-------------------------------------------------------------------------------"); 16454 } 16455 dumpLastANRLocked(pw); 16456 pw.println(); 16457 if (dumpAll) { 16458 pw.println("-------------------------------------------------------------------------------"); 16459 } 16460 dumpActivityStarterLocked(pw, dumpPackage); 16461 pw.println(); 16462 if (dumpAll) { 16463 pw.println("-------------------------------------------------------------------------------"); 16464 } 16465 dumpActivityContainersLocked(pw); 16466 // Activities section is dumped as part of the Critical priority dump. Exclude the 16467 // section if priority is Normal. 16468 if (!dumpNormalPriority){ 16469 pw.println(); 16470 if (dumpAll) { 16471 pw.println("-------------------------------------------------------------------------------"); 16472 } 16473 dumpActivitiesLocked(fd, pw, args, opti, dumpAll, dumpClient, dumpPackage); 16474 } 16475 if (mAssociations.size() > 0) { 16476 pw.println(); 16477 if (dumpAll) { 16478 pw.println("-------------------------------------------------------------------------------"); 16479 } 16480 dumpAssociationsLocked(fd, pw, args, opti, dumpAll, dumpClient, dumpPackage); 16481 } 16482 pw.println(); 16483 if (dumpAll) { 16484 pw.println("-------------------------------------------------------------------------------"); 16485 } 16486 dumpProcessesLocked(fd, pw, args, opti, dumpAll, dumpPackage, dumpAppId); 16487 } 16488 } 16489 Binder.restoreCallingIdentity(origId); 16490 } 16491 16492 private void writeActivitiesToProtoLocked(ProtoOutputStream proto) { 16493 // The output proto of "activity --proto activities" is ActivityManagerServiceDumpActivitiesProto 16494 mStackSupervisor.writeToProto(proto, ActivityManagerServiceDumpActivitiesProto.ACTIVITY_STACK_SUPERVISOR); 16495 } 16496 16497 private void dumpLastANRLocked(PrintWriter pw) { 16498 pw.println("ACTIVITY MANAGER LAST ANR (dumpsys activity lastanr)"); 16499 if (mLastANRState == null) { 16500 pw.println(" <no ANR has occurred since boot>"); 16501 } else { 16502 pw.println(mLastANRState); 16503 } 16504 } 16505 16506 private void dumpActivityContainersLocked(PrintWriter pw) { 16507 pw.println("ACTIVITY MANAGER STARTER (dumpsys activity containers)"); 16508 mStackSupervisor.dumpChildrenNames(pw, " "); 16509 pw.println(" "); 16510 } 16511 16512 private void dumpActivityStarterLocked(PrintWriter pw, String dumpPackage) { 16513 pw.println("ACTIVITY MANAGER STARTER (dumpsys activity starter)"); 16514 mActivityStartController.dump(pw, "", dumpPackage); 16515 } 16516 16517 void dumpActivitiesLocked(FileDescriptor fd, PrintWriter pw, String[] args, 16518 int opti, boolean dumpAll, boolean dumpClient, String dumpPackage) { 16519 dumpActivitiesLocked(fd, pw, args, opti, dumpAll, dumpClient, dumpPackage, 16520 "ACTIVITY MANAGER ACTIVITIES (dumpsys activity activities)"); 16521 } 16522 16523 void dumpActivitiesLocked(FileDescriptor fd, PrintWriter pw, String[] args, 16524 int opti, boolean dumpAll, boolean dumpClient, String dumpPackage, String header) { 16525 pw.println(header); 16526 16527 boolean printedAnything = mStackSupervisor.dumpActivitiesLocked(fd, pw, dumpAll, dumpClient, 16528 dumpPackage); 16529 boolean needSep = printedAnything; 16530 16531 boolean printed = ActivityStackSupervisor.printThisActivity(pw, 16532 mStackSupervisor.getResumedActivityLocked(), 16533 dumpPackage, needSep, " ResumedActivity: "); 16534 if (printed) { 16535 printedAnything = true; 16536 needSep = false; 16537 } 16538 16539 if (dumpPackage == null) { 16540 if (needSep) { 16541 pw.println(); 16542 } 16543 printedAnything = true; 16544 mStackSupervisor.dump(pw, " "); 16545 } 16546 16547 if (!printedAnything) { 16548 pw.println(" (nothing)"); 16549 } 16550 } 16551 16552 void dumpAssociationsLocked(FileDescriptor fd, PrintWriter pw, String[] args, 16553 int opti, boolean dumpAll, boolean dumpClient, String dumpPackage) { 16554 pw.println("ACTIVITY MANAGER ASSOCIATIONS (dumpsys activity associations)"); 16555 16556 int dumpUid = 0; 16557 if (dumpPackage != null) { 16558 IPackageManager pm = AppGlobals.getPackageManager(); 16559 try { 16560 dumpUid = pm.getPackageUid(dumpPackage, MATCH_ANY_USER, 0); 16561 } catch (RemoteException e) { 16562 } 16563 } 16564 16565 boolean printedAnything = false; 16566 16567 final long now = SystemClock.uptimeMillis(); 16568 16569 for (int i1=0, N1=mAssociations.size(); i1<N1; i1++) { 16570 ArrayMap<ComponentName, SparseArray<ArrayMap<String, Association>>> targetComponents 16571 = mAssociations.valueAt(i1); 16572 for (int i2=0, N2=targetComponents.size(); i2<N2; i2++) { 16573 SparseArray<ArrayMap<String, Association>> sourceUids 16574 = targetComponents.valueAt(i2); 16575 for (int i3=0, N3=sourceUids.size(); i3<N3; i3++) { 16576 ArrayMap<String, Association> sourceProcesses = sourceUids.valueAt(i3); 16577 for (int i4=0, N4=sourceProcesses.size(); i4<N4; i4++) { 16578 Association ass = sourceProcesses.valueAt(i4); 16579 if (dumpPackage != null) { 16580 if (!ass.mTargetComponent.getPackageName().equals(dumpPackage) 16581 && UserHandle.getAppId(ass.mSourceUid) != dumpUid) { 16582 continue; 16583 } 16584 } 16585 printedAnything = true; 16586 pw.print(" "); 16587 pw.print(ass.mTargetProcess); 16588 pw.print("/"); 16589 UserHandle.formatUid(pw, ass.mTargetUid); 16590 pw.print(" <- "); 16591 pw.print(ass.mSourceProcess); 16592 pw.print("/"); 16593 UserHandle.formatUid(pw, ass.mSourceUid); 16594 pw.println(); 16595 pw.print(" via "); 16596 pw.print(ass.mTargetComponent.flattenToShortString()); 16597 pw.println(); 16598 pw.print(" "); 16599 long dur = ass.mTime; 16600 if (ass.mNesting > 0) { 16601 dur += now - ass.mStartTime; 16602 } 16603 TimeUtils.formatDuration(dur, pw); 16604 pw.print(" ("); 16605 pw.print(ass.mCount); 16606 pw.print(" times)"); 16607 pw.print(" "); 16608 for (int i=0; i<ass.mStateTimes.length; i++) { 16609 long amt = ass.mStateTimes[i]; 16610 if ((ass.mLastState-ActivityManager.MIN_PROCESS_STATE) == i) { 16611 amt += now - ass.mLastStateUptime; 16612 } 16613 if (amt != 0) { 16614 pw.print(" "); 16615 pw.print(ProcessList.makeProcStateString( 16616 i + ActivityManager.MIN_PROCESS_STATE)); 16617 pw.print("="); 16618 TimeUtils.formatDuration(amt, pw); 16619 if ((ass.mLastState-ActivityManager.MIN_PROCESS_STATE) == i) { 16620 pw.print("*"); 16621 } 16622 } 16623 } 16624 pw.println(); 16625 if (ass.mNesting > 0) { 16626 pw.print(" Currently active: "); 16627 TimeUtils.formatDuration(now - ass.mStartTime, pw); 16628 pw.println(); 16629 } 16630 } 16631 } 16632 } 16633 16634 } 16635 16636 if (!printedAnything) { 16637 pw.println(" (nothing)"); 16638 } 16639 } 16640 16641 private int getAppId(String dumpPackage) { 16642 if (dumpPackage != null) { 16643 try { 16644 ApplicationInfo info = mContext.getPackageManager().getApplicationInfo( 16645 dumpPackage, 0); 16646 return UserHandle.getAppId(info.uid); 16647 } catch (NameNotFoundException e) { 16648 e.printStackTrace(); 16649 } 16650 } 16651 return -1; 16652 } 16653 16654 boolean dumpUids(PrintWriter pw, String dumpPackage, int dumpAppId, SparseArray<UidRecord> uids, 16655 String header, boolean needSep) { 16656 boolean printed = false; 16657 for (int i=0; i<uids.size(); i++) { 16658 UidRecord uidRec = uids.valueAt(i); 16659 if (dumpPackage != null && UserHandle.getAppId(uidRec.uid) != dumpAppId) { 16660 continue; 16661 } 16662 if (!printed) { 16663 printed = true; 16664 if (needSep) { 16665 pw.println(); 16666 } 16667 pw.print(" "); 16668 pw.println(header); 16669 needSep = true; 16670 } 16671 pw.print(" UID "); UserHandle.formatUid(pw, uidRec.uid); 16672 pw.print(": "); pw.println(uidRec); 16673 } 16674 return printed; 16675 } 16676 16677 boolean dumpBinderProxiesCounts(PrintWriter pw, SparseIntArray counts, String header) { 16678 if(counts != null) { 16679 pw.println(header); 16680 for (int i = 0; i < counts.size(); i++) { 16681 final int uid = counts.keyAt(i); 16682 final int binderCount = counts.valueAt(i); 16683 pw.print(" UID "); 16684 pw.print(uid); 16685 pw.print(", binder count = "); 16686 pw.print(binderCount); 16687 pw.print(", package(s)= "); 16688 final String[] pkgNames = mContext.getPackageManager().getPackagesForUid(uid); 16689 if (pkgNames != null) { 16690 for (int j = 0; j < pkgNames.length; j++) { 16691 pw.print(pkgNames[j]); 16692 pw.print("; "); 16693 } 16694 } else { 16695 pw.print("NO PACKAGE NAME FOUND"); 16696 } 16697 pw.println(); 16698 } 16699 pw.println(); 16700 return true; 16701 } 16702 return false; 16703 } 16704 16705 @GuardedBy("this") 16706 void dumpProcessesLocked(FileDescriptor fd, PrintWriter pw, String[] args, 16707 int opti, boolean dumpAll, String dumpPackage, int dumpAppId) { 16708 boolean needSep = false; 16709 int numPers = 0; 16710 16711 pw.println("ACTIVITY MANAGER RUNNING PROCESSES (dumpsys activity processes)"); 16712 16713 if (dumpAll) { 16714 final int NP = mProcessNames.getMap().size(); 16715 for (int ip=0; ip<NP; ip++) { 16716 SparseArray<ProcessRecord> procs = mProcessNames.getMap().valueAt(ip); 16717 final int NA = procs.size(); 16718 for (int ia=0; ia<NA; ia++) { 16719 ProcessRecord r = procs.valueAt(ia); 16720 if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) { 16721 continue; 16722 } 16723 if (!needSep) { 16724 pw.println(" All known processes:"); 16725 needSep = true; 16726 } 16727 pw.print(r.persistent ? " *PERS*" : " *APP*"); 16728 pw.print(" UID "); pw.print(procs.keyAt(ia)); 16729 pw.print(" "); pw.println(r); 16730 r.dump(pw, " "); 16731 if (r.persistent) { 16732 numPers++; 16733 } 16734 } 16735 } 16736 } 16737 16738 if (mIsolatedProcesses.size() > 0) { 16739 boolean printed = false; 16740 for (int i=0; i<mIsolatedProcesses.size(); i++) { 16741 ProcessRecord r = mIsolatedProcesses.valueAt(i); 16742 if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) { 16743 continue; 16744 } 16745 if (!printed) { 16746 if (needSep) { 16747 pw.println(); 16748 } 16749 pw.println(" Isolated process list (sorted by uid):"); 16750 printed = true; 16751 needSep = true; 16752 } 16753 pw.print(" Isolated #"); pw.print(i); pw.print(": "); 16754 pw.println(r); 16755 } 16756 } 16757 16758 if (mActiveInstrumentation.size() > 0) { 16759 boolean printed = false; 16760 for (int i=0; i<mActiveInstrumentation.size(); i++) { 16761 ActiveInstrumentation ai = mActiveInstrumentation.get(i); 16762 if (dumpPackage != null && !ai.mClass.getPackageName().equals(dumpPackage) 16763 && !ai.mTargetInfo.packageName.equals(dumpPackage)) { 16764 continue; 16765 } 16766 if (!printed) { 16767 if (needSep) { 16768 pw.println(); 16769 } 16770 pw.println(" Active instrumentation:"); 16771 printed = true; 16772 needSep = true; 16773 } 16774 pw.print(" Instrumentation #"); pw.print(i); pw.print(": "); 16775 pw.println(ai); 16776 ai.dump(pw, " "); 16777 } 16778 } 16779 16780 if (mActiveUids.size() > 0) { 16781 if (dumpUids(pw, dumpPackage, dumpAppId, mActiveUids, "UID states:", needSep)) { 16782 needSep = true; 16783 } 16784 } 16785 if (dumpAll) { 16786 if (mValidateUids.size() > 0) { 16787 if (dumpUids(pw, dumpPackage, dumpAppId, mValidateUids, "UID validation:", 16788 needSep)) { 16789 needSep = true; 16790 } 16791 } 16792 } 16793 16794 if (mLruProcesses.size() > 0) { 16795 if (needSep) { 16796 pw.println(); 16797 } 16798 pw.print(" Process LRU list (sorted by oom_adj, "); pw.print(mLruProcesses.size()); 16799 pw.print(" total, non-act at "); 16800 pw.print(mLruProcesses.size()-mLruProcessActivityStart); 16801 pw.print(", non-svc at "); 16802 pw.print(mLruProcesses.size()-mLruProcessServiceStart); 16803 pw.println("):"); 16804 dumpProcessOomList(pw, this, mLruProcesses, " ", "Proc", "PERS", false, dumpPackage); 16805 needSep = true; 16806 } 16807 16808 if (dumpAll || dumpPackage != null) { 16809 synchronized (mPidsSelfLocked) { 16810 boolean printed = false; 16811 for (int i=0; i<mPidsSelfLocked.size(); i++) { 16812 ProcessRecord r = mPidsSelfLocked.valueAt(i); 16813 if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) { 16814 continue; 16815 } 16816 if (!printed) { 16817 if (needSep) pw.println(); 16818 needSep = true; 16819 pw.println(" PID mappings:"); 16820 printed = true; 16821 } 16822 pw.print(" PID #"); pw.print(mPidsSelfLocked.keyAt(i)); 16823 pw.print(": "); pw.println(mPidsSelfLocked.valueAt(i)); 16824 } 16825 } 16826 } 16827 16828 if (mImportantProcesses.size() > 0) { 16829 synchronized (mPidsSelfLocked) { 16830 boolean printed = false; 16831 for (int i = 0; i< mImportantProcesses.size(); i++) { 16832 ProcessRecord r = mPidsSelfLocked.get( 16833 mImportantProcesses.valueAt(i).pid); 16834 if (dumpPackage != null && (r == null 16835 || !r.pkgList.containsKey(dumpPackage))) { 16836 continue; 16837 } 16838 if (!printed) { 16839 if (needSep) pw.println(); 16840 needSep = true; 16841 pw.println(" Foreground Processes:"); 16842 printed = true; 16843 } 16844 pw.print(" PID #"); pw.print(mImportantProcesses.keyAt(i)); 16845 pw.print(": "); pw.println(mImportantProcesses.valueAt(i)); 16846 } 16847 } 16848 } 16849 16850 if (mPersistentStartingProcesses.size() > 0) { 16851 if (needSep) pw.println(); 16852 needSep = true; 16853 pw.println(" Persisent processes that are starting:"); 16854 dumpProcessList(pw, this, mPersistentStartingProcesses, " ", 16855 "Starting Norm", "Restarting PERS", dumpPackage); 16856 } 16857 16858 if (mRemovedProcesses.size() > 0) { 16859 if (needSep) pw.println(); 16860 needSep = true; 16861 pw.println(" Processes that are being removed:"); 16862 dumpProcessList(pw, this, mRemovedProcesses, " ", 16863 "Removed Norm", "Removed PERS", dumpPackage); 16864 } 16865 16866 if (mProcessesOnHold.size() > 0) { 16867 if (needSep) pw.println(); 16868 needSep = true; 16869 pw.println(" Processes that are on old until the system is ready:"); 16870 dumpProcessList(pw, this, mProcessesOnHold, " ", 16871 "OnHold Norm", "OnHold PERS", dumpPackage); 16872 } 16873 16874 needSep = dumpProcessesToGc(pw, needSep, dumpPackage); 16875 16876 needSep = mAppErrors.dumpLocked(fd, pw, needSep, dumpPackage); 16877 16878 if (dumpPackage == null) { 16879 pw.println(); 16880 needSep = false; 16881 mUserController.dump(pw, dumpAll); 16882 } 16883 if (mHomeProcess != null && (dumpPackage == null 16884 || mHomeProcess.pkgList.containsKey(dumpPackage))) { 16885 if (needSep) { 16886 pw.println(); 16887 needSep = false; 16888 } 16889 pw.println(" mHomeProcess: " + mHomeProcess); 16890 } 16891 if (mPreviousProcess != null && (dumpPackage == null 16892 || mPreviousProcess.pkgList.containsKey(dumpPackage))) { 16893 if (needSep) { 16894 pw.println(); 16895 needSep = false; 16896 } 16897 pw.println(" mPreviousProcess: " + mPreviousProcess); 16898 } 16899 if (dumpAll && (mPreviousProcess == null || dumpPackage == null 16900 || mPreviousProcess.pkgList.containsKey(dumpPackage))) { 16901 StringBuilder sb = new StringBuilder(128); 16902 sb.append(" mPreviousProcessVisibleTime: "); 16903 TimeUtils.formatDuration(mPreviousProcessVisibleTime, sb); 16904 pw.println(sb); 16905 } 16906 if (mHeavyWeightProcess != null && (dumpPackage == null 16907 || mHeavyWeightProcess.pkgList.containsKey(dumpPackage))) { 16908 if (needSep) { 16909 pw.println(); 16910 needSep = false; 16911 } 16912 pw.println(" mHeavyWeightProcess: " + mHeavyWeightProcess); 16913 } 16914 if (dumpAll && mPendingStarts.size() > 0) { 16915 if (needSep) pw.println(); 16916 needSep = true; 16917 pw.println(" mPendingStarts: "); 16918 for (int i = 0, len = mPendingStarts.size(); i < len; ++i ) { 16919 pw.println(" " + mPendingStarts.keyAt(i) + ": " + mPendingStarts.valueAt(i)); 16920 } 16921 } 16922 if (dumpPackage == null) { 16923 pw.println(" mGlobalConfiguration: " + getGlobalConfiguration()); 16924 mStackSupervisor.dumpDisplayConfigs(pw, " "); 16925 } 16926 if (dumpAll) { 16927 if (dumpPackage == null) { 16928 pw.println(" mConfigWillChange: " + getFocusedStack().mConfigWillChange); 16929 } 16930 if (mCompatModePackages.getPackages().size() > 0) { 16931 boolean printed = false; 16932 for (Map.Entry<String, Integer> entry 16933 : mCompatModePackages.getPackages().entrySet()) { 16934 String pkg = entry.getKey(); 16935 int mode = entry.getValue(); 16936 if (dumpPackage != null && !dumpPackage.equals(pkg)) { 16937 continue; 16938 } 16939 if (!printed) { 16940 pw.println(" mScreenCompatPackages:"); 16941 printed = true; 16942 } 16943 pw.print(" "); pw.print(pkg); pw.print(": "); 16944 pw.print(mode); pw.println(); 16945 } 16946 } 16947 final int NI = mUidObservers.getRegisteredCallbackCount(); 16948 boolean printed = false; 16949 for (int i=0; i<NI; i++) { 16950 final UidObserverRegistration reg = (UidObserverRegistration) 16951 mUidObservers.getRegisteredCallbackCookie(i); 16952 if (dumpPackage == null || dumpPackage.equals(reg.pkg)) { 16953 if (!printed) { 16954 pw.println(" mUidObservers:"); 16955 printed = true; 16956 } 16957 pw.print(" "); UserHandle.formatUid(pw, reg.uid); 16958 pw.print(" "); pw.print(reg.pkg); pw.print(":"); 16959 if ((reg.which&ActivityManager.UID_OBSERVER_IDLE) != 0) { 16960 pw.print(" IDLE"); 16961 } 16962 if ((reg.which&ActivityManager.UID_OBSERVER_ACTIVE) != 0) { 16963 pw.print(" ACT" ); 16964 } 16965 if ((reg.which&ActivityManager.UID_OBSERVER_GONE) != 0) { 16966 pw.print(" GONE"); 16967 } 16968 if ((reg.which&ActivityManager.UID_OBSERVER_PROCSTATE) != 0) { 16969 pw.print(" STATE"); 16970 pw.print(" (cut="); pw.print(reg.cutpoint); 16971 pw.print(")"); 16972 } 16973 pw.println(); 16974 if (reg.lastProcStates != null) { 16975 final int NJ = reg.lastProcStates.size(); 16976 for (int j=0; j<NJ; j++) { 16977 pw.print(" Last "); 16978 UserHandle.formatUid(pw, reg.lastProcStates.keyAt(j)); 16979 pw.print(": "); pw.println(reg.lastProcStates.valueAt(j)); 16980 } 16981 } 16982 } 16983 } 16984 pw.println(" mDeviceIdleWhitelist=" + Arrays.toString(mDeviceIdleWhitelist)); 16985 pw.println(" mDeviceIdleExceptIdleWhitelist=" 16986 + Arrays.toString(mDeviceIdleExceptIdleWhitelist)); 16987 pw.println(" mDeviceIdleTempWhitelist=" + Arrays.toString(mDeviceIdleTempWhitelist)); 16988 if (mPendingTempWhitelist.size() > 0) { 16989 pw.println(" mPendingTempWhitelist:"); 16990 for (int i = 0; i < mPendingTempWhitelist.size(); i++) { 16991 PendingTempWhitelist ptw = mPendingTempWhitelist.valueAt(i); 16992 pw.print(" "); 16993 UserHandle.formatUid(pw, ptw.targetUid); 16994 pw.print(": "); 16995 TimeUtils.formatDuration(ptw.duration, pw); 16996 pw.print(" "); 16997 pw.println(ptw.tag); 16998 } 16999 } 17000 } 17001 if (dumpPackage == null) { 17002 pw.println(" mWakefulness=" 17003 + PowerManagerInternal.wakefulnessToString(mWakefulness)); 17004 pw.println(" mSleepTokens=" + mStackSupervisor.mSleepTokens); 17005 pw.println(" mSleeping=" + mSleeping); 17006 pw.println(" mShuttingDown=" + mShuttingDown + " mTestPssMode=" + mTestPssMode); 17007 if (mRunningVoice != null) { 17008 pw.println(" mRunningVoice=" + mRunningVoice); 17009 pw.println(" mVoiceWakeLock" + mVoiceWakeLock); 17010 } 17011 pw.println(" mVrController=" + mVrController); 17012 } 17013 if (mDebugApp != null || mOrigDebugApp != null || mDebugTransient 17014 || mOrigWaitForDebugger) { 17015 if (dumpPackage == null || dumpPackage.equals(mDebugApp) 17016 || dumpPackage.equals(mOrigDebugApp)) { 17017 if (needSep) { 17018 pw.println(); 17019 needSep = false; 17020 } 17021 pw.println(" mDebugApp=" + mDebugApp + "/orig=" + mOrigDebugApp 17022 + " mDebugTransient=" + mDebugTransient 17023 + " mOrigWaitForDebugger=" + mOrigWaitForDebugger); 17024 } 17025 } 17026 if (mCurAppTimeTracker != null) { 17027 mCurAppTimeTracker.dumpWithHeader(pw, " ", true); 17028 } 17029 if (mMemWatchProcesses.getMap().size() > 0) { 17030 pw.println(" Mem watch processes:"); 17031 final ArrayMap<String, SparseArray<Pair<Long, String>>> procs 17032 = mMemWatchProcesses.getMap(); 17033 for (int i=0; i<procs.size(); i++) { 17034 final String proc = procs.keyAt(i); 17035 final SparseArray<Pair<Long, String>> uids = procs.valueAt(i); 17036 for (int j=0; j<uids.size(); j++) { 17037 if (needSep) { 17038 pw.println(); 17039 needSep = false; 17040 } 17041 StringBuilder sb = new StringBuilder(); 17042 sb.append(" ").append(proc).append('/'); 17043 UserHandle.formatUid(sb, uids.keyAt(j)); 17044 Pair<Long, String> val = uids.valueAt(j); 17045 sb.append(": "); DebugUtils.sizeValueToString(val.first, sb); 17046 if (val.second != null) { 17047 sb.append(", report to ").append(val.second); 17048 } 17049 pw.println(sb.toString()); 17050 } 17051 } 17052 pw.print(" mMemWatchDumpProcName="); pw.println(mMemWatchDumpProcName); 17053 pw.print(" mMemWatchDumpFile="); pw.println(mMemWatchDumpFile); 17054 pw.print(" mMemWatchDumpPid="); pw.print(mMemWatchDumpPid); 17055 pw.print(" mMemWatchDumpUid="); pw.println(mMemWatchDumpUid); 17056 } 17057 if (mTrackAllocationApp != null) { 17058 if (dumpPackage == null || dumpPackage.equals(mTrackAllocationApp)) { 17059 if (needSep) { 17060 pw.println(); 17061 needSep = false; 17062 } 17063 pw.println(" mTrackAllocationApp=" + mTrackAllocationApp); 17064 } 17065 } 17066 if (mProfileApp != null || mProfileProc != null || (mProfilerInfo != null && 17067 (mProfilerInfo.profileFile != null || mProfilerInfo.profileFd != null))) { 17068 if (dumpPackage == null || dumpPackage.equals(mProfileApp)) { 17069 if (needSep) { 17070 pw.println(); 17071 needSep = false; 17072 } 17073 pw.println(" mProfileApp=" + mProfileApp + " mProfileProc=" + mProfileProc); 17074 if (mProfilerInfo != null) { 17075 pw.println(" mProfileFile=" + mProfilerInfo.profileFile + " mProfileFd=" + 17076 mProfilerInfo.profileFd); 17077 pw.println(" mSamplingInterval=" + mProfilerInfo.samplingInterval + 17078 " mAutoStopProfiler=" + mProfilerInfo.autoStopProfiler + 17079 " mStreamingOutput=" + mProfilerInfo.streamingOutput); 17080 pw.println(" mProfileType=" + mProfileType); 17081 } 17082 } 17083 } 17084 if (mNativeDebuggingApp != null) { 17085 if (dumpPackage == null || dumpPackage.equals(mNativeDebuggingApp)) { 17086 if (needSep) { 17087 pw.println(); 17088 needSep = false; 17089 } 17090 pw.println(" mNativeDebuggingApp=" + mNativeDebuggingApp); 17091 } 17092 } 17093 if (mAllowAppSwitchUids.size() > 0) { 17094 boolean printed = false; 17095 for (int i = 0; i < mAllowAppSwitchUids.size(); i++) { 17096 ArrayMap<String, Integer> types = mAllowAppSwitchUids.valueAt(i); 17097 for (int j = 0; j < types.size(); j++) { 17098 if (dumpPackage == null || 17099 UserHandle.getAppId(types.valueAt(j).intValue()) == dumpAppId) { 17100 if (needSep) { 17101 pw.println(); 17102 needSep = false; 17103 } 17104 if (!printed) { 17105 pw.println(" mAllowAppSwitchUids:"); 17106 printed = true; 17107 } 17108 pw.print(" User "); 17109 pw.print(mAllowAppSwitchUids.keyAt(i)); 17110 pw.print(": Type "); 17111 pw.print(types.keyAt(j)); 17112 pw.print(" = "); 17113 UserHandle.formatUid(pw, types.valueAt(j).intValue()); 17114 pw.println(); 17115 } 17116 } 17117 } 17118 } 17119 if (dumpPackage == null) { 17120 if (mAlwaysFinishActivities) { 17121 pw.println(" mAlwaysFinishActivities=" + mAlwaysFinishActivities); 17122 } 17123 if (mController != null) { 17124 pw.println(" mController=" + mController 17125 + " mControllerIsAMonkey=" + mControllerIsAMonkey); 17126 } 17127 if (dumpAll) { 17128 pw.println(" Total persistent processes: " + numPers); 17129 pw.println(" mProcessesReady=" + mProcessesReady 17130 + " mSystemReady=" + mSystemReady 17131 + " mBooted=" + mBooted 17132 + " mFactoryTest=" + mFactoryTest); 17133 pw.println(" mBooting=" + mBooting 17134 + " mCallFinishBooting=" + mCallFinishBooting 17135 + " mBootAnimationComplete=" + mBootAnimationComplete); 17136 pw.print(" mLastPowerCheckUptime="); 17137 TimeUtils.formatDuration(mLastPowerCheckUptime, pw); 17138 pw.println(""); 17139 pw.println(" mGoingToSleep=" + mStackSupervisor.mGoingToSleep); 17140 pw.println(" mLaunchingActivity=" + mStackSupervisor.mLaunchingActivity); 17141 pw.println(" mAdjSeq=" + mAdjSeq + " mLruSeq=" + mLruSeq); 17142 pw.println(" mNumNonCachedProcs=" + mNumNonCachedProcs 17143 + " (" + mLruProcesses.size() + " total)" 17144 + " mNumCachedHiddenProcs=" + mNumCachedHiddenProcs 17145 + " mNumServiceProcs=" + mNumServiceProcs 17146 + " mNewNumServiceProcs=" + mNewNumServiceProcs); 17147 pw.println(" mAllowLowerMemLevel=" + mAllowLowerMemLevel 17148 + " mLastMemoryLevel=" + mLastMemoryLevel 17149 + " mLastNumProcesses=" + mLastNumProcesses); 17150 long now = SystemClock.uptimeMillis(); 17151 pw.print(" mLastIdleTime="); 17152 TimeUtils.formatDuration(now, mLastIdleTime, pw); 17153 pw.print(" mLowRamSinceLastIdle="); 17154 TimeUtils.formatDuration(getLowRamTimeSinceIdle(now), pw); 17155 pw.println(); 17156 pw.println(); 17157 pw.print(" mUidChangeDispatchCount="); 17158 pw.print(mUidChangeDispatchCount); 17159 pw.println(); 17160 17161 pw.println(" Slow UID dispatches:"); 17162 final int N = mUidObservers.beginBroadcast(); 17163 for (int i = 0; i < N; i++) { 17164 UidObserverRegistration r = 17165 (UidObserverRegistration) mUidObservers.getBroadcastCookie(i); 17166 pw.print(" "); 17167 pw.print(mUidObservers.getBroadcastItem(i).getClass().getTypeName()); 17168 pw.print(": "); 17169 pw.print(r.mSlowDispatchCount); 17170 pw.print(" / Max "); 17171 pw.print(r.mMaxDispatchTime); 17172 pw.println("ms"); 17173 } 17174 mUidObservers.finishBroadcast(); 17175 17176 pw.println(); 17177 pw.println(" ServiceManager statistics:"); 17178 ServiceManager.sStatLogger.dump(pw, " "); 17179 pw.println(); 17180 } 17181 } 17182 pw.println(" mForceBackgroundCheck=" + mForceBackgroundCheck); 17183 } 17184 17185 @GuardedBy("this") 17186 void writeProcessesToProtoLocked(ProtoOutputStream proto, String dumpPackage) { 17187 int numPers = 0; 17188 17189 final int NP = mProcessNames.getMap().size(); 17190 for (int ip=0; ip<NP; ip++) { 17191 SparseArray<ProcessRecord> procs = mProcessNames.getMap().valueAt(ip); 17192 final int NA = procs.size(); 17193 for (int ia = 0; ia<NA; ia++) { 17194 ProcessRecord r = procs.valueAt(ia); 17195 if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) { 17196 continue; 17197 } 17198 r.writeToProto(proto, ActivityManagerServiceDumpProcessesProto.PROCS); 17199 if (r.persistent) { 17200 numPers++; 17201 } 17202 } 17203 } 17204 17205 for (int i=0; i<mIsolatedProcesses.size(); i++) { 17206 ProcessRecord r = mIsolatedProcesses.valueAt(i); 17207 if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) { 17208 continue; 17209 } 17210 r.writeToProto(proto, ActivityManagerServiceDumpProcessesProto.ISOLATED_PROCS); 17211 } 17212 17213 for (int i=0; i<mActiveInstrumentation.size(); i++) { 17214 ActiveInstrumentation ai = mActiveInstrumentation.get(i); 17215 if (dumpPackage != null && !ai.mClass.getPackageName().equals(dumpPackage) 17216 && !ai.mTargetInfo.packageName.equals(dumpPackage)) { 17217 continue; 17218 } 17219 ai.writeToProto(proto, ActivityManagerServiceDumpProcessesProto.ACTIVE_INSTRUMENTATIONS); 17220 } 17221 17222 int whichAppId = getAppId(dumpPackage); 17223 for (int i=0; i<mActiveUids.size(); i++) { 17224 UidRecord uidRec = mActiveUids.valueAt(i); 17225 if (dumpPackage != null && UserHandle.getAppId(uidRec.uid) != whichAppId) { 17226 continue; 17227 } 17228 uidRec.writeToProto(proto, ActivityManagerServiceDumpProcessesProto.ACTIVE_UIDS); 17229 } 17230 17231 for (int i=0; i<mValidateUids.size(); i++) { 17232 UidRecord uidRec = mValidateUids.valueAt(i); 17233 if (dumpPackage != null && UserHandle.getAppId(uidRec.uid) != whichAppId) { 17234 continue; 17235 } 17236 uidRec.writeToProto(proto, ActivityManagerServiceDumpProcessesProto.VALIDATE_UIDS); 17237 } 17238 17239 if (mLruProcesses.size() > 0) { 17240 long lruToken = proto.start(ActivityManagerServiceDumpProcessesProto.LRU_PROCS); 17241 int total = mLruProcesses.size(); 17242 proto.write(ActivityManagerServiceDumpProcessesProto.LruProcesses.SIZE, total); 17243 proto.write(ActivityManagerServiceDumpProcessesProto.LruProcesses.NON_ACT_AT, total-mLruProcessActivityStart); 17244 proto.write(ActivityManagerServiceDumpProcessesProto.LruProcesses.NON_SVC_AT, total-mLruProcessServiceStart); 17245 writeProcessOomListToProto(proto, ActivityManagerServiceDumpProcessesProto.LruProcesses.LIST, this, 17246 mLruProcesses,false, dumpPackage); 17247 proto.end(lruToken); 17248 } 17249 17250 if (dumpPackage != null) { 17251 synchronized (mPidsSelfLocked) { 17252 for (int i=0; i<mPidsSelfLocked.size(); i++) { 17253 ProcessRecord r = mPidsSelfLocked.valueAt(i); 17254 if (!r.pkgList.containsKey(dumpPackage)) { 17255 continue; 17256 } 17257 r.writeToProto(proto, ActivityManagerServiceDumpProcessesProto.PIDS_SELF_LOCKED); 17258 } 17259 } 17260 } 17261 17262 if (mImportantProcesses.size() > 0) { 17263 synchronized (mPidsSelfLocked) { 17264 for (int i=0; i<mImportantProcesses.size(); i++) { 17265 ImportanceToken it = mImportantProcesses.valueAt(i); 17266 ProcessRecord r = mPidsSelfLocked.get(it.pid); 17267 if (dumpPackage != null && (r == null 17268 || !r.pkgList.containsKey(dumpPackage))) { 17269 continue; 17270 } 17271 it.writeToProto(proto, ActivityManagerServiceDumpProcessesProto.IMPORTANT_PROCS); 17272 } 17273 } 17274 } 17275 17276 for (int i=0; i<mPersistentStartingProcesses.size(); i++) { 17277 ProcessRecord r = mPersistentStartingProcesses.get(i); 17278 if (dumpPackage != null && !dumpPackage.equals(r.info.packageName)) { 17279 continue; 17280 } 17281 r.writeToProto(proto, ActivityManagerServiceDumpProcessesProto.PERSISTENT_STARTING_PROCS); 17282 } 17283 17284 for (int i=0; i<mRemovedProcesses.size(); i++) { 17285 ProcessRecord r = mRemovedProcesses.get(i); 17286 if (dumpPackage != null && !dumpPackage.equals(r.info.packageName)) { 17287 continue; 17288 } 17289 r.writeToProto(proto, ActivityManagerServiceDumpProcessesProto.REMOVED_PROCS); 17290 } 17291 17292 for (int i=0; i<mProcessesOnHold.size(); i++) { 17293 ProcessRecord r = mProcessesOnHold.get(i); 17294 if (dumpPackage != null && !dumpPackage.equals(r.info.packageName)) { 17295 continue; 17296 } 17297 r.writeToProto(proto, ActivityManagerServiceDumpProcessesProto.ON_HOLD_PROCS); 17298 } 17299 17300 writeProcessesToGcToProto(proto, ActivityManagerServiceDumpProcessesProto.GC_PROCS, dumpPackage); 17301 mAppErrors.writeToProto(proto, ActivityManagerServiceDumpProcessesProto.APP_ERRORS, dumpPackage); 17302 17303 if (dumpPackage == null) { 17304 mUserController.writeToProto(proto, ActivityManagerServiceDumpProcessesProto.USER_CONTROLLER); 17305 getGlobalConfiguration().writeToProto(proto, ActivityManagerServiceDumpProcessesProto.GLOBAL_CONFIGURATION); 17306 proto.write(ActivityManagerServiceDumpProcessesProto.CONFIG_WILL_CHANGE, getFocusedStack().mConfigWillChange); 17307 } 17308 17309 if (mHomeProcess != null && (dumpPackage == null 17310 || mHomeProcess.pkgList.containsKey(dumpPackage))) { 17311 mHomeProcess.writeToProto(proto, ActivityManagerServiceDumpProcessesProto.HOME_PROC); 17312 } 17313 17314 if (mPreviousProcess != null && (dumpPackage == null 17315 || mPreviousProcess.pkgList.containsKey(dumpPackage))) { 17316 mPreviousProcess.writeToProto(proto, ActivityManagerServiceDumpProcessesProto.PREVIOUS_PROC); 17317 proto.write(ActivityManagerServiceDumpProcessesProto.PREVIOUS_PROC_VISIBLE_TIME_MS, mPreviousProcessVisibleTime); 17318 } 17319 17320 if (mHeavyWeightProcess != null && (dumpPackage == null 17321 || mHeavyWeightProcess.pkgList.containsKey(dumpPackage))) { 17322 mHeavyWeightProcess.writeToProto(proto, ActivityManagerServiceDumpProcessesProto.HEAVY_WEIGHT_PROC); 17323 } 17324 17325 for (Map.Entry<String, Integer> entry : mCompatModePackages.getPackages().entrySet()) { 17326 String pkg = entry.getKey(); 17327 int mode = entry.getValue(); 17328 if (dumpPackage == null || dumpPackage.equals(pkg)) { 17329 long compatToken = proto.start(ActivityManagerServiceDumpProcessesProto.SCREEN_COMPAT_PACKAGES); 17330 proto.write(ActivityManagerServiceDumpProcessesProto.ScreenCompatPackage.PACKAGE, pkg); 17331 proto.write(ActivityManagerServiceDumpProcessesProto.ScreenCompatPackage.MODE, mode); 17332 proto.end(compatToken); 17333 } 17334 } 17335 17336 final int NI = mUidObservers.getRegisteredCallbackCount(); 17337 for (int i=0; i<NI; i++) { 17338 final UidObserverRegistration reg = (UidObserverRegistration) 17339 mUidObservers.getRegisteredCallbackCookie(i); 17340 if (dumpPackage == null || dumpPackage.equals(reg.pkg)) { 17341 reg.writeToProto(proto, ActivityManagerServiceDumpProcessesProto.UID_OBSERVERS); 17342 } 17343 } 17344 17345 for (int v : mDeviceIdleWhitelist) { 17346 proto.write(ActivityManagerServiceDumpProcessesProto.DEVICE_IDLE_WHITELIST, v); 17347 } 17348 17349 for (int v : mDeviceIdleTempWhitelist) { 17350 proto.write(ActivityManagerServiceDumpProcessesProto.DEVICE_IDLE_TEMP_WHITELIST, v); 17351 } 17352 17353 if (mPendingTempWhitelist.size() > 0) { 17354 for (int i=0; i < mPendingTempWhitelist.size(); i++) { 17355 mPendingTempWhitelist.valueAt(i).writeToProto(proto, 17356 ActivityManagerServiceDumpProcessesProto.PENDING_TEMP_WHITELIST); 17357 } 17358 } 17359 17360 if (dumpPackage == null) { 17361 final long sleepToken = proto.start(ActivityManagerServiceDumpProcessesProto.SLEEP_STATUS); 17362 proto.write(ActivityManagerServiceDumpProcessesProto.SleepStatus.WAKEFULNESS, 17363 PowerManagerInternal.wakefulnessToProtoEnum(mWakefulness)); 17364 for (SleepToken st : mStackSupervisor.mSleepTokens) { 17365 proto.write(ActivityManagerServiceDumpProcessesProto.SleepStatus.SLEEP_TOKENS, st.toString()); 17366 } 17367 proto.write(ActivityManagerServiceDumpProcessesProto.SleepStatus.SLEEPING, mSleeping); 17368 proto.write(ActivityManagerServiceDumpProcessesProto.SleepStatus.SHUTTING_DOWN, mShuttingDown); 17369 proto.write(ActivityManagerServiceDumpProcessesProto.SleepStatus.TEST_PSS_MODE, mTestPssMode); 17370 proto.end(sleepToken); 17371 17372 if (mRunningVoice != null) { 17373 final long vrToken = proto.start(ActivityManagerServiceDumpProcessesProto.RUNNING_VOICE); 17374 proto.write(ActivityManagerServiceDumpProcessesProto.Voice.SESSION, mRunningVoice.toString()); 17375 mVoiceWakeLock.writeToProto(proto, ActivityManagerServiceDumpProcessesProto.Voice.WAKELOCK); 17376 proto.end(vrToken); 17377 } 17378 17379 mVrController.writeToProto(proto, ActivityManagerServiceDumpProcessesProto.VR_CONTROLLER); 17380 } 17381 17382 if (mDebugApp != null || mOrigDebugApp != null || mDebugTransient 17383 || mOrigWaitForDebugger) { 17384 if (dumpPackage == null || dumpPackage.equals(mDebugApp) 17385 || dumpPackage.equals(mOrigDebugApp)) { 17386 final long debugAppToken = proto.start(ActivityManagerServiceDumpProcessesProto.DEBUG); 17387 proto.write(ActivityManagerServiceDumpProcessesProto.DebugApp.DEBUG_APP, mDebugApp); 17388 proto.write(ActivityManagerServiceDumpProcessesProto.DebugApp.ORIG_DEBUG_APP, mOrigDebugApp); 17389 proto.write(ActivityManagerServiceDumpProcessesProto.DebugApp.DEBUG_TRANSIENT, mDebugTransient); 17390 proto.write(ActivityManagerServiceDumpProcessesProto.DebugApp.ORIG_WAIT_FOR_DEBUGGER, mOrigWaitForDebugger); 17391 proto.end(debugAppToken); 17392 } 17393 } 17394 17395 if (mCurAppTimeTracker != null) { 17396 mCurAppTimeTracker.writeToProto(proto, ActivityManagerServiceDumpProcessesProto.CURRENT_TRACKER, true); 17397 } 17398 17399 if (mMemWatchProcesses.getMap().size() > 0) { 17400 final long token = proto.start(ActivityManagerServiceDumpProcessesProto.MEM_WATCH_PROCESSES); 17401 ArrayMap<String, SparseArray<Pair<Long, String>>> procs = mMemWatchProcesses.getMap(); 17402 for (int i=0; i<procs.size(); i++) { 17403 final String proc = procs.keyAt(i); 17404 final SparseArray<Pair<Long, String>> uids = procs.valueAt(i); 17405 final long ptoken = proto.start(ActivityManagerServiceDumpProcessesProto.MemWatchProcess.PROCS); 17406 proto.write(ActivityManagerServiceDumpProcessesProto.MemWatchProcess.Process.NAME, proc); 17407 for (int j=0; j<uids.size(); j++) { 17408 final long utoken = proto.start(ActivityManagerServiceDumpProcessesProto.MemWatchProcess.Process.MEM_STATS); 17409 Pair<Long, String> val = uids.valueAt(j); 17410 proto.write(ActivityManagerServiceDumpProcessesProto.MemWatchProcess.Process.MemStats.UID, uids.keyAt(j)); 17411 proto.write(ActivityManagerServiceDumpProcessesProto.MemWatchProcess.Process.MemStats.SIZE, 17412 DebugUtils.sizeValueToString(val.first, new StringBuilder())); 17413 proto.write(ActivityManagerServiceDumpProcessesProto.MemWatchProcess.Process.MemStats.REPORT_TO, val.second); 17414 proto.end(utoken); 17415 } 17416 proto.end(ptoken); 17417 } 17418 17419 final long dtoken = proto.start(ActivityManagerServiceDumpProcessesProto.MemWatchProcess.DUMP); 17420 proto.write(ActivityManagerServiceDumpProcessesProto.MemWatchProcess.Dump.PROC_NAME, mMemWatchDumpProcName); 17421 proto.write(ActivityManagerServiceDumpProcessesProto.MemWatchProcess.Dump.FILE, mMemWatchDumpFile); 17422 proto.write(ActivityManagerServiceDumpProcessesProto.MemWatchProcess.Dump.PID, mMemWatchDumpPid); 17423 proto.write(ActivityManagerServiceDumpProcessesProto.MemWatchProcess.Dump.UID, mMemWatchDumpUid); 17424 proto.end(dtoken); 17425 17426 proto.end(token); 17427 } 17428 17429 if (mTrackAllocationApp != null) { 17430 if (dumpPackage == null || dumpPackage.equals(mTrackAllocationApp)) { 17431 proto.write(ActivityManagerServiceDumpProcessesProto.TRACK_ALLOCATION_APP, mTrackAllocationApp); 17432 } 17433 } 17434 17435 if (mProfileApp != null || mProfileProc != null || (mProfilerInfo != null && 17436 (mProfilerInfo.profileFile != null || mProfilerInfo.profileFd != null))) { 17437 if (dumpPackage == null || dumpPackage.equals(mProfileApp)) { 17438 final long token = proto.start(ActivityManagerServiceDumpProcessesProto.PROFILE); 17439 proto.write(ActivityManagerServiceDumpProcessesProto.Profile.APP_NAME, mProfileApp); 17440 mProfileProc.writeToProto(proto,ActivityManagerServiceDumpProcessesProto.Profile.PROC); 17441 if (mProfilerInfo != null) { 17442 mProfilerInfo.writeToProto(proto, ActivityManagerServiceDumpProcessesProto.Profile.INFO); 17443 proto.write(ActivityManagerServiceDumpProcessesProto.Profile.TYPE, mProfileType); 17444 } 17445 proto.end(token); 17446 } 17447 } 17448 17449 if (dumpPackage == null || dumpPackage.equals(mNativeDebuggingApp)) { 17450 proto.write(ActivityManagerServiceDumpProcessesProto.NATIVE_DEBUGGING_APP, mNativeDebuggingApp); 17451 } 17452 17453 if (dumpPackage == null) { 17454 proto.write(ActivityManagerServiceDumpProcessesProto.ALWAYS_FINISH_ACTIVITIES, mAlwaysFinishActivities); 17455 if (mController != null) { 17456 final long token = proto.start(ActivityManagerServiceDumpProcessesProto.CONTROLLER); 17457 proto.write(ActivityManagerServiceDumpProcessesProto.Controller.CONTROLLER, mController.toString()); 17458 proto.write(ActivityManagerServiceDumpProcessesProto.Controller.IS_A_MONKEY, mControllerIsAMonkey); 17459 proto.end(token); 17460 } 17461 proto.write(ActivityManagerServiceDumpProcessesProto.TOTAL_PERSISTENT_PROCS, numPers); 17462 proto.write(ActivityManagerServiceDumpProcessesProto.PROCESSES_READY, mProcessesReady); 17463 proto.write(ActivityManagerServiceDumpProcessesProto.SYSTEM_READY, mSystemReady); 17464 proto.write(ActivityManagerServiceDumpProcessesProto.BOOTED, mBooted); 17465 proto.write(ActivityManagerServiceDumpProcessesProto.FACTORY_TEST, mFactoryTest); 17466 proto.write(ActivityManagerServiceDumpProcessesProto.BOOTING, mBooting); 17467 proto.write(ActivityManagerServiceDumpProcessesProto.CALL_FINISH_BOOTING, mCallFinishBooting); 17468 proto.write(ActivityManagerServiceDumpProcessesProto.BOOT_ANIMATION_COMPLETE, mBootAnimationComplete); 17469 proto.write(ActivityManagerServiceDumpProcessesProto.LAST_POWER_CHECK_UPTIME_MS, mLastPowerCheckUptime); 17470 mStackSupervisor.mGoingToSleep.writeToProto(proto, ActivityManagerServiceDumpProcessesProto.GOING_TO_SLEEP); 17471 mStackSupervisor.mLaunchingActivity.writeToProto(proto, ActivityManagerServiceDumpProcessesProto.LAUNCHING_ACTIVITY); 17472 proto.write(ActivityManagerServiceDumpProcessesProto.ADJ_SEQ, mAdjSeq); 17473 proto.write(ActivityManagerServiceDumpProcessesProto.LRU_SEQ, mLruSeq); 17474 proto.write(ActivityManagerServiceDumpProcessesProto.NUM_NON_CACHED_PROCS, mNumNonCachedProcs); 17475 proto.write(ActivityManagerServiceDumpProcessesProto.NUM_SERVICE_PROCS, mNumServiceProcs); 17476 proto.write(ActivityManagerServiceDumpProcessesProto.NEW_NUM_SERVICE_PROCS, mNewNumServiceProcs); 17477 proto.write(ActivityManagerServiceDumpProcessesProto.ALLOW_LOWER_MEM_LEVEL, mAllowLowerMemLevel); 17478 proto.write(ActivityManagerServiceDumpProcessesProto.LAST_MEMORY_LEVEL, mLastMemoryLevel); 17479 proto.write(ActivityManagerServiceDumpProcessesProto.LAST_NUM_PROCESSES, mLastNumProcesses); 17480 long now = SystemClock.uptimeMillis(); 17481 ProtoUtils.toDuration(proto, ActivityManagerServiceDumpProcessesProto.LAST_IDLE_TIME, mLastIdleTime, now); 17482 proto.write(ActivityManagerServiceDumpProcessesProto.LOW_RAM_SINCE_LAST_IDLE_MS, getLowRamTimeSinceIdle(now)); 17483 } 17484 17485 } 17486 17487 void writeProcessesToGcToProto(ProtoOutputStream proto, long fieldId, String dumpPackage) { 17488 if (mProcessesToGc.size() > 0) { 17489 long now = SystemClock.uptimeMillis(); 17490 for (int i=0; i<mProcessesToGc.size(); i++) { 17491 ProcessRecord r = mProcessesToGc.get(i); 17492 if (dumpPackage != null && !dumpPackage.equals(r.info.packageName)) { 17493 continue; 17494 } 17495 final long token = proto.start(fieldId); 17496 r.writeToProto(proto, ProcessToGcProto.PROC); 17497 proto.write(ProcessToGcProto.REPORT_LOW_MEMORY, r.reportLowMemory); 17498 proto.write(ProcessToGcProto.NOW_UPTIME_MS, now); 17499 proto.write(ProcessToGcProto.LAST_GCED_MS, r.lastRequestedGc); 17500 proto.write(ProcessToGcProto.LAST_LOW_MEMORY_MS, r.lastLowMemory); 17501 proto.end(token); 17502 } 17503 } 17504 } 17505 17506 boolean dumpProcessesToGc(PrintWriter pw, boolean needSep, String dumpPackage) { 17507 if (mProcessesToGc.size() > 0) { 17508 boolean printed = false; 17509 long now = SystemClock.uptimeMillis(); 17510 for (int i=0; i<mProcessesToGc.size(); i++) { 17511 ProcessRecord proc = mProcessesToGc.get(i); 17512 if (dumpPackage != null && !dumpPackage.equals(proc.info.packageName)) { 17513 continue; 17514 } 17515 if (!printed) { 17516 if (needSep) pw.println(); 17517 needSep = true; 17518 pw.println(" Processes that are waiting to GC:"); 17519 printed = true; 17520 } 17521 pw.print(" Process "); pw.println(proc); 17522 pw.print(" lowMem="); pw.print(proc.reportLowMemory); 17523 pw.print(", last gced="); 17524 pw.print(now-proc.lastRequestedGc); 17525 pw.print(" ms ago, last lowMem="); 17526 pw.print(now-proc.lastLowMemory); 17527 pw.println(" ms ago"); 17528 17529 } 17530 } 17531 return needSep; 17532 } 17533 17534 void printOomLevel(PrintWriter pw, String name, int adj) { 17535 pw.print(" "); 17536 if (adj >= 0) { 17537 pw.print(' '); 17538 if (adj < 10) pw.print(' '); 17539 } else { 17540 if (adj > -10) pw.print(' '); 17541 } 17542 pw.print(adj); 17543 pw.print(": "); 17544 pw.print(name); 17545 pw.print(" ("); 17546 pw.print(stringifySize(mProcessList.getMemLevel(adj), 1024)); 17547 pw.println(")"); 17548 } 17549 17550 boolean dumpOomLocked(FileDescriptor fd, PrintWriter pw, String[] args, 17551 int opti, boolean dumpAll) { 17552 boolean needSep = false; 17553 17554 if (mLruProcesses.size() > 0) { 17555 if (needSep) pw.println(); 17556 needSep = true; 17557 pw.println(" OOM levels:"); 17558 printOomLevel(pw, "SYSTEM_ADJ", ProcessList.SYSTEM_ADJ); 17559 printOomLevel(pw, "PERSISTENT_PROC_ADJ", ProcessList.PERSISTENT_PROC_ADJ); 17560 printOomLevel(pw, "PERSISTENT_SERVICE_ADJ", ProcessList.PERSISTENT_SERVICE_ADJ); 17561 printOomLevel(pw, "FOREGROUND_APP_ADJ", ProcessList.FOREGROUND_APP_ADJ); 17562 printOomLevel(pw, "VISIBLE_APP_ADJ", ProcessList.VISIBLE_APP_ADJ); 17563 printOomLevel(pw, "PERCEPTIBLE_APP_ADJ", ProcessList.PERCEPTIBLE_APP_ADJ); 17564 printOomLevel(pw, "BACKUP_APP_ADJ", ProcessList.BACKUP_APP_ADJ); 17565 printOomLevel(pw, "HEAVY_WEIGHT_APP_ADJ", ProcessList.HEAVY_WEIGHT_APP_ADJ); 17566 printOomLevel(pw, "SERVICE_ADJ", ProcessList.SERVICE_ADJ); 17567 printOomLevel(pw, "HOME_APP_ADJ", ProcessList.HOME_APP_ADJ); 17568 printOomLevel(pw, "PREVIOUS_APP_ADJ", ProcessList.PREVIOUS_APP_ADJ); 17569 printOomLevel(pw, "SERVICE_B_ADJ", ProcessList.SERVICE_B_ADJ); 17570 printOomLevel(pw, "CACHED_APP_MIN_ADJ", ProcessList.CACHED_APP_MIN_ADJ); 17571 printOomLevel(pw, "CACHED_APP_MAX_ADJ", ProcessList.CACHED_APP_MAX_ADJ); 17572 17573 if (needSep) pw.println(); 17574 pw.print(" Process OOM control ("); pw.print(mLruProcesses.size()); 17575 pw.print(" total, non-act at "); 17576 pw.print(mLruProcesses.size()-mLruProcessActivityStart); 17577 pw.print(", non-svc at "); 17578 pw.print(mLruProcesses.size()-mLruProcessServiceStart); 17579 pw.println("):"); 17580 dumpProcessOomList(pw, this, mLruProcesses, " ", "Proc", "PERS", true, null); 17581 needSep = true; 17582 } 17583 17584 dumpProcessesToGc(pw, needSep, null); 17585 17586 pw.println(); 17587 pw.println(" mHomeProcess: " + mHomeProcess); 17588 pw.println(" mPreviousProcess: " + mPreviousProcess); 17589 if (mHeavyWeightProcess != null) { 17590 pw.println(" mHeavyWeightProcess: " + mHeavyWeightProcess); 17591 } 17592 17593 return true; 17594 } 17595 17596 /** 17597 * There are three ways to call this: 17598 * - no provider specified: dump all the providers 17599 * - a flattened component name that matched an existing provider was specified as the 17600 * first arg: dump that one provider 17601 * - the first arg isn't the flattened component name of an existing provider: 17602 * dump all providers whose component contains the first arg as a substring 17603 */ 17604 protected boolean dumpProvider(FileDescriptor fd, PrintWriter pw, String name, String[] args, 17605 int opti, boolean dumpAll) { 17606 return mProviderMap.dumpProvider(fd, pw, name, args, opti, dumpAll); 17607 } 17608 17609 /** 17610 * Similar to the dumpProvider, but only dumps the first matching provider. 17611 * The provider is responsible for dumping as proto. 17612 */ 17613 protected boolean dumpProviderProto(FileDescriptor fd, PrintWriter pw, String name, 17614 String[] args) { 17615 return mProviderMap.dumpProviderProto(fd, pw, name, args); 17616 } 17617 17618 static class ItemMatcher { 17619 ArrayList<ComponentName> components; 17620 ArrayList<String> strings; 17621 ArrayList<Integer> objects; 17622 boolean all; 17623 17624 ItemMatcher() { 17625 all = true; 17626 } 17627 17628 void build(String name) { 17629 ComponentName componentName = ComponentName.unflattenFromString(name); 17630 if (componentName != null) { 17631 if (components == null) { 17632 components = new ArrayList<ComponentName>(); 17633 } 17634 components.add(componentName); 17635 all = false; 17636 } else { 17637 int objectId = 0; 17638 // Not a '/' separated full component name; maybe an object ID? 17639 try { 17640 objectId = Integer.parseInt(name, 16); 17641 if (objects == null) { 17642 objects = new ArrayList<Integer>(); 17643 } 17644 objects.add(objectId); 17645 all = false; 17646 } catch (RuntimeException e) { 17647 // Not an integer; just do string match. 17648 if (strings == null) { 17649 strings = new ArrayList<String>(); 17650 } 17651 strings.add(name); 17652 all = false; 17653 } 17654 } 17655 } 17656 17657 int build(String[] args, int opti) { 17658 for (; opti<args.length; opti++) { 17659 String name = args[opti]; 17660 if ("--".equals(name)) { 17661 return opti+1; 17662 } 17663 build(name); 17664 } 17665 return opti; 17666 } 17667 17668 boolean match(Object object, ComponentName comp) { 17669 if (all) { 17670 return true; 17671 } 17672 if (components != null) { 17673 for (int i=0; i<components.size(); i++) { 17674 if (components.get(i).equals(comp)) { 17675 return true; 17676 } 17677 } 17678 } 17679 if (objects != null) { 17680 for (int i=0; i<objects.size(); i++) { 17681 if (System.identityHashCode(object) == objects.get(i)) { 17682 return true; 17683 } 17684 } 17685 } 17686 if (strings != null) { 17687 String flat = comp.flattenToString(); 17688 for (int i=0; i<strings.size(); i++) { 17689 if (flat.contains(strings.get(i))) { 17690 return true; 17691 } 17692 } 17693 } 17694 return false; 17695 } 17696 } 17697 17698 /** 17699 * There are three things that cmd can be: 17700 * - a flattened component name that matches an existing activity 17701 * - the cmd arg isn't the flattened component name of an existing activity: 17702 * dump all activity whose component contains the cmd as a substring 17703 * - A hex number of the ActivityRecord object instance. 17704 * 17705 * @param dumpVisibleStacksOnly dump activity with {@param name} only if in a visible stack 17706 * @param dumpFocusedStackOnly dump activity with {@param name} only if in the focused stack 17707 */ 17708 protected boolean dumpActivity(FileDescriptor fd, PrintWriter pw, String name, String[] args, 17709 int opti, boolean dumpAll, boolean dumpVisibleStacksOnly, boolean dumpFocusedStackOnly) { 17710 ArrayList<ActivityRecord> activities; 17711 17712 synchronized (this) { 17713 activities = mStackSupervisor.getDumpActivitiesLocked(name, dumpVisibleStacksOnly, 17714 dumpFocusedStackOnly); 17715 } 17716 17717 if (activities.size() <= 0) { 17718 return false; 17719 } 17720 17721 String[] newArgs = new String[args.length - opti]; 17722 System.arraycopy(args, opti, newArgs, 0, args.length - opti); 17723 17724 TaskRecord lastTask = null; 17725 boolean needSep = false; 17726 for (int i=activities.size()-1; i>=0; i--) { 17727 ActivityRecord r = activities.get(i); 17728 if (needSep) { 17729 pw.println(); 17730 } 17731 needSep = true; 17732 synchronized (this) { 17733 final TaskRecord task = r.getTask(); 17734 if (lastTask != task) { 17735 lastTask = task; 17736 pw.print("TASK "); pw.print(lastTask.affinity); 17737 pw.print(" id="); pw.print(lastTask.taskId); 17738 pw.print(" userId="); pw.println(lastTask.userId); 17739 if (dumpAll) { 17740 lastTask.dump(pw, " "); 17741 } 17742 } 17743 } 17744 dumpActivity(" ", fd, pw, activities.get(i), newArgs, dumpAll); 17745 } 17746 return true; 17747 } 17748 17749 /** 17750 * Invokes IApplicationThread.dumpActivity() on the thread of the specified activity if 17751 * there is a thread associated with the activity. 17752 */ 17753 private void dumpActivity(String prefix, FileDescriptor fd, PrintWriter pw, 17754 final ActivityRecord r, String[] args, boolean dumpAll) { 17755 String innerPrefix = prefix + " "; 17756 synchronized (this) { 17757 pw.print(prefix); pw.print("ACTIVITY "); pw.print(r.shortComponentName); 17758 pw.print(" "); pw.print(Integer.toHexString(System.identityHashCode(r))); 17759 pw.print(" pid="); 17760 if (r.app != null) pw.println(r.app.pid); 17761 else pw.println("(not running)"); 17762 if (dumpAll) { 17763 r.dump(pw, innerPrefix); 17764 } 17765 } 17766 if (r.app != null && r.app.thread != null) { 17767 // flush anything that is already in the PrintWriter since the thread is going 17768 // to write to the file descriptor directly 17769 pw.flush(); 17770 try { 17771 TransferPipe tp = new TransferPipe(); 17772 try { 17773 r.app.thread.dumpActivity(tp.getWriteFd(), 17774 r.appToken, innerPrefix, args); 17775 tp.go(fd); 17776 } finally { 17777 tp.kill(); 17778 } 17779 } catch (IOException e) { 17780 pw.println(innerPrefix + "Failure while dumping the activity: " + e); 17781 } catch (RemoteException e) { 17782 pw.println(innerPrefix + "Got a RemoteException while dumping the activity"); 17783 } 17784 } 17785 } 17786 17787 void writeBroadcastsToProtoLocked(ProtoOutputStream proto) { 17788 if (mRegisteredReceivers.size() > 0) { 17789 Iterator it = mRegisteredReceivers.values().iterator(); 17790 while (it.hasNext()) { 17791 ReceiverList r = (ReceiverList)it.next(); 17792 r.writeToProto(proto, ActivityManagerServiceDumpBroadcastsProto.RECEIVER_LIST); 17793 } 17794 } 17795 mReceiverResolver.writeToProto(proto, ActivityManagerServiceDumpBroadcastsProto.RECEIVER_RESOLVER); 17796 for (BroadcastQueue q : mBroadcastQueues) { 17797 q.writeToProto(proto, ActivityManagerServiceDumpBroadcastsProto.BROADCAST_QUEUE); 17798 } 17799 for (int user=0; user<mStickyBroadcasts.size(); user++) { 17800 long token = proto.start(ActivityManagerServiceDumpBroadcastsProto.STICKY_BROADCASTS); 17801 proto.write(StickyBroadcastProto.USER, mStickyBroadcasts.keyAt(user)); 17802 for (Map.Entry<String, ArrayList<Intent>> ent 17803 : mStickyBroadcasts.valueAt(user).entrySet()) { 17804 long actionToken = proto.start(StickyBroadcastProto.ACTIONS); 17805 proto.write(StickyBroadcastProto.StickyAction.NAME, ent.getKey()); 17806 for (Intent intent : ent.getValue()) { 17807 intent.writeToProto(proto, StickyBroadcastProto.StickyAction.INTENTS, 17808 false, true, true, false); 17809 } 17810 proto.end(actionToken); 17811 } 17812 proto.end(token); 17813 } 17814 17815 long handlerToken = proto.start(ActivityManagerServiceDumpBroadcastsProto.HANDLER); 17816 proto.write(ActivityManagerServiceDumpBroadcastsProto.MainHandler.HANDLER, mHandler.toString()); 17817 mHandler.getLooper().writeToProto(proto, 17818 ActivityManagerServiceDumpBroadcastsProto.MainHandler.LOOPER); 17819 proto.end(handlerToken); 17820 } 17821 17822 void dumpBroadcastsLocked(FileDescriptor fd, PrintWriter pw, String[] args, 17823 int opti, boolean dumpAll, String dumpPackage) { 17824 boolean needSep = false; 17825 boolean onlyHistory = false; 17826 boolean printedAnything = false; 17827 17828 if ("history".equals(dumpPackage)) { 17829 if (opti < args.length && "-s".equals(args[opti])) { 17830 dumpAll = false; 17831 } 17832 onlyHistory = true; 17833 dumpPackage = null; 17834 } 17835 17836 pw.println("ACTIVITY MANAGER BROADCAST STATE (dumpsys activity broadcasts)"); 17837 if (!onlyHistory && dumpAll) { 17838 if (mRegisteredReceivers.size() > 0) { 17839 boolean printed = false; 17840 Iterator it = mRegisteredReceivers.values().iterator(); 17841 while (it.hasNext()) { 17842 ReceiverList r = (ReceiverList)it.next(); 17843 if (dumpPackage != null && (r.app == null || 17844 !dumpPackage.equals(r.app.info.packageName))) { 17845 continue; 17846 } 17847 if (!printed) { 17848 pw.println(" Registered Receivers:"); 17849 needSep = true; 17850 printed = true; 17851 printedAnything = true; 17852 } 17853 pw.print(" * "); pw.println(r); 17854 r.dump(pw, " "); 17855 } 17856 } 17857 17858 if (mReceiverResolver.dump(pw, needSep ? 17859 "\n Receiver Resolver Table:" : " Receiver Resolver Table:", 17860 " ", dumpPackage, false, false)) { 17861 needSep = true; 17862 printedAnything = true; 17863 } 17864 } 17865 17866 for (BroadcastQueue q : mBroadcastQueues) { 17867 needSep = q.dumpLocked(fd, pw, args, opti, dumpAll, dumpPackage, needSep); 17868 printedAnything |= needSep; 17869 } 17870 17871 needSep = true; 17872 17873 if (!onlyHistory && mStickyBroadcasts != null && dumpPackage == null) { 17874 for (int user=0; user<mStickyBroadcasts.size(); user++) { 17875 if (needSep) { 17876 pw.println(); 17877 } 17878 needSep = true; 17879 printedAnything = true; 17880 pw.print(" Sticky broadcasts for user "); 17881 pw.print(mStickyBroadcasts.keyAt(user)); pw.println(":"); 17882 StringBuilder sb = new StringBuilder(128); 17883 for (Map.Entry<String, ArrayList<Intent>> ent 17884 : mStickyBroadcasts.valueAt(user).entrySet()) { 17885 pw.print(" * Sticky action "); pw.print(ent.getKey()); 17886 if (dumpAll) { 17887 pw.println(":"); 17888 ArrayList<Intent> intents = ent.getValue(); 17889 final int N = intents.size(); 17890 for (int i=0; i<N; i++) { 17891 sb.setLength(0); 17892 sb.append(" Intent: "); 17893 intents.get(i).toShortString(sb, false, true, false, false); 17894 pw.println(sb.toString()); 17895 Bundle bundle = intents.get(i).getExtras(); 17896 if (bundle != null) { 17897 pw.print(" "); 17898 pw.println(bundle.toString()); 17899 } 17900 } 17901 } else { 17902 pw.println(""); 17903 } 17904 } 17905 } 17906 } 17907 17908 if (!onlyHistory && dumpAll) { 17909 pw.println(); 17910 for (BroadcastQueue queue : mBroadcastQueues) { 17911 pw.println(" mBroadcastsScheduled [" + queue.mQueueName + "]=" 17912 + queue.mBroadcastsScheduled); 17913 } 17914 pw.println(" mHandler:"); 17915 mHandler.dump(new PrintWriterPrinter(pw), " "); 17916 needSep = true; 17917 printedAnything = true; 17918 } 17919 17920 if (!printedAnything) { 17921 pw.println(" (nothing)"); 17922 } 17923 } 17924 17925 void dumpBroadcastStatsLocked(FileDescriptor fd, PrintWriter pw, String[] args, 17926 int opti, boolean dumpAll, String dumpPackage) { 17927 if (mCurBroadcastStats == null) { 17928 return; 17929 } 17930 17931 pw.println("ACTIVITY MANAGER BROADCAST STATS STATE (dumpsys activity broadcast-stats)"); 17932 final long now = SystemClock.elapsedRealtime(); 17933 if (mLastBroadcastStats != null) { 17934 pw.print(" Last stats (from "); 17935 TimeUtils.formatDuration(mLastBroadcastStats.mStartRealtime, now, pw); 17936 pw.print(" to "); 17937 TimeUtils.formatDuration(mLastBroadcastStats.mEndRealtime, now, pw); 17938 pw.print(", "); 17939 TimeUtils.formatDuration(mLastBroadcastStats.mEndUptime 17940 - mLastBroadcastStats.mStartUptime, pw); 17941 pw.println(" uptime):"); 17942 if (!mLastBroadcastStats.dumpStats(pw, " ", dumpPackage)) { 17943 pw.println(" (nothing)"); 17944 } 17945 pw.println(); 17946 } 17947 pw.print(" Current stats (from "); 17948 TimeUtils.formatDuration(mCurBroadcastStats.mStartRealtime, now, pw); 17949 pw.print(" to now, "); 17950 TimeUtils.formatDuration(SystemClock.uptimeMillis() 17951 - mCurBroadcastStats.mStartUptime, pw); 17952 pw.println(" uptime):"); 17953 if (!mCurBroadcastStats.dumpStats(pw, " ", dumpPackage)) { 17954 pw.println(" (nothing)"); 17955 } 17956 } 17957 17958 void dumpBroadcastStatsCheckinLocked(FileDescriptor fd, PrintWriter pw, String[] args, 17959 int opti, boolean fullCheckin, String dumpPackage) { 17960 if (mCurBroadcastStats == null) { 17961 return; 17962 } 17963 17964 if (mLastBroadcastStats != null) { 17965 mLastBroadcastStats.dumpCheckinStats(pw, dumpPackage); 17966 if (fullCheckin) { 17967 mLastBroadcastStats = null; 17968 return; 17969 } 17970 } 17971 mCurBroadcastStats.dumpCheckinStats(pw, dumpPackage); 17972 if (fullCheckin) { 17973 mCurBroadcastStats = null; 17974 } 17975 } 17976 17977 void dumpProvidersLocked(FileDescriptor fd, PrintWriter pw, String[] args, 17978 int opti, boolean dumpAll, String dumpPackage) { 17979 boolean needSep; 17980 boolean printedAnything = false; 17981 17982 ItemMatcher matcher = new ItemMatcher(); 17983 matcher.build(args, opti); 17984 17985 pw.println("ACTIVITY MANAGER CONTENT PROVIDERS (dumpsys activity providers)"); 17986 17987 needSep = mProviderMap.dumpProvidersLocked(pw, dumpAll, dumpPackage); 17988 printedAnything |= needSep; 17989 17990 if (mLaunchingProviders.size() > 0) { 17991 boolean printed = false; 17992 for (int i=mLaunchingProviders.size()-1; i>=0; i--) { 17993 ContentProviderRecord r = mLaunchingProviders.get(i); 17994 if (dumpPackage != null && !dumpPackage.equals(r.name.getPackageName())) { 17995 continue; 17996 } 17997 if (!printed) { 17998 if (needSep) pw.println(); 17999 needSep = true; 18000 pw.println(" Launching content providers:"); 18001 printed = true; 18002 printedAnything = true; 18003 } 18004 pw.print(" Launching #"); pw.print(i); pw.print(": "); 18005 pw.println(r); 18006 } 18007 } 18008 18009 if (!printedAnything) { 18010 pw.println(" (nothing)"); 18011 } 18012 } 18013 18014 @GuardedBy("this") 18015 void dumpPermissionsLocked(FileDescriptor fd, PrintWriter pw, String[] args, 18016 int opti, boolean dumpAll, String dumpPackage) { 18017 boolean needSep = false; 18018 boolean printedAnything = false; 18019 18020 pw.println("ACTIVITY MANAGER URI PERMISSIONS (dumpsys activity permissions)"); 18021 18022 if (mGrantedUriPermissions.size() > 0) { 18023 boolean printed = false; 18024 int dumpUid = -2; 18025 if (dumpPackage != null) { 18026 try { 18027 dumpUid = mContext.getPackageManager().getPackageUidAsUser(dumpPackage, 18028 MATCH_ANY_USER, 0); 18029 } catch (NameNotFoundException e) { 18030 dumpUid = -1; 18031 } 18032 } 18033 for (int i=0; i<mGrantedUriPermissions.size(); i++) { 18034 int uid = mGrantedUriPermissions.keyAt(i); 18035 if (dumpUid >= -1 && UserHandle.getAppId(uid) != dumpUid) { 18036 continue; 18037 } 18038 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i); 18039 if (!printed) { 18040 if (needSep) pw.println(); 18041 needSep = true; 18042 pw.println(" Granted Uri Permissions:"); 18043 printed = true; 18044 printedAnything = true; 18045 } 18046 pw.print(" * UID "); pw.print(uid); pw.println(" holds:"); 18047 for (UriPermission perm : perms.values()) { 18048 pw.print(" "); pw.println(perm); 18049 if (dumpAll) { 18050 perm.dump(pw, " "); 18051 } 18052 } 18053 } 18054 } 18055 18056 if (!printedAnything) { 18057 pw.println(" (nothing)"); 18058 } 18059 } 18060 18061 void dumpPendingIntentsLocked(FileDescriptor fd, PrintWriter pw, String[] args, 18062 int opti, boolean dumpAll, String dumpPackage) { 18063 boolean printed = false; 18064 18065 pw.println("ACTIVITY MANAGER PENDING INTENTS (dumpsys activity intents)"); 18066 18067 if (mIntentSenderRecords.size() > 0) { 18068 // Organize these by package name, so they are easier to read. 18069 final ArrayMap<String, ArrayList<PendingIntentRecord>> byPackage = new ArrayMap<>(); 18070 final ArrayList<WeakReference<PendingIntentRecord>> weakRefs = new ArrayList<>(); 18071 final Iterator<WeakReference<PendingIntentRecord>> it 18072 = mIntentSenderRecords.values().iterator(); 18073 while (it.hasNext()) { 18074 WeakReference<PendingIntentRecord> ref = it.next(); 18075 PendingIntentRecord rec = ref != null ? ref.get() : null; 18076 if (rec == null) { 18077 weakRefs.add(ref); 18078 continue; 18079 } 18080 if (dumpPackage != null && !dumpPackage.equals(rec.key.packageName)) { 18081 continue; 18082 } 18083 ArrayList<PendingIntentRecord> list = byPackage.get(rec.key.packageName); 18084 if (list == null) { 18085 list = new ArrayList<>(); 18086 byPackage.put(rec.key.packageName, list); 18087 } 18088 list.add(rec); 18089 } 18090 for (int i = 0; i < byPackage.size(); i++) { 18091 ArrayList<PendingIntentRecord> intents = byPackage.valueAt(i); 18092 printed = true; 18093 pw.print(" * "); pw.print(byPackage.keyAt(i)); 18094 pw.print(": "); pw.print(intents.size()); pw.println(" items"); 18095 for (int j = 0; j < intents.size(); j++) { 18096 pw.print(" #"); pw.print(j); pw.print(": "); pw.println(intents.get(j)); 18097 if (dumpAll) { 18098 intents.get(j).dump(pw, " "); 18099 } 18100 } 18101 } 18102 if (weakRefs.size() > 0) { 18103 printed = true; 18104 pw.println(" * WEAK REFS:"); 18105 for (int i = 0; i < weakRefs.size(); i++) { 18106 pw.print(" #"); pw.print(i); pw.print(": "); pw.println(weakRefs.get(i)); 18107 } 18108 } 18109 } 18110 18111 if (!printed) { 18112 pw.println(" (nothing)"); 18113 } 18114 } 18115 18116 private static final int dumpProcessList(PrintWriter pw, 18117 ActivityManagerService service, List list, 18118 String prefix, String normalLabel, String persistentLabel, 18119 String dumpPackage) { 18120 int numPers = 0; 18121 final int N = list.size()-1; 18122 for (int i=N; i>=0; i--) { 18123 ProcessRecord r = (ProcessRecord)list.get(i); 18124 if (dumpPackage != null && !dumpPackage.equals(r.info.packageName)) { 18125 continue; 18126 } 18127 pw.println(String.format("%s%s #%2d: %s", 18128 prefix, (r.persistent ? persistentLabel : normalLabel), 18129 i, r.toString())); 18130 if (r.persistent) { 18131 numPers++; 18132 } 18133 } 18134 return numPers; 18135 } 18136 18137 private static final ArrayList<Pair<ProcessRecord, Integer>> 18138 sortProcessOomList(List<ProcessRecord> origList, String dumpPackage) { 18139 ArrayList<Pair<ProcessRecord, Integer>> list 18140 = new ArrayList<Pair<ProcessRecord, Integer>>(origList.size()); 18141 for (int i=0; i<origList.size(); i++) { 18142 ProcessRecord r = origList.get(i); 18143 if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) { 18144 continue; 18145 } 18146 list.add(new Pair<ProcessRecord, Integer>(origList.get(i), i)); 18147 } 18148 18149 Comparator<Pair<ProcessRecord, Integer>> comparator 18150 = new Comparator<Pair<ProcessRecord, Integer>>() { 18151 @Override 18152 public int compare(Pair<ProcessRecord, Integer> object1, 18153 Pair<ProcessRecord, Integer> object2) { 18154 if (object1.first.setAdj != object2.first.setAdj) { 18155 return object1.first.setAdj > object2.first.setAdj ? -1 : 1; 18156 } 18157 if (object1.first.setProcState != object2.first.setProcState) { 18158 return object1.first.setProcState > object2.first.setProcState ? -1 : 1; 18159 } 18160 if (object1.second.intValue() != object2.second.intValue()) { 18161 return object1.second.intValue() > object2.second.intValue() ? -1 : 1; 18162 } 18163 return 0; 18164 } 18165 }; 18166 18167 Collections.sort(list, comparator); 18168 return list; 18169 } 18170 18171 private static final boolean writeProcessOomListToProto(ProtoOutputStream proto, long fieldId, 18172 ActivityManagerService service, List<ProcessRecord> origList, 18173 boolean inclDetails, String dumpPackage) { 18174 ArrayList<Pair<ProcessRecord, Integer>> list = sortProcessOomList(origList, dumpPackage); 18175 if (list.isEmpty()) return false; 18176 18177 final long curUptime = SystemClock.uptimeMillis(); 18178 18179 for (int i = list.size() - 1; i >= 0; i--) { 18180 ProcessRecord r = list.get(i).first; 18181 long token = proto.start(fieldId); 18182 String oomAdj = ProcessList.makeOomAdjString(r.setAdj); 18183 proto.write(ProcessOomProto.PERSISTENT, r.persistent); 18184 proto.write(ProcessOomProto.NUM, (origList.size()-1)-list.get(i).second); 18185 proto.write(ProcessOomProto.OOM_ADJ, oomAdj); 18186 int schedGroup = ProcessOomProto.SCHED_GROUP_UNKNOWN; 18187 switch (r.setSchedGroup) { 18188 case ProcessList.SCHED_GROUP_BACKGROUND: 18189 schedGroup = ProcessOomProto.SCHED_GROUP_BACKGROUND; 18190 break; 18191 case ProcessList.SCHED_GROUP_DEFAULT: 18192 schedGroup = ProcessOomProto.SCHED_GROUP_DEFAULT; 18193 break; 18194 case ProcessList.SCHED_GROUP_TOP_APP: 18195 schedGroup = ProcessOomProto.SCHED_GROUP_TOP_APP; 18196 break; 18197 case ProcessList.SCHED_GROUP_TOP_APP_BOUND: 18198 schedGroup = ProcessOomProto.SCHED_GROUP_TOP_APP_BOUND; 18199 break; 18200 } 18201 if (schedGroup != ProcessOomProto.SCHED_GROUP_UNKNOWN) { 18202 proto.write(ProcessOomProto.SCHED_GROUP, schedGroup); 18203 } 18204 if (r.foregroundActivities) { 18205 proto.write(ProcessOomProto.ACTIVITIES, true); 18206 } else if (r.foregroundServices) { 18207 proto.write(ProcessOomProto.SERVICES, true); 18208 } 18209 proto.write(ProcessOomProto.STATE, ProcessList.makeProcStateProtoEnum(r.curProcState)); 18210 proto.write(ProcessOomProto.TRIM_MEMORY_LEVEL, r.trimMemoryLevel); 18211 r.writeToProto(proto, ProcessOomProto.PROC); 18212 proto.write(ProcessOomProto.ADJ_TYPE, r.adjType); 18213 if (r.adjSource != null || r.adjTarget != null) { 18214 if (r.adjTarget instanceof ComponentName) { 18215 ComponentName cn = (ComponentName) r.adjTarget; 18216 cn.writeToProto(proto, ProcessOomProto.ADJ_TARGET_COMPONENT_NAME); 18217 } else if (r.adjTarget != null) { 18218 proto.write(ProcessOomProto.ADJ_TARGET_OBJECT, r.adjTarget.toString()); 18219 } 18220 if (r.adjSource instanceof ProcessRecord) { 18221 ProcessRecord p = (ProcessRecord) r.adjSource; 18222 p.writeToProto(proto, ProcessOomProto.ADJ_SOURCE_PROC); 18223 } else if (r.adjSource != null) { 18224 proto.write(ProcessOomProto.ADJ_SOURCE_OBJECT, r.adjSource.toString()); 18225 } 18226 } 18227 if (inclDetails) { 18228 long detailToken = proto.start(ProcessOomProto.DETAIL); 18229 proto.write(ProcessOomProto.Detail.MAX_ADJ, r.maxAdj); 18230 proto.write(ProcessOomProto.Detail.CUR_RAW_ADJ, r.curRawAdj); 18231 proto.write(ProcessOomProto.Detail.SET_RAW_ADJ, r.setRawAdj); 18232 proto.write(ProcessOomProto.Detail.CUR_ADJ, r.curAdj); 18233 proto.write(ProcessOomProto.Detail.SET_ADJ, r.setAdj); 18234 proto.write(ProcessOomProto.Detail.CURRENT_STATE, 18235 ProcessList.makeProcStateProtoEnum(r.curProcState)); 18236 proto.write(ProcessOomProto.Detail.SET_STATE, 18237 ProcessList.makeProcStateProtoEnum(r.setProcState)); 18238 proto.write(ProcessOomProto.Detail.LAST_PSS, DebugUtils.sizeValueToString( 18239 r.lastPss*1024, new StringBuilder())); 18240 proto.write(ProcessOomProto.Detail.LAST_SWAP_PSS, DebugUtils.sizeValueToString( 18241 r.lastSwapPss*1024, new StringBuilder())); 18242 proto.write(ProcessOomProto.Detail.LAST_CACHED_PSS, DebugUtils.sizeValueToString( 18243 r.lastCachedPss*1024, new StringBuilder())); 18244 proto.write(ProcessOomProto.Detail.CACHED, r.cached); 18245 proto.write(ProcessOomProto.Detail.EMPTY, r.empty); 18246 proto.write(ProcessOomProto.Detail.HAS_ABOVE_CLIENT, r.hasAboveClient); 18247 18248 if (r.setProcState >= ActivityManager.PROCESS_STATE_SERVICE) { 18249 if (r.lastCpuTime != 0) { 18250 long uptimeSince = curUptime - service.mLastPowerCheckUptime; 18251 long timeUsed = r.curCpuTime - r.lastCpuTime; 18252 long cpuTimeToken = proto.start(ProcessOomProto.Detail.SERVICE_RUN_TIME); 18253 proto.write(ProcessOomProto.Detail.CpuRunTime.OVER_MS, uptimeSince); 18254 proto.write(ProcessOomProto.Detail.CpuRunTime.USED_MS, timeUsed); 18255 proto.write(ProcessOomProto.Detail.CpuRunTime.ULTILIZATION, 18256 (100.0*timeUsed)/uptimeSince); 18257 proto.end(cpuTimeToken); 18258 } 18259 } 18260 proto.end(detailToken); 18261 } 18262 proto.end(token); 18263 } 18264 18265 return true; 18266 } 18267 18268 private static final boolean dumpProcessOomList(PrintWriter pw, 18269 ActivityManagerService service, List<ProcessRecord> origList, 18270 String prefix, String normalLabel, String persistentLabel, 18271 boolean inclDetails, String dumpPackage) { 18272 18273 ArrayList<Pair<ProcessRecord, Integer>> list = sortProcessOomList(origList, dumpPackage); 18274 if (list.isEmpty()) return false; 18275 18276 final long curUptime = SystemClock.uptimeMillis(); 18277 final long uptimeSince = curUptime - service.mLastPowerCheckUptime; 18278 18279 for (int i=list.size()-1; i>=0; i--) { 18280 ProcessRecord r = list.get(i).first; 18281 String oomAdj = ProcessList.makeOomAdjString(r.setAdj); 18282 char schedGroup; 18283 switch (r.setSchedGroup) { 18284 case ProcessList.SCHED_GROUP_BACKGROUND: 18285 schedGroup = 'B'; 18286 break; 18287 case ProcessList.SCHED_GROUP_DEFAULT: 18288 schedGroup = 'F'; 18289 break; 18290 case ProcessList.SCHED_GROUP_TOP_APP: 18291 schedGroup = 'T'; 18292 break; 18293 case ProcessList.SCHED_GROUP_RESTRICTED: 18294 schedGroup = 'R'; 18295 break; 18296 default: 18297 schedGroup = '?'; 18298 break; 18299 } 18300 char foreground; 18301 if (r.foregroundActivities) { 18302 foreground = 'A'; 18303 } else if (r.foregroundServices) { 18304 foreground = 'S'; 18305 } else { 18306 foreground = ' '; 18307 } 18308 String procState = ProcessList.makeProcStateString(r.curProcState); 18309 pw.print(prefix); 18310 pw.print(r.persistent ? persistentLabel : normalLabel); 18311 pw.print(" #"); 18312 int num = (origList.size()-1)-list.get(i).second; 18313 if (num < 10) pw.print(' '); 18314 pw.print(num); 18315 pw.print(": "); 18316 pw.print(oomAdj); 18317 pw.print(' '); 18318 pw.print(schedGroup); 18319 pw.print('/'); 18320 pw.print(foreground); 18321 pw.print('/'); 18322 pw.print(procState); 18323 pw.print(" trm:"); 18324 if (r.trimMemoryLevel < 10) pw.print(' '); 18325 pw.print(r.trimMemoryLevel); 18326 pw.print(' '); 18327 pw.print(r.toShortString()); 18328 pw.print(" ("); 18329 pw.print(r.adjType); 18330 pw.println(')'); 18331 if (r.adjSource != null || r.adjTarget != null) { 18332 pw.print(prefix); 18333 pw.print(" "); 18334 if (r.adjTarget instanceof ComponentName) { 18335 pw.print(((ComponentName)r.adjTarget).flattenToShortString()); 18336 } else if (r.adjTarget != null) { 18337 pw.print(r.adjTarget.toString()); 18338 } else { 18339 pw.print("{null}"); 18340 } 18341 pw.print("<="); 18342 if (r.adjSource instanceof ProcessRecord) { 18343 pw.print("Proc{"); 18344 pw.print(((ProcessRecord)r.adjSource).toShortString()); 18345 pw.println("}"); 18346 } else if (r.adjSource != null) { 18347 pw.println(r.adjSource.toString()); 18348 } else { 18349 pw.println("{null}"); 18350 } 18351 } 18352 if (inclDetails) { 18353 pw.print(prefix); 18354 pw.print(" "); 18355 pw.print("oom: max="); pw.print(r.maxAdj); 18356 pw.print(" curRaw="); pw.print(r.curRawAdj); 18357 pw.print(" setRaw="); pw.print(r.setRawAdj); 18358 pw.print(" cur="); pw.print(r.curAdj); 18359 pw.print(" set="); pw.println(r.setAdj); 18360 pw.print(prefix); 18361 pw.print(" "); 18362 pw.print("state: cur="); pw.print(ProcessList.makeProcStateString(r.curProcState)); 18363 pw.print(" set="); pw.print(ProcessList.makeProcStateString(r.setProcState)); 18364 pw.print(" lastPss="); DebugUtils.printSizeValue(pw, r.lastPss*1024); 18365 pw.print(" lastSwapPss="); DebugUtils.printSizeValue(pw, r.lastSwapPss*1024); 18366 pw.print(" lastCachedPss="); DebugUtils.printSizeValue(pw, r.lastCachedPss*1024); 18367 pw.println(); 18368 pw.print(prefix); 18369 pw.print(" "); 18370 pw.print("cached="); pw.print(r.cached); 18371 pw.print(" empty="); pw.print(r.empty); 18372 pw.print(" hasAboveClient="); pw.println(r.hasAboveClient); 18373 18374 if (r.setProcState >= ActivityManager.PROCESS_STATE_SERVICE) { 18375 if (r.lastCpuTime != 0) { 18376 long timeUsed = r.curCpuTime - r.lastCpuTime; 18377 pw.print(prefix); 18378 pw.print(" "); 18379 pw.print("run cpu over "); 18380 TimeUtils.formatDuration(uptimeSince, pw); 18381 pw.print(" used "); 18382 TimeUtils.formatDuration(timeUsed, pw); 18383 pw.print(" ("); 18384 pw.print((timeUsed*100)/uptimeSince); 18385 pw.println("%)"); 18386 } 18387 } 18388 } 18389 } 18390 return true; 18391 } 18392 18393 ArrayList<ProcessRecord> collectProcesses(PrintWriter pw, int start, boolean allPkgs, 18394 String[] args) { 18395 ArrayList<ProcessRecord> procs; 18396 synchronized (this) { 18397 if (args != null && args.length > start 18398 && args[start].charAt(0) != '-') { 18399 procs = new ArrayList<ProcessRecord>(); 18400 int pid = -1; 18401 try { 18402 pid = Integer.parseInt(args[start]); 18403 } catch (NumberFormatException e) { 18404 } 18405 for (int i=mLruProcesses.size()-1; i>=0; i--) { 18406 ProcessRecord proc = mLruProcesses.get(i); 18407 if (proc.pid > 0 && proc.pid == pid) { 18408 procs.add(proc); 18409 } else if (allPkgs && proc.pkgList != null 18410 && proc.pkgList.containsKey(args[start])) { 18411 procs.add(proc); 18412 } else if (proc.processName.equals(args[start])) { 18413 procs.add(proc); 18414 } 18415 } 18416 if (procs.size() <= 0) { 18417 return null; 18418 } 18419 } else { 18420 procs = new ArrayList<ProcessRecord>(mLruProcesses); 18421 } 18422 } 18423 return procs; 18424 } 18425 18426 final void dumpGraphicsHardwareUsage(FileDescriptor fd, 18427 PrintWriter pw, String[] args) { 18428 ArrayList<ProcessRecord> procs = collectProcesses(pw, 0, false, args); 18429 if (procs == null) { 18430 pw.println("No process found for: " + args[0]); 18431 return; 18432 } 18433 18434 long uptime = SystemClock.uptimeMillis(); 18435 long realtime = SystemClock.elapsedRealtime(); 18436 pw.println("Applications Graphics Acceleration Info:"); 18437 pw.println("Uptime: " + uptime + " Realtime: " + realtime); 18438 18439 for (int i = procs.size() - 1 ; i >= 0 ; i--) { 18440 ProcessRecord r = procs.get(i); 18441 if (r.thread != null) { 18442 pw.println("\n** Graphics info for pid " + r.pid + " [" + r.processName + "] **"); 18443 pw.flush(); 18444 try { 18445 TransferPipe tp = new TransferPipe(); 18446 try { 18447 r.thread.dumpGfxInfo(tp.getWriteFd(), args); 18448 tp.go(fd); 18449 } finally { 18450 tp.kill(); 18451 } 18452 } catch (IOException e) { 18453 pw.println("Failure while dumping the app: " + r); 18454 pw.flush(); 18455 } catch (RemoteException e) { 18456 pw.println("Got a RemoteException while dumping the app " + r); 18457 pw.flush(); 18458 } 18459 } 18460 } 18461 } 18462 18463 final void dumpDbInfo(FileDescriptor fd, PrintWriter pw, String[] args) { 18464 ArrayList<ProcessRecord> procs = collectProcesses(pw, 0, false, args); 18465 if (procs == null) { 18466 pw.println("No process found for: " + args[0]); 18467 return; 18468 } 18469 18470 pw.println("Applications Database Info:"); 18471 18472 for (int i = procs.size() - 1 ; i >= 0 ; i--) { 18473 ProcessRecord r = procs.get(i); 18474 if (r.thread != null) { 18475 pw.println("\n** Database info for pid " + r.pid + " [" + r.processName + "] **"); 18476 pw.flush(); 18477 try { 18478 TransferPipe tp = new TransferPipe(); 18479 try { 18480 r.thread.dumpDbInfo(tp.getWriteFd(), args); 18481 tp.go(fd); 18482 } finally { 18483 tp.kill(); 18484 } 18485 } catch (IOException e) { 18486 pw.println("Failure while dumping the app: " + r); 18487 pw.flush(); 18488 } catch (RemoteException e) { 18489 pw.println("Got a RemoteException while dumping the app " + r); 18490 pw.flush(); 18491 } 18492 } 18493 } 18494 } 18495 18496 final static class MemItem { 18497 final boolean isProc; 18498 final String label; 18499 final String shortLabel; 18500 final long pss; 18501 final long swapPss; 18502 final int id; 18503 final boolean hasActivities; 18504 ArrayList<MemItem> subitems; 18505 18506 public MemItem(String _label, String _shortLabel, long _pss, long _swapPss, int _id, 18507 boolean _hasActivities) { 18508 isProc = true; 18509 label = _label; 18510 shortLabel = _shortLabel; 18511 pss = _pss; 18512 swapPss = _swapPss; 18513 id = _id; 18514 hasActivities = _hasActivities; 18515 } 18516 18517 public MemItem(String _label, String _shortLabel, long _pss, long _swapPss, int _id) { 18518 isProc = false; 18519 label = _label; 18520 shortLabel = _shortLabel; 18521 pss = _pss; 18522 swapPss = _swapPss; 18523 id = _id; 18524 hasActivities = false; 18525 } 18526 } 18527 18528 private static void sortMemItems(List<MemItem> items) { 18529 Collections.sort(items, new Comparator<MemItem>() { 18530 @Override 18531 public int compare(MemItem lhs, MemItem rhs) { 18532 if (lhs.pss < rhs.pss) { 18533 return 1; 18534 } else if (lhs.pss > rhs.pss) { 18535 return -1; 18536 } 18537 return 0; 18538 } 18539 }); 18540 } 18541 18542 static final void dumpMemItems(PrintWriter pw, String prefix, String tag, 18543 ArrayList<MemItem> items, boolean sort, boolean isCompact, boolean dumpSwapPss) { 18544 if (sort && !isCompact) { 18545 sortMemItems(items); 18546 } 18547 18548 for (int i=0; i<items.size(); i++) { 18549 MemItem mi = items.get(i); 18550 if (!isCompact) { 18551 if (dumpSwapPss) { 18552 pw.printf("%s%s: %-60s (%s in swap)\n", prefix, stringifyKBSize(mi.pss), 18553 mi.label, stringifyKBSize(mi.swapPss)); 18554 } else { 18555 pw.printf("%s%s: %s\n", prefix, stringifyKBSize(mi.pss), mi.label); 18556 } 18557 } else if (mi.isProc) { 18558 pw.print("proc,"); pw.print(tag); pw.print(","); pw.print(mi.shortLabel); 18559 pw.print(","); pw.print(mi.id); pw.print(","); pw.print(mi.pss); pw.print(","); 18560 pw.print(dumpSwapPss ? mi.swapPss : "N/A"); 18561 pw.println(mi.hasActivities ? ",a" : ",e"); 18562 } else { 18563 pw.print(tag); pw.print(","); pw.print(mi.shortLabel); pw.print(","); 18564 pw.print(mi.pss); pw.print(","); pw.println(dumpSwapPss ? mi.swapPss : "N/A"); 18565 } 18566 if (mi.subitems != null) { 18567 dumpMemItems(pw, prefix + " ", mi.shortLabel, mi.subitems, 18568 true, isCompact, dumpSwapPss); 18569 } 18570 } 18571 } 18572 18573 static final void dumpMemItems(ProtoOutputStream proto, long fieldId, String tag, 18574 ArrayList<MemItem> items, boolean sort, boolean dumpSwapPss) { 18575 if (sort) { 18576 sortMemItems(items); 18577 } 18578 18579 for (int i=0; i<items.size(); i++) { 18580 MemItem mi = items.get(i); 18581 final long token = proto.start(fieldId); 18582 18583 proto.write(MemInfoDumpProto.MemItem.TAG, tag); 18584 proto.write(MemInfoDumpProto.MemItem.LABEL, mi.shortLabel); 18585 proto.write(MemInfoDumpProto.MemItem.IS_PROC, mi.isProc); 18586 proto.write(MemInfoDumpProto.MemItem.ID, mi.id); 18587 proto.write(MemInfoDumpProto.MemItem.HAS_ACTIVITIES, mi.hasActivities); 18588 proto.write(MemInfoDumpProto.MemItem.PSS_KB, mi.pss); 18589 if (dumpSwapPss) { 18590 proto.write(MemInfoDumpProto.MemItem.SWAP_PSS_KB, mi.swapPss); 18591 } 18592 if (mi.subitems != null) { 18593 dumpMemItems(proto, MemInfoDumpProto.MemItem.SUB_ITEMS, mi.shortLabel, mi.subitems, 18594 true, dumpSwapPss); 18595 } 18596 proto.end(token); 18597 } 18598 } 18599 18600 // These are in KB. 18601 static final long[] DUMP_MEM_BUCKETS = new long[] { 18602 5*1024, 7*1024, 10*1024, 15*1024, 20*1024, 30*1024, 40*1024, 80*1024, 18603 120*1024, 160*1024, 200*1024, 18604 250*1024, 300*1024, 350*1024, 400*1024, 500*1024, 600*1024, 800*1024, 18605 1*1024*1024, 2*1024*1024, 5*1024*1024, 10*1024*1024, 20*1024*1024 18606 }; 18607 18608 static final void appendMemBucket(StringBuilder out, long memKB, String label, 18609 boolean stackLike) { 18610 int start = label.lastIndexOf('.'); 18611 if (start >= 0) start++; 18612 else start = 0; 18613 int end = label.length(); 18614 for (int i=0; i<DUMP_MEM_BUCKETS.length; i++) { 18615 if (DUMP_MEM_BUCKETS[i] >= memKB) { 18616 long bucket = DUMP_MEM_BUCKETS[i]/1024; 18617 out.append(bucket); 18618 out.append(stackLike ? "MB." : "MB "); 18619 out.append(label, start, end); 18620 return; 18621 } 18622 } 18623 out.append(memKB/1024); 18624 out.append(stackLike ? "MB." : "MB "); 18625 out.append(label, start, end); 18626 } 18627 18628 static final int[] DUMP_MEM_OOM_ADJ = new int[] { 18629 ProcessList.NATIVE_ADJ, 18630 ProcessList.SYSTEM_ADJ, ProcessList.PERSISTENT_PROC_ADJ, 18631 ProcessList.PERSISTENT_SERVICE_ADJ, ProcessList.FOREGROUND_APP_ADJ, 18632 ProcessList.VISIBLE_APP_ADJ, ProcessList.PERCEPTIBLE_APP_ADJ, 18633 ProcessList.BACKUP_APP_ADJ, ProcessList.HEAVY_WEIGHT_APP_ADJ, 18634 ProcessList.SERVICE_ADJ, ProcessList.HOME_APP_ADJ, 18635 ProcessList.PREVIOUS_APP_ADJ, ProcessList.SERVICE_B_ADJ, ProcessList.CACHED_APP_MIN_ADJ 18636 }; 18637 static final String[] DUMP_MEM_OOM_LABEL = new String[] { 18638 "Native", 18639 "System", "Persistent", "Persistent Service", "Foreground", 18640 "Visible", "Perceptible", 18641 "Heavy Weight", "Backup", 18642 "A Services", "Home", 18643 "Previous", "B Services", "Cached" 18644 }; 18645 static final String[] DUMP_MEM_OOM_COMPACT_LABEL = new String[] { 18646 "native", 18647 "sys", "pers", "persvc", "fore", 18648 "vis", "percept", 18649 "heavy", "backup", 18650 "servicea", "home", 18651 "prev", "serviceb", "cached" 18652 }; 18653 18654 private final void dumpApplicationMemoryUsageHeader(PrintWriter pw, long uptime, 18655 long realtime, boolean isCheckinRequest, boolean isCompact) { 18656 if (isCompact) { 18657 pw.print("version,"); pw.println(MEMINFO_COMPACT_VERSION); 18658 } 18659 if (isCheckinRequest || isCompact) { 18660 // short checkin version 18661 pw.print("time,"); pw.print(uptime); pw.print(","); pw.println(realtime); 18662 } else { 18663 pw.println("Applications Memory Usage (in Kilobytes):"); 18664 pw.println("Uptime: " + uptime + " Realtime: " + realtime); 18665 } 18666 } 18667 18668 private static final int KSM_SHARED = 0; 18669 private static final int KSM_SHARING = 1; 18670 private static final int KSM_UNSHARED = 2; 18671 private static final int KSM_VOLATILE = 3; 18672 18673 private final long[] getKsmInfo() { 18674 long[] longOut = new long[4]; 18675 final int[] SINGLE_LONG_FORMAT = new int[] { 18676 PROC_SPACE_TERM| PROC_OUT_LONG 18677 }; 18678 long[] longTmp = new long[1]; 18679 readProcFile("/sys/kernel/mm/ksm/pages_shared", 18680 SINGLE_LONG_FORMAT, null, longTmp, null); 18681 longOut[KSM_SHARED] = longTmp[0] * ProcessList.PAGE_SIZE / 1024; 18682 longTmp[0] = 0; 18683 readProcFile("/sys/kernel/mm/ksm/pages_sharing", 18684 SINGLE_LONG_FORMAT, null, longTmp, null); 18685 longOut[KSM_SHARING] = longTmp[0] * ProcessList.PAGE_SIZE / 1024; 18686 longTmp[0] = 0; 18687 readProcFile("/sys/kernel/mm/ksm/pages_unshared", 18688 SINGLE_LONG_FORMAT, null, longTmp, null); 18689 longOut[KSM_UNSHARED] = longTmp[0] * ProcessList.PAGE_SIZE / 1024; 18690 longTmp[0] = 0; 18691 readProcFile("/sys/kernel/mm/ksm/pages_volatile", 18692 SINGLE_LONG_FORMAT, null, longTmp, null); 18693 longOut[KSM_VOLATILE] = longTmp[0] * ProcessList.PAGE_SIZE / 1024; 18694 return longOut; 18695 } 18696 18697 private static String stringifySize(long size, int order) { 18698 Locale locale = Locale.US; 18699 switch (order) { 18700 case 1: 18701 return String.format(locale, "%,13d", size); 18702 case 1024: 18703 return String.format(locale, "%,9dK", size / 1024); 18704 case 1024 * 1024: 18705 return String.format(locale, "%,5dM", size / 1024 / 1024); 18706 case 1024 * 1024 * 1024: 18707 return String.format(locale, "%,1dG", size / 1024 / 1024 / 1024); 18708 default: 18709 throw new IllegalArgumentException("Invalid size order"); 18710 } 18711 } 18712 18713 private static String stringifyKBSize(long size) { 18714 return stringifySize(size * 1024, 1024); 18715 } 18716 18717 // Update this version number if you change the 'compact' format. 18718 private static final int MEMINFO_COMPACT_VERSION = 1; 18719 18720 private static class MemoryUsageDumpOptions { 18721 boolean dumpDetails; 18722 boolean dumpFullDetails; 18723 boolean dumpDalvik; 18724 boolean dumpSummaryOnly; 18725 boolean dumpUnreachable; 18726 boolean oomOnly; 18727 boolean isCompact; 18728 boolean localOnly; 18729 boolean packages; 18730 boolean isCheckinRequest; 18731 boolean dumpSwapPss; 18732 boolean dumpProto; 18733 } 18734 18735 final void dumpApplicationMemoryUsage(FileDescriptor fd, PrintWriter pw, String prefix, 18736 String[] args, boolean brief, PrintWriter categoryPw, boolean asProto) { 18737 MemoryUsageDumpOptions opts = new MemoryUsageDumpOptions(); 18738 opts.dumpDetails = false; 18739 opts.dumpFullDetails = false; 18740 opts.dumpDalvik = false; 18741 opts.dumpSummaryOnly = false; 18742 opts.dumpUnreachable = false; 18743 opts.oomOnly = false; 18744 opts.isCompact = false; 18745 opts.localOnly = false; 18746 opts.packages = false; 18747 opts.isCheckinRequest = false; 18748 opts.dumpSwapPss = false; 18749 opts.dumpProto = asProto; 18750 18751 int opti = 0; 18752 while (opti < args.length) { 18753 String opt = args[opti]; 18754 if (opt == null || opt.length() <= 0 || opt.charAt(0) != '-') { 18755 break; 18756 } 18757 opti++; 18758 if ("-a".equals(opt)) { 18759 opts.dumpDetails = true; 18760 opts.dumpFullDetails = true; 18761 opts.dumpDalvik = true; 18762 opts.dumpSwapPss = true; 18763 } else if ("-d".equals(opt)) { 18764 opts.dumpDalvik = true; 18765 } else if ("-c".equals(opt)) { 18766 opts.isCompact = true; 18767 } else if ("-s".equals(opt)) { 18768 opts.dumpDetails = true; 18769 opts.dumpSummaryOnly = true; 18770 } else if ("-S".equals(opt)) { 18771 opts.dumpSwapPss = true; 18772 } else if ("--unreachable".equals(opt)) { 18773 opts.dumpUnreachable = true; 18774 } else if ("--oom".equals(opt)) { 18775 opts.oomOnly = true; 18776 } else if ("--local".equals(opt)) { 18777 opts.localOnly = true; 18778 } else if ("--package".equals(opt)) { 18779 opts.packages = true; 18780 } else if ("--checkin".equals(opt)) { 18781 opts.isCheckinRequest = true; 18782 } else if ("--proto".equals(opt)) { 18783 opts.dumpProto = true; 18784 18785 } else if ("-h".equals(opt)) { 18786 pw.println("meminfo dump options: [-a] [-d] [-c] [-s] [--oom] [process]"); 18787 pw.println(" -a: include all available information for each process."); 18788 pw.println(" -d: include dalvik details."); 18789 pw.println(" -c: dump in a compact machine-parseable representation."); 18790 pw.println(" -s: dump only summary of application memory usage."); 18791 pw.println(" -S: dump also SwapPss."); 18792 pw.println(" --oom: only show processes organized by oom adj."); 18793 pw.println(" --local: only collect details locally, don't call process."); 18794 pw.println(" --package: interpret process arg as package, dumping all"); 18795 pw.println(" processes that have loaded that package."); 18796 pw.println(" --checkin: dump data for a checkin"); 18797 pw.println(" --proto: dump data to proto"); 18798 pw.println("If [process] is specified it can be the name or "); 18799 pw.println("pid of a specific process to dump."); 18800 return; 18801 } else { 18802 pw.println("Unknown argument: " + opt + "; use -h for help"); 18803 } 18804 } 18805 18806 String[] innerArgs = new String[args.length-opti]; 18807 System.arraycopy(args, opti, innerArgs, 0, args.length-opti); 18808 18809 ArrayList<ProcessRecord> procs = collectProcesses(pw, opti, opts.packages, args); 18810 if (opts.dumpProto) { 18811 dumpApplicationMemoryUsage(fd, opts, innerArgs, brief, procs); 18812 } else { 18813 dumpApplicationMemoryUsage(fd, pw, prefix, opts, innerArgs, brief, procs, categoryPw); 18814 } 18815 } 18816 18817 private final void dumpApplicationMemoryUsage(FileDescriptor fd, PrintWriter pw, String prefix, 18818 MemoryUsageDumpOptions opts, String[] innerArgs, boolean brief, 18819 ArrayList<ProcessRecord> procs, PrintWriter categoryPw) { 18820 long uptime = SystemClock.uptimeMillis(); 18821 long realtime = SystemClock.elapsedRealtime(); 18822 final long[] tmpLong = new long[1]; 18823 18824 if (procs == null) { 18825 // No Java processes. Maybe they want to print a native process. 18826 String proc = "N/A"; 18827 if (innerArgs.length > 0) { 18828 proc = innerArgs[0]; 18829 if (proc.charAt(0) != '-') { 18830 ArrayList<ProcessCpuTracker.Stats> nativeProcs 18831 = new ArrayList<ProcessCpuTracker.Stats>(); 18832 updateCpuStatsNow(); 18833 int findPid = -1; 18834 try { 18835 findPid = Integer.parseInt(innerArgs[0]); 18836 } catch (NumberFormatException e) { 18837 } 18838 synchronized (mProcessCpuTracker) { 18839 final int N = mProcessCpuTracker.countStats(); 18840 for (int i=0; i<N; i++) { 18841 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(i); 18842 if (st.pid == findPid || (st.baseName != null 18843 && st.baseName.equals(innerArgs[0]))) { 18844 nativeProcs.add(st); 18845 } 18846 } 18847 } 18848 if (nativeProcs.size() > 0) { 18849 dumpApplicationMemoryUsageHeader(pw, uptime, realtime, 18850 opts.isCheckinRequest, opts.isCompact); 18851 Debug.MemoryInfo mi = null; 18852 for (int i = nativeProcs.size() - 1 ; i >= 0 ; i--) { 18853 final ProcessCpuTracker.Stats r = nativeProcs.get(i); 18854 final int pid = r.pid; 18855 if (!opts.isCheckinRequest && opts.dumpDetails) { 18856 pw.println("\n** MEMINFO in pid " + pid + " [" + r.baseName + "] **"); 18857 } 18858 if (mi == null) { 18859 mi = new Debug.MemoryInfo(); 18860 } 18861 if (opts.dumpDetails || (!brief && !opts.oomOnly)) { 18862 Debug.getMemoryInfo(pid, mi); 18863 } else { 18864 mi.dalvikPss = (int)Debug.getPss(pid, tmpLong, null); 18865 mi.dalvikPrivateDirty = (int)tmpLong[0]; 18866 } 18867 ActivityThread.dumpMemInfoTable(pw, mi, opts.isCheckinRequest, 18868 opts.dumpFullDetails, opts.dumpDalvik, opts.dumpSummaryOnly, 18869 pid, r.baseName, 0, 0, 0, 0, 0, 0); 18870 if (opts.isCheckinRequest) { 18871 pw.println(); 18872 } 18873 } 18874 return; 18875 } 18876 } 18877 } 18878 pw.println("No process found for: " + proc); 18879 return; 18880 } 18881 18882 if (!brief && !opts.oomOnly && (procs.size() == 1 || opts.isCheckinRequest || opts.packages)) { 18883 opts.dumpDetails = true; 18884 } 18885 18886 dumpApplicationMemoryUsageHeader(pw, uptime, realtime, opts.isCheckinRequest, opts.isCompact); 18887 18888 ArrayList<MemItem> procMems = new ArrayList<MemItem>(); 18889 final SparseArray<MemItem> procMemsMap = new SparseArray<MemItem>(); 18890 long nativePss = 0; 18891 long nativeSwapPss = 0; 18892 long dalvikPss = 0; 18893 long dalvikSwapPss = 0; 18894 long[] dalvikSubitemPss = opts.dumpDalvik ? new long[Debug.MemoryInfo.NUM_DVK_STATS] : 18895 EmptyArray.LONG; 18896 long[] dalvikSubitemSwapPss = opts.dumpDalvik ? new long[Debug.MemoryInfo.NUM_DVK_STATS] : 18897 EmptyArray.LONG; 18898 long otherPss = 0; 18899 long otherSwapPss = 0; 18900 long[] miscPss = new long[Debug.MemoryInfo.NUM_OTHER_STATS]; 18901 long[] miscSwapPss = new long[Debug.MemoryInfo.NUM_OTHER_STATS]; 18902 18903 long oomPss[] = new long[DUMP_MEM_OOM_LABEL.length]; 18904 long oomSwapPss[] = new long[DUMP_MEM_OOM_LABEL.length]; 18905 ArrayList<MemItem>[] oomProcs = (ArrayList<MemItem>[]) 18906 new ArrayList[DUMP_MEM_OOM_LABEL.length]; 18907 18908 long totalPss = 0; 18909 long totalSwapPss = 0; 18910 long cachedPss = 0; 18911 long cachedSwapPss = 0; 18912 boolean hasSwapPss = false; 18913 18914 Debug.MemoryInfo mi = null; 18915 for (int i = procs.size() - 1 ; i >= 0 ; i--) { 18916 final ProcessRecord r = procs.get(i); 18917 final IApplicationThread thread; 18918 final int pid; 18919 final int oomAdj; 18920 final boolean hasActivities; 18921 synchronized (this) { 18922 thread = r.thread; 18923 pid = r.pid; 18924 oomAdj = r.getSetAdjWithServices(); 18925 hasActivities = r.activities.size() > 0; 18926 } 18927 if (thread != null) { 18928 if (!opts.isCheckinRequest && opts.dumpDetails) { 18929 pw.println("\n** MEMINFO in pid " + pid + " [" + r.processName + "] **"); 18930 } 18931 if (mi == null) { 18932 mi = new Debug.MemoryInfo(); 18933 } 18934 final int reportType; 18935 final long startTime; 18936 final long endTime; 18937 if (opts.dumpDetails || (!brief && !opts.oomOnly)) { 18938 reportType = ProcessStats.ADD_PSS_EXTERNAL_SLOW; 18939 startTime = SystemClock.currentThreadTimeMillis(); 18940 Debug.getMemoryInfo(pid, mi); 18941 endTime = SystemClock.currentThreadTimeMillis(); 18942 hasSwapPss = mi.hasSwappedOutPss; 18943 } else { 18944 reportType = ProcessStats.ADD_PSS_EXTERNAL; 18945 startTime = SystemClock.currentThreadTimeMillis(); 18946 mi.dalvikPss = (int)Debug.getPss(pid, tmpLong, null); 18947 endTime = SystemClock.currentThreadTimeMillis(); 18948 mi.dalvikPrivateDirty = (int)tmpLong[0]; 18949 } 18950 if (opts.dumpDetails) { 18951 if (opts.localOnly) { 18952 ActivityThread.dumpMemInfoTable(pw, mi, opts.isCheckinRequest, opts.dumpFullDetails, 18953 opts.dumpDalvik, opts.dumpSummaryOnly, pid, r.processName, 0, 0, 0, 0, 0, 0); 18954 if (opts.isCheckinRequest) { 18955 pw.println(); 18956 } 18957 } else { 18958 pw.flush(); 18959 try { 18960 TransferPipe tp = new TransferPipe(); 18961 try { 18962 thread.dumpMemInfo(tp.getWriteFd(), 18963 mi, opts.isCheckinRequest, opts.dumpFullDetails, 18964 opts.dumpDalvik, opts.dumpSummaryOnly, opts.dumpUnreachable, innerArgs); 18965 tp.go(fd, opts.dumpUnreachable ? 30000 : 5000); 18966 } finally { 18967 tp.kill(); 18968 } 18969 } catch (IOException e) { 18970 if (!opts.isCheckinRequest) { 18971 pw.println("Got IoException! " + e); 18972 pw.flush(); 18973 } 18974 } catch (RemoteException e) { 18975 if (!opts.isCheckinRequest) { 18976 pw.println("Got RemoteException! " + e); 18977 pw.flush(); 18978 } 18979 } 18980 } 18981 } 18982 18983 final long myTotalPss = mi.getTotalPss(); 18984 final long myTotalUss = mi.getTotalUss(); 18985 final long myTotalRss = mi.getTotalRss(); 18986 final long myTotalSwapPss = mi.getTotalSwappedOutPss(); 18987 18988 synchronized (this) { 18989 if (r.thread != null && oomAdj == r.getSetAdjWithServices()) { 18990 // Record this for posterity if the process has been stable. 18991 r.baseProcessTracker.addPss(myTotalPss, myTotalUss, myTotalRss, true, 18992 reportType, endTime-startTime, r.pkgList); 18993 } 18994 } 18995 18996 if (!opts.isCheckinRequest && mi != null) { 18997 totalPss += myTotalPss; 18998 totalSwapPss += myTotalSwapPss; 18999 MemItem pssItem = new MemItem(r.processName + " (pid " + pid + 19000 (hasActivities ? " / activities)" : ")"), r.processName, myTotalPss, 19001 myTotalSwapPss, pid, hasActivities); 19002 procMems.add(pssItem); 19003 procMemsMap.put(pid, pssItem); 19004 19005 nativePss += mi.nativePss; 19006 nativeSwapPss += mi.nativeSwappedOutPss; 19007 dalvikPss += mi.dalvikPss; 19008 dalvikSwapPss += mi.dalvikSwappedOutPss; 19009 for (int j=0; j<dalvikSubitemPss.length; j++) { 19010 dalvikSubitemPss[j] += mi.getOtherPss(Debug.MemoryInfo.NUM_OTHER_STATS + j); 19011 dalvikSubitemSwapPss[j] += 19012 mi.getOtherSwappedOutPss(Debug.MemoryInfo.NUM_OTHER_STATS + j); 19013 } 19014 otherPss += mi.otherPss; 19015 otherSwapPss += mi.otherSwappedOutPss; 19016 for (int j=0; j<Debug.MemoryInfo.NUM_OTHER_STATS; j++) { 19017 long mem = mi.getOtherPss(j); 19018 miscPss[j] += mem; 19019 otherPss -= mem; 19020 mem = mi.getOtherSwappedOutPss(j); 19021 miscSwapPss[j] += mem; 19022 otherSwapPss -= mem; 19023 } 19024 19025 if (oomAdj >= ProcessList.CACHED_APP_MIN_ADJ) { 19026 cachedPss += myTotalPss; 19027 cachedSwapPss += myTotalSwapPss; 19028 } 19029 19030 for (int oomIndex=0; oomIndex<oomPss.length; oomIndex++) { 19031 if (oomIndex == (oomPss.length - 1) 19032 || (oomAdj >= DUMP_MEM_OOM_ADJ[oomIndex] 19033 && oomAdj < DUMP_MEM_OOM_ADJ[oomIndex + 1])) { 19034 oomPss[oomIndex] += myTotalPss; 19035 oomSwapPss[oomIndex] += myTotalSwapPss; 19036 if (oomProcs[oomIndex] == null) { 19037 oomProcs[oomIndex] = new ArrayList<MemItem>(); 19038 } 19039 oomProcs[oomIndex].add(pssItem); 19040 break; 19041 } 19042 } 19043 } 19044 } 19045 } 19046 19047 long nativeProcTotalPss = 0; 19048 19049 if (!opts.isCheckinRequest && procs.size() > 1 && !opts.packages) { 19050 // If we are showing aggregations, also look for native processes to 19051 // include so that our aggregations are more accurate. 19052 updateCpuStatsNow(); 19053 mi = null; 19054 synchronized (mProcessCpuTracker) { 19055 final int N = mProcessCpuTracker.countStats(); 19056 for (int i=0; i<N; i++) { 19057 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(i); 19058 if (st.vsize > 0 && procMemsMap.indexOfKey(st.pid) < 0) { 19059 if (mi == null) { 19060 mi = new Debug.MemoryInfo(); 19061 } 19062 if (!brief && !opts.oomOnly) { 19063 Debug.getMemoryInfo(st.pid, mi); 19064 } else { 19065 mi.nativePss = (int)Debug.getPss(st.pid, tmpLong, null); 19066 mi.nativePrivateDirty = (int)tmpLong[0]; 19067 } 19068 19069 final long myTotalPss = mi.getTotalPss(); 19070 final long myTotalSwapPss = mi.getTotalSwappedOutPss(); 19071 totalPss += myTotalPss; 19072 totalSwapPss += myTotalSwapPss; 19073 nativeProcTotalPss += myTotalPss; 19074 19075 MemItem pssItem = new MemItem(st.name + " (pid " + st.pid + ")", 19076 st.name, myTotalPss, mi.getSummaryTotalSwapPss(), st.pid, false); 19077 procMems.add(pssItem); 19078 19079 nativePss += mi.nativePss; 19080 nativeSwapPss += mi.nativeSwappedOutPss; 19081 dalvikPss += mi.dalvikPss; 19082 dalvikSwapPss += mi.dalvikSwappedOutPss; 19083 for (int j=0; j<dalvikSubitemPss.length; j++) { 19084 dalvikSubitemPss[j] += mi.getOtherPss(Debug.MemoryInfo.NUM_OTHER_STATS + j); 19085 dalvikSubitemSwapPss[j] += 19086 mi.getOtherSwappedOutPss(Debug.MemoryInfo.NUM_OTHER_STATS + j); 19087 } 19088 otherPss += mi.otherPss; 19089 otherSwapPss += mi.otherSwappedOutPss; 19090 for (int j=0; j<Debug.MemoryInfo.NUM_OTHER_STATS; j++) { 19091 long mem = mi.getOtherPss(j); 19092 miscPss[j] += mem; 19093 otherPss -= mem; 19094 mem = mi.getOtherSwappedOutPss(j); 19095 miscSwapPss[j] += mem; 19096 otherSwapPss -= mem; 19097 } 19098 oomPss[0] += myTotalPss; 19099 oomSwapPss[0] += myTotalSwapPss; 19100 if (oomProcs[0] == null) { 19101 oomProcs[0] = new ArrayList<MemItem>(); 19102 } 19103 oomProcs[0].add(pssItem); 19104 } 19105 } 19106 } 19107 19108 ArrayList<MemItem> catMems = new ArrayList<MemItem>(); 19109 19110 catMems.add(new MemItem("Native", "Native", nativePss, nativeSwapPss, -1)); 19111 final int dalvikId = -2; 19112 catMems.add(new MemItem("Dalvik", "Dalvik", dalvikPss, dalvikSwapPss, dalvikId)); 19113 catMems.add(new MemItem("Unknown", "Unknown", otherPss, otherSwapPss, -3)); 19114 for (int j=0; j<Debug.MemoryInfo.NUM_OTHER_STATS; j++) { 19115 String label = Debug.MemoryInfo.getOtherLabel(j); 19116 catMems.add(new MemItem(label, label, miscPss[j], miscSwapPss[j], j)); 19117 } 19118 if (dalvikSubitemPss.length > 0) { 19119 // Add dalvik subitems. 19120 for (MemItem memItem : catMems) { 19121 int memItemStart = 0, memItemEnd = 0; 19122 if (memItem.id == dalvikId) { 19123 memItemStart = Debug.MemoryInfo.OTHER_DVK_STAT_DALVIK_START; 19124 memItemEnd = Debug.MemoryInfo.OTHER_DVK_STAT_DALVIK_END; 19125 } else if (memItem.id == Debug.MemoryInfo.OTHER_DALVIK_OTHER) { 19126 memItemStart = Debug.MemoryInfo.OTHER_DVK_STAT_DALVIK_OTHER_START; 19127 memItemEnd = Debug.MemoryInfo.OTHER_DVK_STAT_DALVIK_OTHER_END; 19128 } else if (memItem.id == Debug.MemoryInfo.OTHER_DEX) { 19129 memItemStart = Debug.MemoryInfo.OTHER_DVK_STAT_DEX_START; 19130 memItemEnd = Debug.MemoryInfo.OTHER_DVK_STAT_DEX_END; 19131 } else if (memItem.id == Debug.MemoryInfo.OTHER_ART) { 19132 memItemStart = Debug.MemoryInfo.OTHER_DVK_STAT_ART_START; 19133 memItemEnd = Debug.MemoryInfo.OTHER_DVK_STAT_ART_END; 19134 } else { 19135 continue; // No subitems, continue. 19136 } 19137 memItem.subitems = new ArrayList<MemItem>(); 19138 for (int j=memItemStart; j<=memItemEnd; j++) { 19139 final String name = Debug.MemoryInfo.getOtherLabel( 19140 Debug.MemoryInfo.NUM_OTHER_STATS + j); 19141 memItem.subitems.add(new MemItem(name, name, dalvikSubitemPss[j], 19142 dalvikSubitemSwapPss[j], j)); 19143 } 19144 } 19145 } 19146 19147 ArrayList<MemItem> oomMems = new ArrayList<MemItem>(); 19148 for (int j=0; j<oomPss.length; j++) { 19149 if (oomPss[j] != 0) { 19150 String label = opts.isCompact ? DUMP_MEM_OOM_COMPACT_LABEL[j] 19151 : DUMP_MEM_OOM_LABEL[j]; 19152 MemItem item = new MemItem(label, label, oomPss[j], oomSwapPss[j], 19153 DUMP_MEM_OOM_ADJ[j]); 19154 item.subitems = oomProcs[j]; 19155 oomMems.add(item); 19156 } 19157 } 19158 19159 opts.dumpSwapPss = opts.dumpSwapPss && hasSwapPss && totalSwapPss != 0; 19160 if (!brief && !opts.oomOnly && !opts.isCompact) { 19161 pw.println(); 19162 pw.println("Total PSS by process:"); 19163 dumpMemItems(pw, " ", "proc", procMems, true, opts.isCompact, opts.dumpSwapPss); 19164 pw.println(); 19165 } 19166 if (!opts.isCompact) { 19167 pw.println("Total PSS by OOM adjustment:"); 19168 } 19169 dumpMemItems(pw, " ", "oom", oomMems, false, opts.isCompact, opts.dumpSwapPss); 19170 if (!brief && !opts.oomOnly) { 19171 PrintWriter out = categoryPw != null ? categoryPw : pw; 19172 if (!opts.isCompact) { 19173 out.println(); 19174 out.println("Total PSS by category:"); 19175 } 19176 dumpMemItems(out, " ", "cat", catMems, true, opts.isCompact, opts.dumpSwapPss); 19177 } 19178 if (!opts.isCompact) { 19179 pw.println(); 19180 } 19181 MemInfoReader memInfo = new MemInfoReader(); 19182 memInfo.readMemInfo(); 19183 if (nativeProcTotalPss > 0) { 19184 synchronized (this) { 19185 final long cachedKb = memInfo.getCachedSizeKb(); 19186 final long freeKb = memInfo.getFreeSizeKb(); 19187 final long zramKb = memInfo.getZramTotalSizeKb(); 19188 final long kernelKb = memInfo.getKernelUsedSizeKb(); 19189 EventLogTags.writeAmMeminfo(cachedKb*1024, freeKb*1024, zramKb*1024, 19190 kernelKb*1024, nativeProcTotalPss*1024); 19191 mProcessStats.addSysMemUsageLocked(cachedKb, freeKb, zramKb, kernelKb, 19192 nativeProcTotalPss); 19193 } 19194 } 19195 if (!brief) { 19196 if (!opts.isCompact) { 19197 pw.print("Total RAM: "); pw.print(stringifyKBSize(memInfo.getTotalSizeKb())); 19198 pw.print(" (status "); 19199 switch (mLastMemoryLevel) { 19200 case ProcessStats.ADJ_MEM_FACTOR_NORMAL: 19201 pw.println("normal)"); 19202 break; 19203 case ProcessStats.ADJ_MEM_FACTOR_MODERATE: 19204 pw.println("moderate)"); 19205 break; 19206 case ProcessStats.ADJ_MEM_FACTOR_LOW: 19207 pw.println("low)"); 19208 break; 19209 case ProcessStats.ADJ_MEM_FACTOR_CRITICAL: 19210 pw.println("critical)"); 19211 break; 19212 default: 19213 pw.print(mLastMemoryLevel); 19214 pw.println(")"); 19215 break; 19216 } 19217 pw.print(" Free RAM: "); 19218 pw.print(stringifyKBSize(cachedPss + memInfo.getCachedSizeKb() 19219 + memInfo.getFreeSizeKb())); 19220 pw.print(" ("); 19221 pw.print(stringifyKBSize(cachedPss)); 19222 pw.print(" cached pss + "); 19223 pw.print(stringifyKBSize(memInfo.getCachedSizeKb())); 19224 pw.print(" cached kernel + "); 19225 pw.print(stringifyKBSize(memInfo.getFreeSizeKb())); 19226 pw.println(" free)"); 19227 } else { 19228 pw.print("ram,"); pw.print(memInfo.getTotalSizeKb()); pw.print(","); 19229 pw.print(cachedPss + memInfo.getCachedSizeKb() 19230 + memInfo.getFreeSizeKb()); pw.print(","); 19231 pw.println(totalPss - cachedPss); 19232 } 19233 } 19234 long lostRAM = memInfo.getTotalSizeKb() - (totalPss - totalSwapPss) 19235 - memInfo.getFreeSizeKb() - memInfo.getCachedSizeKb() 19236 - memInfo.getKernelUsedSizeKb() - memInfo.getZramTotalSizeKb(); 19237 if (!opts.isCompact) { 19238 pw.print(" Used RAM: "); pw.print(stringifyKBSize(totalPss - cachedPss 19239 + memInfo.getKernelUsedSizeKb())); pw.print(" ("); 19240 pw.print(stringifyKBSize(totalPss - cachedPss)); pw.print(" used pss + "); 19241 pw.print(stringifyKBSize(memInfo.getKernelUsedSizeKb())); pw.print(" kernel)\n"); 19242 pw.print(" Lost RAM: "); pw.println(stringifyKBSize(lostRAM)); 19243 } else { 19244 pw.print("lostram,"); pw.println(lostRAM); 19245 } 19246 if (!brief) { 19247 if (memInfo.getZramTotalSizeKb() != 0) { 19248 if (!opts.isCompact) { 19249 pw.print(" ZRAM: "); 19250 pw.print(stringifyKBSize(memInfo.getZramTotalSizeKb())); 19251 pw.print(" physical used for "); 19252 pw.print(stringifyKBSize(memInfo.getSwapTotalSizeKb() 19253 - memInfo.getSwapFreeSizeKb())); 19254 pw.print(" in swap ("); 19255 pw.print(stringifyKBSize(memInfo.getSwapTotalSizeKb())); 19256 pw.println(" total swap)"); 19257 } else { 19258 pw.print("zram,"); pw.print(memInfo.getZramTotalSizeKb()); pw.print(","); 19259 pw.print(memInfo.getSwapTotalSizeKb()); pw.print(","); 19260 pw.println(memInfo.getSwapFreeSizeKb()); 19261 } 19262 } 19263 final long[] ksm = getKsmInfo(); 19264 if (!opts.isCompact) { 19265 if (ksm[KSM_SHARING] != 0 || ksm[KSM_SHARED] != 0 || ksm[KSM_UNSHARED] != 0 19266 || ksm[KSM_VOLATILE] != 0) { 19267 pw.print(" KSM: "); pw.print(stringifyKBSize(ksm[KSM_SHARING])); 19268 pw.print(" saved from shared "); 19269 pw.print(stringifyKBSize(ksm[KSM_SHARED])); 19270 pw.print(" "); pw.print(stringifyKBSize(ksm[KSM_UNSHARED])); 19271 pw.print(" unshared; "); 19272 pw.print(stringifyKBSize( 19273 ksm[KSM_VOLATILE])); pw.println(" volatile"); 19274 } 19275 pw.print(" Tuning: "); 19276 pw.print(ActivityManager.staticGetMemoryClass()); 19277 pw.print(" (large "); 19278 pw.print(ActivityManager.staticGetLargeMemoryClass()); 19279 pw.print("), oom "); 19280 pw.print(stringifySize( 19281 mProcessList.getMemLevel(ProcessList.CACHED_APP_MAX_ADJ), 1024)); 19282 pw.print(", restore limit "); 19283 pw.print(stringifyKBSize(mProcessList.getCachedRestoreThresholdKb())); 19284 if (ActivityManager.isLowRamDeviceStatic()) { 19285 pw.print(" (low-ram)"); 19286 } 19287 if (ActivityManager.isHighEndGfx()) { 19288 pw.print(" (high-end-gfx)"); 19289 } 19290 pw.println(); 19291 } else { 19292 pw.print("ksm,"); pw.print(ksm[KSM_SHARING]); pw.print(","); 19293 pw.print(ksm[KSM_SHARED]); pw.print(","); pw.print(ksm[KSM_UNSHARED]); 19294 pw.print(","); pw.println(ksm[KSM_VOLATILE]); 19295 pw.print("tuning,"); 19296 pw.print(ActivityManager.staticGetMemoryClass()); 19297 pw.print(','); 19298 pw.print(ActivityManager.staticGetLargeMemoryClass()); 19299 pw.print(','); 19300 pw.print(mProcessList.getMemLevel(ProcessList.CACHED_APP_MAX_ADJ)/1024); 19301 if (ActivityManager.isLowRamDeviceStatic()) { 19302 pw.print(",low-ram"); 19303 } 19304 if (ActivityManager.isHighEndGfx()) { 19305 pw.print(",high-end-gfx"); 19306 } 19307 pw.println(); 19308 } 19309 } 19310 } 19311 } 19312 19313 private final void dumpApplicationMemoryUsage(FileDescriptor fd, 19314 MemoryUsageDumpOptions opts, String[] innerArgs, boolean brief, 19315 ArrayList<ProcessRecord> procs) { 19316 final long uptimeMs = SystemClock.uptimeMillis(); 19317 final long realtimeMs = SystemClock.elapsedRealtime(); 19318 final long[] tmpLong = new long[1]; 19319 19320 if (procs == null) { 19321 // No Java processes. Maybe they want to print a native process. 19322 String proc = "N/A"; 19323 if (innerArgs.length > 0) { 19324 proc = innerArgs[0]; 19325 if (proc.charAt(0) != '-') { 19326 ArrayList<ProcessCpuTracker.Stats> nativeProcs 19327 = new ArrayList<ProcessCpuTracker.Stats>(); 19328 updateCpuStatsNow(); 19329 int findPid = -1; 19330 try { 19331 findPid = Integer.parseInt(innerArgs[0]); 19332 } catch (NumberFormatException e) { 19333 } 19334 synchronized (mProcessCpuTracker) { 19335 final int N = mProcessCpuTracker.countStats(); 19336 for (int i=0; i<N; i++) { 19337 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(i); 19338 if (st.pid == findPid || (st.baseName != null 19339 && st.baseName.equals(innerArgs[0]))) { 19340 nativeProcs.add(st); 19341 } 19342 } 19343 } 19344 if (nativeProcs.size() > 0) { 19345 ProtoOutputStream proto = new ProtoOutputStream(fd); 19346 19347 proto.write(MemInfoDumpProto.UPTIME_DURATION_MS, uptimeMs); 19348 proto.write(MemInfoDumpProto.ELAPSED_REALTIME_MS, realtimeMs); 19349 Debug.MemoryInfo mi = null; 19350 for (int i = nativeProcs.size() - 1 ; i >= 0 ; i--) { 19351 final ProcessCpuTracker.Stats r = nativeProcs.get(i); 19352 final int pid = r.pid; 19353 final long nToken = proto.start(MemInfoDumpProto.NATIVE_PROCESSES); 19354 19355 proto.write(MemInfoDumpProto.ProcessMemory.PID, pid); 19356 proto.write(MemInfoDumpProto.ProcessMemory.PROCESS_NAME, r.baseName); 19357 19358 if (mi == null) { 19359 mi = new Debug.MemoryInfo(); 19360 } 19361 if (opts.dumpDetails || (!brief && !opts.oomOnly)) { 19362 Debug.getMemoryInfo(pid, mi); 19363 } else { 19364 mi.dalvikPss = (int)Debug.getPss(pid, tmpLong, null); 19365 mi.dalvikPrivateDirty = (int)tmpLong[0]; 19366 } 19367 ActivityThread.dumpMemInfoTable(proto, mi, opts.dumpDalvik, 19368 opts.dumpSummaryOnly, 0, 0, 0, 0, 0, 0); 19369 19370 proto.end(nToken); 19371 } 19372 19373 proto.flush(); 19374 return; 19375 } 19376 } 19377 } 19378 Log.d(TAG, "No process found for: " + innerArgs[0]); 19379 return; 19380 } 19381 19382 if (!brief && !opts.oomOnly && (procs.size() == 1 || opts.isCheckinRequest || opts.packages)) { 19383 opts.dumpDetails = true; 19384 } 19385 19386 ProtoOutputStream proto = new ProtoOutputStream(fd); 19387 19388 proto.write(MemInfoDumpProto.UPTIME_DURATION_MS, uptimeMs); 19389 proto.write(MemInfoDumpProto.ELAPSED_REALTIME_MS, realtimeMs); 19390 19391 ArrayList<MemItem> procMems = new ArrayList<MemItem>(); 19392 final SparseArray<MemItem> procMemsMap = new SparseArray<MemItem>(); 19393 long nativePss = 0; 19394 long nativeSwapPss = 0; 19395 long dalvikPss = 0; 19396 long dalvikSwapPss = 0; 19397 long[] dalvikSubitemPss = opts.dumpDalvik ? new long[Debug.MemoryInfo.NUM_DVK_STATS] : 19398 EmptyArray.LONG; 19399 long[] dalvikSubitemSwapPss = opts.dumpDalvik ? new long[Debug.MemoryInfo.NUM_DVK_STATS] : 19400 EmptyArray.LONG; 19401 long otherPss = 0; 19402 long otherSwapPss = 0; 19403 long[] miscPss = new long[Debug.MemoryInfo.NUM_OTHER_STATS]; 19404 long[] miscSwapPss = new long[Debug.MemoryInfo.NUM_OTHER_STATS]; 19405 19406 long oomPss[] = new long[DUMP_MEM_OOM_LABEL.length]; 19407 long oomSwapPss[] = new long[DUMP_MEM_OOM_LABEL.length]; 19408 ArrayList<MemItem>[] oomProcs = (ArrayList<MemItem>[]) 19409 new ArrayList[DUMP_MEM_OOM_LABEL.length]; 19410 19411 long totalPss = 0; 19412 long totalSwapPss = 0; 19413 long cachedPss = 0; 19414 long cachedSwapPss = 0; 19415 boolean hasSwapPss = false; 19416 19417 Debug.MemoryInfo mi = null; 19418 for (int i = procs.size() - 1 ; i >= 0 ; i--) { 19419 final ProcessRecord r = procs.get(i); 19420 final IApplicationThread thread; 19421 final int pid; 19422 final int oomAdj; 19423 final boolean hasActivities; 19424 synchronized (this) { 19425 thread = r.thread; 19426 pid = r.pid; 19427 oomAdj = r.getSetAdjWithServices(); 19428 hasActivities = r.activities.size() > 0; 19429 } 19430 if (thread == null) { 19431 continue; 19432 } 19433 if (mi == null) { 19434 mi = new Debug.MemoryInfo(); 19435 } 19436 final int reportType; 19437 final long startTime; 19438 final long endTime; 19439 if (opts.dumpDetails || (!brief && !opts.oomOnly)) { 19440 reportType = ProcessStats.ADD_PSS_EXTERNAL_SLOW; 19441 startTime = SystemClock.currentThreadTimeMillis(); 19442 Debug.getMemoryInfo(pid, mi); 19443 endTime = SystemClock.currentThreadTimeMillis(); 19444 hasSwapPss = mi.hasSwappedOutPss; 19445 } else { 19446 reportType = ProcessStats.ADD_PSS_EXTERNAL; 19447 startTime = SystemClock.currentThreadTimeMillis(); 19448 mi.dalvikPss = (int) Debug.getPss(pid, tmpLong, null); 19449 endTime = SystemClock.currentThreadTimeMillis(); 19450 mi.dalvikPrivateDirty = (int) tmpLong[0]; 19451 } 19452 if (opts.dumpDetails) { 19453 if (opts.localOnly) { 19454 final long aToken = proto.start(MemInfoDumpProto.APP_PROCESSES); 19455 final long mToken = proto.start(MemInfoDumpProto.AppData.PROCESS_MEMORY); 19456 proto.write(MemInfoDumpProto.ProcessMemory.PID, pid); 19457 proto.write(MemInfoDumpProto.ProcessMemory.PROCESS_NAME, r.processName); 19458 ActivityThread.dumpMemInfoTable(proto, mi, opts.dumpDalvik, 19459 opts.dumpSummaryOnly, 0, 0, 0, 0, 0, 0); 19460 proto.end(mToken); 19461 proto.end(aToken); 19462 } else { 19463 try { 19464 ByteTransferPipe tp = new ByteTransferPipe(); 19465 try { 19466 thread.dumpMemInfoProto(tp.getWriteFd(), 19467 mi, opts.dumpFullDetails, opts.dumpDalvik, opts.dumpSummaryOnly, 19468 opts.dumpUnreachable, innerArgs); 19469 proto.write(MemInfoDumpProto.APP_PROCESSES, tp.get()); 19470 } finally { 19471 tp.kill(); 19472 } 19473 } catch (IOException e) { 19474 Log.e(TAG, "Got IOException!", e); 19475 } catch (RemoteException e) { 19476 Log.e(TAG, "Got RemoteException!", e); 19477 } 19478 } 19479 } 19480 19481 final long myTotalPss = mi.getTotalPss(); 19482 final long myTotalUss = mi.getTotalUss(); 19483 final long myTotalRss = mi.getTotalRss(); 19484 final long myTotalSwapPss = mi.getTotalSwappedOutPss(); 19485 19486 synchronized (this) { 19487 if (r.thread != null && oomAdj == r.getSetAdjWithServices()) { 19488 // Record this for posterity if the process has been stable. 19489 r.baseProcessTracker.addPss(myTotalPss, myTotalUss, myTotalRss, true, 19490 reportType, endTime-startTime, r.pkgList); 19491 } 19492 } 19493 19494 if (!opts.isCheckinRequest && mi != null) { 19495 totalPss += myTotalPss; 19496 totalSwapPss += myTotalSwapPss; 19497 MemItem pssItem = new MemItem(r.processName + " (pid " + pid + 19498 (hasActivities ? " / activities)" : ")"), r.processName, myTotalPss, 19499 myTotalSwapPss, pid, hasActivities); 19500 procMems.add(pssItem); 19501 procMemsMap.put(pid, pssItem); 19502 19503 nativePss += mi.nativePss; 19504 nativeSwapPss += mi.nativeSwappedOutPss; 19505 dalvikPss += mi.dalvikPss; 19506 dalvikSwapPss += mi.dalvikSwappedOutPss; 19507 for (int j=0; j<dalvikSubitemPss.length; j++) { 19508 dalvikSubitemPss[j] += mi.getOtherPss(Debug.MemoryInfo.NUM_OTHER_STATS + j); 19509 dalvikSubitemSwapPss[j] += 19510 mi.getOtherSwappedOutPss(Debug.MemoryInfo.NUM_OTHER_STATS + j); 19511 } 19512 otherPss += mi.otherPss; 19513 otherSwapPss += mi.otherSwappedOutPss; 19514 for (int j=0; j<Debug.MemoryInfo.NUM_OTHER_STATS; j++) { 19515 long mem = mi.getOtherPss(j); 19516 miscPss[j] += mem; 19517 otherPss -= mem; 19518 mem = mi.getOtherSwappedOutPss(j); 19519 miscSwapPss[j] += mem; 19520 otherSwapPss -= mem; 19521 } 19522 19523 if (oomAdj >= ProcessList.CACHED_APP_MIN_ADJ) { 19524 cachedPss += myTotalPss; 19525 cachedSwapPss += myTotalSwapPss; 19526 } 19527 19528 for (int oomIndex=0; oomIndex<oomPss.length; oomIndex++) { 19529 if (oomIndex == (oomPss.length - 1) 19530 || (oomAdj >= DUMP_MEM_OOM_ADJ[oomIndex] 19531 && oomAdj < DUMP_MEM_OOM_ADJ[oomIndex + 1])) { 19532 oomPss[oomIndex] += myTotalPss; 19533 oomSwapPss[oomIndex] += myTotalSwapPss; 19534 if (oomProcs[oomIndex] == null) { 19535 oomProcs[oomIndex] = new ArrayList<MemItem>(); 19536 } 19537 oomProcs[oomIndex].add(pssItem); 19538 break; 19539 } 19540 } 19541 } 19542 } 19543 19544 long nativeProcTotalPss = 0; 19545 19546 if (procs.size() > 1 && !opts.packages) { 19547 // If we are showing aggregations, also look for native processes to 19548 // include so that our aggregations are more accurate. 19549 updateCpuStatsNow(); 19550 mi = null; 19551 synchronized (mProcessCpuTracker) { 19552 final int N = mProcessCpuTracker.countStats(); 19553 for (int i=0; i<N; i++) { 19554 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(i); 19555 if (st.vsize > 0 && procMemsMap.indexOfKey(st.pid) < 0) { 19556 if (mi == null) { 19557 mi = new Debug.MemoryInfo(); 19558 } 19559 if (!brief && !opts.oomOnly) { 19560 Debug.getMemoryInfo(st.pid, mi); 19561 } else { 19562 mi.nativePss = (int)Debug.getPss(st.pid, tmpLong, null); 19563 mi.nativePrivateDirty = (int)tmpLong[0]; 19564 } 19565 19566 final long myTotalPss = mi.getTotalPss(); 19567 final long myTotalSwapPss = mi.getTotalSwappedOutPss(); 19568 totalPss += myTotalPss; 19569 nativeProcTotalPss += myTotalPss; 19570 19571 MemItem pssItem = new MemItem(st.name + " (pid " + st.pid + ")", 19572 st.name, myTotalPss, mi.getSummaryTotalSwapPss(), st.pid, false); 19573 procMems.add(pssItem); 19574 19575 nativePss += mi.nativePss; 19576 nativeSwapPss += mi.nativeSwappedOutPss; 19577 dalvikPss += mi.dalvikPss; 19578 dalvikSwapPss += mi.dalvikSwappedOutPss; 19579 for (int j=0; j<dalvikSubitemPss.length; j++) { 19580 dalvikSubitemPss[j] += mi.getOtherPss(Debug.MemoryInfo.NUM_OTHER_STATS + j); 19581 dalvikSubitemSwapPss[j] += 19582 mi.getOtherSwappedOutPss(Debug.MemoryInfo.NUM_OTHER_STATS + j); 19583 } 19584 otherPss += mi.otherPss; 19585 otherSwapPss += mi.otherSwappedOutPss; 19586 for (int j=0; j<Debug.MemoryInfo.NUM_OTHER_STATS; j++) { 19587 long mem = mi.getOtherPss(j); 19588 miscPss[j] += mem; 19589 otherPss -= mem; 19590 mem = mi.getOtherSwappedOutPss(j); 19591 miscSwapPss[j] += mem; 19592 otherSwapPss -= mem; 19593 } 19594 oomPss[0] += myTotalPss; 19595 oomSwapPss[0] += myTotalSwapPss; 19596 if (oomProcs[0] == null) { 19597 oomProcs[0] = new ArrayList<MemItem>(); 19598 } 19599 oomProcs[0].add(pssItem); 19600 } 19601 } 19602 } 19603 19604 ArrayList<MemItem> catMems = new ArrayList<MemItem>(); 19605 19606 catMems.add(new MemItem("Native", "Native", nativePss, nativeSwapPss, -1)); 19607 final int dalvikId = -2; 19608 catMems.add(new MemItem("Dalvik", "Dalvik", dalvikPss, dalvikSwapPss, dalvikId)); 19609 catMems.add(new MemItem("Unknown", "Unknown", otherPss, otherSwapPss, -3)); 19610 for (int j=0; j<Debug.MemoryInfo.NUM_OTHER_STATS; j++) { 19611 String label = Debug.MemoryInfo.getOtherLabel(j); 19612 catMems.add(new MemItem(label, label, miscPss[j], miscSwapPss[j], j)); 19613 } 19614 if (dalvikSubitemPss.length > 0) { 19615 // Add dalvik subitems. 19616 for (MemItem memItem : catMems) { 19617 int memItemStart = 0, memItemEnd = 0; 19618 if (memItem.id == dalvikId) { 19619 memItemStart = Debug.MemoryInfo.OTHER_DVK_STAT_DALVIK_START; 19620 memItemEnd = Debug.MemoryInfo.OTHER_DVK_STAT_DALVIK_END; 19621 } else if (memItem.id == Debug.MemoryInfo.OTHER_DALVIK_OTHER) { 19622 memItemStart = Debug.MemoryInfo.OTHER_DVK_STAT_DALVIK_OTHER_START; 19623 memItemEnd = Debug.MemoryInfo.OTHER_DVK_STAT_DALVIK_OTHER_END; 19624 } else if (memItem.id == Debug.MemoryInfo.OTHER_DEX) { 19625 memItemStart = Debug.MemoryInfo.OTHER_DVK_STAT_DEX_START; 19626 memItemEnd = Debug.MemoryInfo.OTHER_DVK_STAT_DEX_END; 19627 } else if (memItem.id == Debug.MemoryInfo.OTHER_ART) { 19628 memItemStart = Debug.MemoryInfo.OTHER_DVK_STAT_ART_START; 19629 memItemEnd = Debug.MemoryInfo.OTHER_DVK_STAT_ART_END; 19630 } else { 19631 continue; // No subitems, continue. 19632 } 19633 memItem.subitems = new ArrayList<MemItem>(); 19634 for (int j=memItemStart; j<=memItemEnd; j++) { 19635 final String name = Debug.MemoryInfo.getOtherLabel( 19636 Debug.MemoryInfo.NUM_OTHER_STATS + j); 19637 memItem.subitems.add(new MemItem(name, name, dalvikSubitemPss[j], 19638 dalvikSubitemSwapPss[j], j)); 19639 } 19640 } 19641 } 19642 19643 ArrayList<MemItem> oomMems = new ArrayList<MemItem>(); 19644 for (int j=0; j<oomPss.length; j++) { 19645 if (oomPss[j] != 0) { 19646 String label = opts.isCompact ? DUMP_MEM_OOM_COMPACT_LABEL[j] 19647 : DUMP_MEM_OOM_LABEL[j]; 19648 MemItem item = new MemItem(label, label, oomPss[j], oomSwapPss[j], 19649 DUMP_MEM_OOM_ADJ[j]); 19650 item.subitems = oomProcs[j]; 19651 oomMems.add(item); 19652 } 19653 } 19654 19655 opts.dumpSwapPss = opts.dumpSwapPss && hasSwapPss && totalSwapPss != 0; 19656 if (!opts.oomOnly) { 19657 dumpMemItems(proto, MemInfoDumpProto.TOTAL_PSS_BY_PROCESS, "proc", 19658 procMems, true, opts.dumpSwapPss); 19659 } 19660 dumpMemItems(proto, MemInfoDumpProto.TOTAL_PSS_BY_OOM_ADJUSTMENT, "oom", 19661 oomMems, false, opts.dumpSwapPss); 19662 if (!brief && !opts.oomOnly) { 19663 dumpMemItems(proto, MemInfoDumpProto.TOTAL_PSS_BY_CATEGORY, "cat", 19664 catMems, true, opts.dumpSwapPss); 19665 } 19666 MemInfoReader memInfo = new MemInfoReader(); 19667 memInfo.readMemInfo(); 19668 if (nativeProcTotalPss > 0) { 19669 synchronized (this) { 19670 final long cachedKb = memInfo.getCachedSizeKb(); 19671 final long freeKb = memInfo.getFreeSizeKb(); 19672 final long zramKb = memInfo.getZramTotalSizeKb(); 19673 final long kernelKb = memInfo.getKernelUsedSizeKb(); 19674 EventLogTags.writeAmMeminfo(cachedKb*1024, freeKb*1024, zramKb*1024, 19675 kernelKb*1024, nativeProcTotalPss*1024); 19676 mProcessStats.addSysMemUsageLocked(cachedKb, freeKb, zramKb, kernelKb, 19677 nativeProcTotalPss); 19678 } 19679 } 19680 if (!brief) { 19681 proto.write(MemInfoDumpProto.TOTAL_RAM_KB, memInfo.getTotalSizeKb()); 19682 proto.write(MemInfoDumpProto.STATUS, mLastMemoryLevel); 19683 proto.write(MemInfoDumpProto.CACHED_PSS_KB, cachedPss); 19684 proto.write(MemInfoDumpProto.CACHED_KERNEL_KB, memInfo.getCachedSizeKb()); 19685 proto.write(MemInfoDumpProto.FREE_KB, memInfo.getFreeSizeKb()); 19686 } 19687 long lostRAM = memInfo.getTotalSizeKb() - (totalPss - totalSwapPss) 19688 - memInfo.getFreeSizeKb() - memInfo.getCachedSizeKb() 19689 - memInfo.getKernelUsedSizeKb() - memInfo.getZramTotalSizeKb(); 19690 proto.write(MemInfoDumpProto.USED_PSS_KB, totalPss - cachedPss); 19691 proto.write(MemInfoDumpProto.USED_KERNEL_KB, memInfo.getKernelUsedSizeKb()); 19692 proto.write(MemInfoDumpProto.LOST_RAM_KB, lostRAM); 19693 if (!brief) { 19694 if (memInfo.getZramTotalSizeKb() != 0) { 19695 proto.write(MemInfoDumpProto.TOTAL_ZRAM_KB, memInfo.getZramTotalSizeKb()); 19696 proto.write(MemInfoDumpProto.ZRAM_PHYSICAL_USED_IN_SWAP_KB, 19697 memInfo.getSwapTotalSizeKb() - memInfo.getSwapFreeSizeKb()); 19698 proto.write(MemInfoDumpProto.TOTAL_ZRAM_SWAP_KB, memInfo.getSwapTotalSizeKb()); 19699 } 19700 final long[] ksm = getKsmInfo(); 19701 proto.write(MemInfoDumpProto.KSM_SHARING_KB, ksm[KSM_SHARING]); 19702 proto.write(MemInfoDumpProto.KSM_SHARED_KB, ksm[KSM_SHARED]); 19703 proto.write(MemInfoDumpProto.KSM_UNSHARED_KB, ksm[KSM_UNSHARED]); 19704 proto.write(MemInfoDumpProto.KSM_VOLATILE_KB, ksm[KSM_VOLATILE]); 19705 19706 proto.write(MemInfoDumpProto.TUNING_MB, ActivityManager.staticGetMemoryClass()); 19707 proto.write(MemInfoDumpProto.TUNING_LARGE_MB, ActivityManager.staticGetLargeMemoryClass()); 19708 proto.write(MemInfoDumpProto.OOM_KB, 19709 mProcessList.getMemLevel(ProcessList.CACHED_APP_MAX_ADJ) / 1024); 19710 proto.write(MemInfoDumpProto.RESTORE_LIMIT_KB, 19711 mProcessList.getCachedRestoreThresholdKb()); 19712 19713 proto.write(MemInfoDumpProto.IS_LOW_RAM_DEVICE, ActivityManager.isLowRamDeviceStatic()); 19714 proto.write(MemInfoDumpProto.IS_HIGH_END_GFX, ActivityManager.isHighEndGfx()); 19715 } 19716 } 19717 19718 proto.flush(); 19719 } 19720 19721 private void appendBasicMemEntry(StringBuilder sb, int oomAdj, int procState, long pss, 19722 long memtrack, String name) { 19723 sb.append(" "); 19724 sb.append(ProcessList.makeOomAdjString(oomAdj)); 19725 sb.append(' '); 19726 sb.append(ProcessList.makeProcStateString(procState)); 19727 sb.append(' '); 19728 ProcessList.appendRamKb(sb, pss); 19729 sb.append(": "); 19730 sb.append(name); 19731 if (memtrack > 0) { 19732 sb.append(" ("); 19733 sb.append(stringifyKBSize(memtrack)); 19734 sb.append(" memtrack)"); 19735 } 19736 } 19737 19738 private void appendMemInfo(StringBuilder sb, ProcessMemInfo mi) { 19739 appendBasicMemEntry(sb, mi.oomAdj, mi.procState, mi.pss, mi.memtrack, mi.name); 19740 sb.append(" (pid "); 19741 sb.append(mi.pid); 19742 sb.append(") "); 19743 sb.append(mi.adjType); 19744 sb.append('\n'); 19745 if (mi.adjReason != null) { 19746 sb.append(" "); 19747 sb.append(mi.adjReason); 19748 sb.append('\n'); 19749 } 19750 } 19751 19752 void reportMemUsage(ArrayList<ProcessMemInfo> memInfos) { 19753 final SparseArray<ProcessMemInfo> infoMap = new SparseArray<>(memInfos.size()); 19754 for (int i=0, N=memInfos.size(); i<N; i++) { 19755 ProcessMemInfo mi = memInfos.get(i); 19756 infoMap.put(mi.pid, mi); 19757 } 19758 updateCpuStatsNow(); 19759 long[] memtrackTmp = new long[1]; 19760 final List<ProcessCpuTracker.Stats> stats; 19761 // Get a list of Stats that have vsize > 0 19762 synchronized (mProcessCpuTracker) { 19763 stats = mProcessCpuTracker.getStats((st) -> { 19764 return st.vsize > 0; 19765 }); 19766 } 19767 final int statsCount = stats.size(); 19768 for (int i = 0; i < statsCount; i++) { 19769 ProcessCpuTracker.Stats st = stats.get(i); 19770 long pss = Debug.getPss(st.pid, null, memtrackTmp); 19771 if (pss > 0) { 19772 if (infoMap.indexOfKey(st.pid) < 0) { 19773 ProcessMemInfo mi = new ProcessMemInfo(st.name, st.pid, 19774 ProcessList.NATIVE_ADJ, -1, "native", null); 19775 mi.pss = pss; 19776 mi.memtrack = memtrackTmp[0]; 19777 memInfos.add(mi); 19778 } 19779 } 19780 } 19781 19782 long totalPss = 0; 19783 long totalMemtrack = 0; 19784 for (int i=0, N=memInfos.size(); i<N; i++) { 19785 ProcessMemInfo mi = memInfos.get(i); 19786 if (mi.pss == 0) { 19787 mi.pss = Debug.getPss(mi.pid, null, memtrackTmp); 19788 mi.memtrack = memtrackTmp[0]; 19789 } 19790 totalPss += mi.pss; 19791 totalMemtrack += mi.memtrack; 19792 } 19793 Collections.sort(memInfos, new Comparator<ProcessMemInfo>() { 19794 @Override public int compare(ProcessMemInfo lhs, ProcessMemInfo rhs) { 19795 if (lhs.oomAdj != rhs.oomAdj) { 19796 return lhs.oomAdj < rhs.oomAdj ? -1 : 1; 19797 } 19798 if (lhs.pss != rhs.pss) { 19799 return lhs.pss < rhs.pss ? 1 : -1; 19800 } 19801 return 0; 19802 } 19803 }); 19804 19805 StringBuilder tag = new StringBuilder(128); 19806 StringBuilder stack = new StringBuilder(128); 19807 tag.append("Low on memory -- "); 19808 appendMemBucket(tag, totalPss, "total", false); 19809 appendMemBucket(stack, totalPss, "total", true); 19810 19811 StringBuilder fullNativeBuilder = new StringBuilder(1024); 19812 StringBuilder shortNativeBuilder = new StringBuilder(1024); 19813 StringBuilder fullJavaBuilder = new StringBuilder(1024); 19814 19815 boolean firstLine = true; 19816 int lastOomAdj = Integer.MIN_VALUE; 19817 long extraNativeRam = 0; 19818 long extraNativeMemtrack = 0; 19819 long cachedPss = 0; 19820 for (int i=0, N=memInfos.size(); i<N; i++) { 19821 ProcessMemInfo mi = memInfos.get(i); 19822 19823 if (mi.oomAdj >= ProcessList.CACHED_APP_MIN_ADJ) { 19824 cachedPss += mi.pss; 19825 } 19826 19827 if (mi.oomAdj != ProcessList.NATIVE_ADJ 19828 && (mi.oomAdj < ProcessList.SERVICE_ADJ 19829 || mi.oomAdj == ProcessList.HOME_APP_ADJ 19830 || mi.oomAdj == ProcessList.PREVIOUS_APP_ADJ)) { 19831 if (lastOomAdj != mi.oomAdj) { 19832 lastOomAdj = mi.oomAdj; 19833 if (mi.oomAdj <= ProcessList.FOREGROUND_APP_ADJ) { 19834 tag.append(" / "); 19835 } 19836 if (mi.oomAdj >= ProcessList.FOREGROUND_APP_ADJ) { 19837 if (firstLine) { 19838 stack.append(":"); 19839 firstLine = false; 19840 } 19841 stack.append("\n\t at "); 19842 } else { 19843 stack.append("$"); 19844 } 19845 } else { 19846 tag.append(" "); 19847 stack.append("$"); 19848 } 19849 if (mi.oomAdj <= ProcessList.FOREGROUND_APP_ADJ) { 19850 appendMemBucket(tag, mi.pss, mi.name, false); 19851 } 19852 appendMemBucket(stack, mi.pss, mi.name, true); 19853 if (mi.oomAdj >= ProcessList.FOREGROUND_APP_ADJ 19854 && ((i+1) >= N || memInfos.get(i+1).oomAdj != lastOomAdj)) { 19855 stack.append("("); 19856 for (int k=0; k<DUMP_MEM_OOM_ADJ.length; k++) { 19857 if (DUMP_MEM_OOM_ADJ[k] == mi.oomAdj) { 19858 stack.append(DUMP_MEM_OOM_LABEL[k]); 19859 stack.append(":"); 19860 stack.append(DUMP_MEM_OOM_ADJ[k]); 19861 } 19862 } 19863 stack.append(")"); 19864 } 19865 } 19866 19867 appendMemInfo(fullNativeBuilder, mi); 19868 if (mi.oomAdj == ProcessList.NATIVE_ADJ) { 19869 // The short form only has native processes that are >= 512K. 19870 if (mi.pss >= 512) { 19871 appendMemInfo(shortNativeBuilder, mi); 19872 } else { 19873 extraNativeRam += mi.pss; 19874 extraNativeMemtrack += mi.memtrack; 19875 } 19876 } else { 19877 // Short form has all other details, but if we have collected RAM 19878 // from smaller native processes let's dump a summary of that. 19879 if (extraNativeRam > 0) { 19880 appendBasicMemEntry(shortNativeBuilder, ProcessList.NATIVE_ADJ, 19881 -1, extraNativeRam, extraNativeMemtrack, "(Other native)"); 19882 shortNativeBuilder.append('\n'); 19883 extraNativeRam = 0; 19884 } 19885 appendMemInfo(fullJavaBuilder, mi); 19886 } 19887 } 19888 19889 fullJavaBuilder.append(" "); 19890 ProcessList.appendRamKb(fullJavaBuilder, totalPss); 19891 fullJavaBuilder.append(": TOTAL"); 19892 if (totalMemtrack > 0) { 19893 fullJavaBuilder.append(" ("); 19894 fullJavaBuilder.append(stringifyKBSize(totalMemtrack)); 19895 fullJavaBuilder.append(" memtrack)"); 19896 } else { 19897 } 19898 fullJavaBuilder.append("\n"); 19899 19900 MemInfoReader memInfo = new MemInfoReader(); 19901 memInfo.readMemInfo(); 19902 final long[] infos = memInfo.getRawInfo(); 19903 19904 StringBuilder memInfoBuilder = new StringBuilder(1024); 19905 Debug.getMemInfo(infos); 19906 memInfoBuilder.append(" MemInfo: "); 19907 memInfoBuilder.append(stringifyKBSize(infos[Debug.MEMINFO_SLAB])).append(" slab, "); 19908 memInfoBuilder.append(stringifyKBSize(infos[Debug.MEMINFO_SHMEM])).append(" shmem, "); 19909 memInfoBuilder.append(stringifyKBSize( 19910 infos[Debug.MEMINFO_VM_ALLOC_USED])).append(" vm alloc, "); 19911 memInfoBuilder.append(stringifyKBSize( 19912 infos[Debug.MEMINFO_PAGE_TABLES])).append(" page tables "); 19913 memInfoBuilder.append(stringifyKBSize( 19914 infos[Debug.MEMINFO_KERNEL_STACK])).append(" kernel stack\n"); 19915 memInfoBuilder.append(" "); 19916 memInfoBuilder.append(stringifyKBSize(infos[Debug.MEMINFO_BUFFERS])).append(" buffers, "); 19917 memInfoBuilder.append(stringifyKBSize(infos[Debug.MEMINFO_CACHED])).append(" cached, "); 19918 memInfoBuilder.append(stringifyKBSize(infos[Debug.MEMINFO_MAPPED])).append(" mapped, "); 19919 memInfoBuilder.append(stringifyKBSize(infos[Debug.MEMINFO_FREE])).append(" free\n"); 19920 if (infos[Debug.MEMINFO_ZRAM_TOTAL] != 0) { 19921 memInfoBuilder.append(" ZRAM: "); 19922 memInfoBuilder.append(stringifyKBSize(infos[Debug.MEMINFO_ZRAM_TOTAL])); 19923 memInfoBuilder.append(" RAM, "); 19924 memInfoBuilder.append(stringifyKBSize(infos[Debug.MEMINFO_SWAP_TOTAL])); 19925 memInfoBuilder.append(" swap total, "); 19926 memInfoBuilder.append(stringifyKBSize(infos[Debug.MEMINFO_SWAP_FREE])); 19927 memInfoBuilder.append(" swap free\n"); 19928 } 19929 final long[] ksm = getKsmInfo(); 19930 if (ksm[KSM_SHARING] != 0 || ksm[KSM_SHARED] != 0 || ksm[KSM_UNSHARED] != 0 19931 || ksm[KSM_VOLATILE] != 0) { 19932 memInfoBuilder.append(" KSM: "); 19933 memInfoBuilder.append(stringifyKBSize(ksm[KSM_SHARING])); 19934 memInfoBuilder.append(" saved from shared "); 19935 memInfoBuilder.append(stringifyKBSize(ksm[KSM_SHARED])); 19936 memInfoBuilder.append("\n "); 19937 memInfoBuilder.append(stringifyKBSize(ksm[KSM_UNSHARED])); 19938 memInfoBuilder.append(" unshared; "); 19939 memInfoBuilder.append(stringifyKBSize(ksm[KSM_VOLATILE])); 19940 memInfoBuilder.append(" volatile\n"); 19941 } 19942 memInfoBuilder.append(" Free RAM: "); 19943 memInfoBuilder.append(stringifyKBSize(cachedPss + memInfo.getCachedSizeKb() 19944 + memInfo.getFreeSizeKb())); 19945 memInfoBuilder.append("\n"); 19946 memInfoBuilder.append(" Used RAM: "); 19947 memInfoBuilder.append(stringifyKBSize( 19948 totalPss - cachedPss + memInfo.getKernelUsedSizeKb())); 19949 memInfoBuilder.append("\n"); 19950 memInfoBuilder.append(" Lost RAM: "); 19951 memInfoBuilder.append(stringifyKBSize(memInfo.getTotalSizeKb() 19952 - totalPss - memInfo.getFreeSizeKb() - memInfo.getCachedSizeKb() 19953 - memInfo.getKernelUsedSizeKb() - memInfo.getZramTotalSizeKb())); 19954 memInfoBuilder.append("\n"); 19955 Slog.i(TAG, "Low on memory:"); 19956 Slog.i(TAG, shortNativeBuilder.toString()); 19957 Slog.i(TAG, fullJavaBuilder.toString()); 19958 Slog.i(TAG, memInfoBuilder.toString()); 19959 19960 StringBuilder dropBuilder = new StringBuilder(1024); 19961 /* 19962 StringWriter oomSw = new StringWriter(); 19963 PrintWriter oomPw = new FastPrintWriter(oomSw, false, 256); 19964 StringWriter catSw = new StringWriter(); 19965 PrintWriter catPw = new FastPrintWriter(catSw, false, 256); 19966 String[] emptyArgs = new String[] { }; 19967 dumpApplicationMemoryUsage(null, oomPw, " ", emptyArgs, true, catPw); 19968 oomPw.flush(); 19969 String oomString = oomSw.toString(); 19970 */ 19971 dropBuilder.append("Low on memory:"); 19972 dropBuilder.append(stack); 19973 dropBuilder.append('\n'); 19974 dropBuilder.append(fullNativeBuilder); 19975 dropBuilder.append(fullJavaBuilder); 19976 dropBuilder.append('\n'); 19977 dropBuilder.append(memInfoBuilder); 19978 dropBuilder.append('\n'); 19979 /* 19980 dropBuilder.append(oomString); 19981 dropBuilder.append('\n'); 19982 */ 19983 StringWriter catSw = new StringWriter(); 19984 synchronized (ActivityManagerService.this) { 19985 PrintWriter catPw = new FastPrintWriter(catSw, false, 256); 19986 String[] emptyArgs = new String[] { }; 19987 catPw.println(); 19988 dumpProcessesLocked(null, catPw, emptyArgs, 0, false, null, -1); 19989 catPw.println(); 19990 mServices.newServiceDumperLocked(null, catPw, emptyArgs, 0, 19991 false, null).dumpLocked(); 19992 catPw.println(); 19993 dumpActivitiesLocked(null, catPw, emptyArgs, 0, false, false, null); 19994 catPw.flush(); 19995 } 19996 dropBuilder.append(catSw.toString()); 19997 StatsLog.write(StatsLog.LOW_MEM_REPORTED); 19998 addErrorToDropBox("lowmem", null, "system_server", null, 19999 null, tag.toString(), dropBuilder.toString(), null, null); 20000 //Slog.i(TAG, "Sent to dropbox:"); 20001 //Slog.i(TAG, dropBuilder.toString()); 20002 synchronized (ActivityManagerService.this) { 20003 long now = SystemClock.uptimeMillis(); 20004 if (mLastMemUsageReportTime < now) { 20005 mLastMemUsageReportTime = now; 20006 } 20007 } 20008 } 20009 20010 /** 20011 * Searches array of arguments for the specified string 20012 * @param args array of argument strings 20013 * @param value value to search for 20014 * @return true if the value is contained in the array 20015 */ 20016 private static boolean scanArgs(String[] args, String value) { 20017 if (args != null) { 20018 for (String arg : args) { 20019 if (value.equals(arg)) { 20020 return true; 20021 } 20022 } 20023 } 20024 return false; 20025 } 20026 20027 private final boolean removeDyingProviderLocked(ProcessRecord proc, 20028 ContentProviderRecord cpr, boolean always) { 20029 final boolean inLaunching = mLaunchingProviders.contains(cpr); 20030 20031 if (!inLaunching || always) { 20032 synchronized (cpr) { 20033 cpr.launchingApp = null; 20034 cpr.notifyAll(); 20035 } 20036 mProviderMap.removeProviderByClass(cpr.name, UserHandle.getUserId(cpr.uid)); 20037 String names[] = cpr.info.authority.split(";"); 20038 for (int j = 0; j < names.length; j++) { 20039 mProviderMap.removeProviderByName(names[j], UserHandle.getUserId(cpr.uid)); 20040 } 20041 } 20042 20043 for (int i = cpr.connections.size() - 1; i >= 0; i--) { 20044 ContentProviderConnection conn = cpr.connections.get(i); 20045 if (conn.waiting) { 20046 // If this connection is waiting for the provider, then we don't 20047 // need to mess with its process unless we are always removing 20048 // or for some reason the provider is not currently launching. 20049 if (inLaunching && !always) { 20050 continue; 20051 } 20052 } 20053 ProcessRecord capp = conn.client; 20054 conn.dead = true; 20055 if (conn.stableCount > 0) { 20056 if (!capp.persistent && capp.thread != null 20057 && capp.pid != 0 20058 && capp.pid != MY_PID) { 20059 capp.kill("depends on provider " 20060 + cpr.name.flattenToShortString() 20061 + " in dying proc " + (proc != null ? proc.processName : "??") 20062 + " (adj " + (proc != null ? proc.setAdj : "??") + ")", true); 20063 } 20064 } else if (capp.thread != null && conn.provider.provider != null) { 20065 try { 20066 capp.thread.unstableProviderDied(conn.provider.provider.asBinder()); 20067 } catch (RemoteException e) { 20068 } 20069 // In the protocol here, we don't expect the client to correctly 20070 // clean up this connection, we'll just remove it. 20071 cpr.connections.remove(i); 20072 if (conn.client.conProviders.remove(conn)) { 20073 stopAssociationLocked(capp.uid, capp.processName, cpr.uid, cpr.name); 20074 } 20075 } 20076 } 20077 20078 if (inLaunching && always) { 20079 mLaunchingProviders.remove(cpr); 20080 } 20081 return inLaunching; 20082 } 20083 20084 /** 20085 * Main code for cleaning up a process when it has gone away. This is 20086 * called both as a result of the process dying, or directly when stopping 20087 * a process when running in single process mode. 20088 * 20089 * @return Returns true if the given process has been restarted, so the 20090 * app that was passed in must remain on the process lists. 20091 */ 20092 @GuardedBy("this") 20093 private final boolean cleanUpApplicationRecordLocked(ProcessRecord app, 20094 boolean restarting, boolean allowRestart, int index, boolean replacingPid) { 20095 if (index >= 0) { 20096 removeLruProcessLocked(app); 20097 ProcessList.remove(app.pid); 20098 } 20099 20100 mProcessesToGc.remove(app); 20101 mPendingPssProcesses.remove(app); 20102 ProcessList.abortNextPssTime(app.procStateMemTracker); 20103 20104 // Dismiss any open dialogs. 20105 if (app.crashDialog != null && !app.forceCrashReport) { 20106 app.crashDialog.dismiss(); 20107 app.crashDialog = null; 20108 } 20109 if (app.anrDialog != null) { 20110 app.anrDialog.dismiss(); 20111 app.anrDialog = null; 20112 } 20113 if (app.waitDialog != null) { 20114 app.waitDialog.dismiss(); 20115 app.waitDialog = null; 20116 } 20117 20118 app.crashing = false; 20119 app.notResponding = false; 20120 20121 app.resetPackageList(mProcessStats); 20122 app.unlinkDeathRecipient(); 20123 app.makeInactive(mProcessStats); 20124 app.waitingToKill = null; 20125 app.forcingToImportant = null; 20126 updateProcessForegroundLocked(app, false, false); 20127 app.foregroundActivities = false; 20128 app.hasShownUi = false; 20129 app.treatLikeActivity = false; 20130 app.hasAboveClient = false; 20131 app.hasClientActivities = false; 20132 20133 mServices.killServicesLocked(app, allowRestart); 20134 20135 boolean restart = false; 20136 20137 // Remove published content providers. 20138 for (int i = app.pubProviders.size() - 1; i >= 0; i--) { 20139 ContentProviderRecord cpr = app.pubProviders.valueAt(i); 20140 final boolean always = app.bad || !allowRestart; 20141 boolean inLaunching = removeDyingProviderLocked(app, cpr, always); 20142 if ((inLaunching || always) && cpr.hasConnectionOrHandle()) { 20143 // We left the provider in the launching list, need to 20144 // restart it. 20145 restart = true; 20146 } 20147 20148 cpr.provider = null; 20149 cpr.proc = null; 20150 } 20151 app.pubProviders.clear(); 20152 20153 // Take care of any launching providers waiting for this process. 20154 if (cleanupAppInLaunchingProvidersLocked(app, false)) { 20155 restart = true; 20156 } 20157 20158 // Unregister from connected content providers. 20159 if (!app.conProviders.isEmpty()) { 20160 for (int i = app.conProviders.size() - 1; i >= 0; i--) { 20161 ContentProviderConnection conn = app.conProviders.get(i); 20162 conn.provider.connections.remove(conn); 20163 stopAssociationLocked(app.uid, app.processName, conn.provider.uid, 20164 conn.provider.name); 20165 } 20166 app.conProviders.clear(); 20167 } 20168 20169 // At this point there may be remaining entries in mLaunchingProviders 20170 // where we were the only one waiting, so they are no longer of use. 20171 // Look for these and clean up if found. 20172 // XXX Commented out for now. Trying to figure out a way to reproduce 20173 // the actual situation to identify what is actually going on. 20174 if (false) { 20175 for (int i = mLaunchingProviders.size() - 1; i >= 0; i--) { 20176 ContentProviderRecord cpr = mLaunchingProviders.get(i); 20177 if (cpr.connections.size() <= 0 && !cpr.hasExternalProcessHandles()) { 20178 synchronized (cpr) { 20179 cpr.launchingApp = null; 20180 cpr.notifyAll(); 20181 } 20182 } 20183 } 20184 } 20185 20186 skipCurrentReceiverLocked(app); 20187 20188 // Unregister any receivers. 20189 for (int i = app.receivers.size() - 1; i >= 0; i--) { 20190 removeReceiverLocked(app.receivers.valueAt(i)); 20191 } 20192 app.receivers.clear(); 20193 20194 // If the app is undergoing backup, tell the backup manager about it 20195 if (mBackupTarget != null && app.pid == mBackupTarget.app.pid) { 20196 if (DEBUG_BACKUP || DEBUG_CLEANUP) Slog.d(TAG_CLEANUP, "App " 20197 + mBackupTarget.appInfo + " died during backup"); 20198 mHandler.post(new Runnable() { 20199 @Override 20200 public void run(){ 20201 try { 20202 IBackupManager bm = IBackupManager.Stub.asInterface( 20203 ServiceManager.getService(Context.BACKUP_SERVICE)); 20204 bm.agentDisconnected(app.info.packageName); 20205 } catch (RemoteException e) { 20206 // can't happen; backup manager is local 20207 } 20208 } 20209 }); 20210 } 20211 20212 for (int i = mPendingProcessChanges.size() - 1; i >= 0; i--) { 20213 ProcessChangeItem item = mPendingProcessChanges.get(i); 20214 if (app.pid > 0 && item.pid == app.pid) { 20215 mPendingProcessChanges.remove(i); 20216 mAvailProcessChanges.add(item); 20217 } 20218 } 20219 mUiHandler.obtainMessage(DISPATCH_PROCESS_DIED_UI_MSG, app.pid, app.info.uid, 20220 null).sendToTarget(); 20221 20222 // If the caller is restarting this app, then leave it in its 20223 // current lists and let the caller take care of it. 20224 if (restarting) { 20225 return false; 20226 } 20227 20228 if (!app.persistent || app.isolated) { 20229 if (DEBUG_PROCESSES || DEBUG_CLEANUP) Slog.v(TAG_CLEANUP, 20230 "Removing non-persistent process during cleanup: " + app); 20231 if (!replacingPid) { 20232 removeProcessNameLocked(app.processName, app.uid, app); 20233 } 20234 if (mHeavyWeightProcess == app) { 20235 mHandler.sendMessage(mHandler.obtainMessage(CANCEL_HEAVY_NOTIFICATION_MSG, 20236 mHeavyWeightProcess.userId, 0)); 20237 mHeavyWeightProcess = null; 20238 } 20239 } else if (!app.removed) { 20240 // This app is persistent, so we need to keep its record around. 20241 // If it is not already on the pending app list, add it there 20242 // and start a new process for it. 20243 if (mPersistentStartingProcesses.indexOf(app) < 0) { 20244 mPersistentStartingProcesses.add(app); 20245 restart = true; 20246 } 20247 } 20248 if ((DEBUG_PROCESSES || DEBUG_CLEANUP) && mProcessesOnHold.contains(app)) Slog.v( 20249 TAG_CLEANUP, "Clean-up removing on hold: " + app); 20250 mProcessesOnHold.remove(app); 20251 20252 if (app == mHomeProcess) { 20253 mHomeProcess = null; 20254 } 20255 if (app == mPreviousProcess) { 20256 mPreviousProcess = null; 20257 } 20258 20259 if (restart && !app.isolated) { 20260 // We have components that still need to be running in the 20261 // process, so re-launch it. 20262 if (index < 0) { 20263 ProcessList.remove(app.pid); 20264 } 20265 addProcessNameLocked(app); 20266 app.pendingStart = false; 20267 startProcessLocked(app, "restart", app.processName); 20268 return true; 20269 } else if (app.pid > 0 && app.pid != MY_PID) { 20270 // Goodbye! 20271 boolean removed; 20272 synchronized (mPidsSelfLocked) { 20273 mPidsSelfLocked.remove(app.pid); 20274 mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app); 20275 } 20276 mBatteryStatsService.noteProcessFinish(app.processName, app.info.uid); 20277 if (app.isolated) { 20278 mBatteryStatsService.removeIsolatedUid(app.uid, app.info.uid); 20279 } 20280 app.setPid(0); 20281 } 20282 return false; 20283 } 20284 20285 boolean checkAppInLaunchingProvidersLocked(ProcessRecord app) { 20286 for (int i = mLaunchingProviders.size() - 1; i >= 0; i--) { 20287 ContentProviderRecord cpr = mLaunchingProviders.get(i); 20288 if (cpr.launchingApp == app) { 20289 return true; 20290 } 20291 } 20292 return false; 20293 } 20294 20295 boolean cleanupAppInLaunchingProvidersLocked(ProcessRecord app, boolean alwaysBad) { 20296 // Look through the content providers we are waiting to have launched, 20297 // and if any run in this process then either schedule a restart of 20298 // the process or kill the client waiting for it if this process has 20299 // gone bad. 20300 boolean restart = false; 20301 for (int i = mLaunchingProviders.size() - 1; i >= 0; i--) { 20302 ContentProviderRecord cpr = mLaunchingProviders.get(i); 20303 if (cpr.launchingApp == app) { 20304 if (!alwaysBad && !app.bad && cpr.hasConnectionOrHandle()) { 20305 restart = true; 20306 } else { 20307 removeDyingProviderLocked(app, cpr, true); 20308 } 20309 } 20310 } 20311 return restart; 20312 } 20313 20314 // ========================================================= 20315 // SERVICES 20316 // ========================================================= 20317 20318 @Override 20319 public List<ActivityManager.RunningServiceInfo> getServices(int maxNum, int flags) { 20320 enforceNotIsolatedCaller("getServices"); 20321 20322 final int callingUid = Binder.getCallingUid(); 20323 final boolean canInteractAcrossUsers = (ActivityManager.checkUidPermission( 20324 INTERACT_ACROSS_USERS_FULL, callingUid) == PERMISSION_GRANTED); 20325 final boolean allowed = isGetTasksAllowed("getServices", Binder.getCallingPid(), 20326 callingUid); 20327 synchronized (this) { 20328 return mServices.getRunningServiceInfoLocked(maxNum, flags, callingUid, 20329 allowed, canInteractAcrossUsers); 20330 } 20331 } 20332 20333 @Override 20334 public PendingIntent getRunningServiceControlPanel(ComponentName name) { 20335 enforceNotIsolatedCaller("getRunningServiceControlPanel"); 20336 synchronized (this) { 20337 return mServices.getRunningServiceControlPanelLocked(name); 20338 } 20339 } 20340 20341 @Override 20342 public ComponentName startService(IApplicationThread caller, Intent service, 20343 String resolvedType, boolean requireForeground, String callingPackage, int userId) 20344 throws TransactionTooLargeException { 20345 enforceNotIsolatedCaller("startService"); 20346 // Refuse possible leaked file descriptors 20347 if (service != null && service.hasFileDescriptors() == true) { 20348 throw new IllegalArgumentException("File descriptors passed in Intent"); 20349 } 20350 20351 if (callingPackage == null) { 20352 throw new IllegalArgumentException("callingPackage cannot be null"); 20353 } 20354 20355 if (DEBUG_SERVICE) Slog.v(TAG_SERVICE, 20356 "*** startService: " + service + " type=" + resolvedType + " fg=" + requireForeground); 20357 synchronized(this) { 20358 final int callingPid = Binder.getCallingPid(); 20359 final int callingUid = Binder.getCallingUid(); 20360 final long origId = Binder.clearCallingIdentity(); 20361 ComponentName res; 20362 try { 20363 res = mServices.startServiceLocked(caller, service, 20364 resolvedType, callingPid, callingUid, 20365 requireForeground, callingPackage, userId); 20366 } finally { 20367 Binder.restoreCallingIdentity(origId); 20368 } 20369 return res; 20370 } 20371 } 20372 20373 ComponentName startServiceInPackage(int uid, Intent service, String resolvedType, 20374 boolean fgRequired, String callingPackage, int userId) 20375 throws TransactionTooLargeException { 20376 synchronized(this) { 20377 if (DEBUG_SERVICE) Slog.v(TAG_SERVICE, 20378 "startServiceInPackage: " + service + " type=" + resolvedType); 20379 final long origId = Binder.clearCallingIdentity(); 20380 ComponentName res; 20381 try { 20382 res = mServices.startServiceLocked(null, service, 20383 resolvedType, -1, uid, fgRequired, callingPackage, userId); 20384 } finally { 20385 Binder.restoreCallingIdentity(origId); 20386 } 20387 return res; 20388 } 20389 } 20390 20391 @Override 20392 public int stopService(IApplicationThread caller, Intent service, 20393 String resolvedType, int userId) { 20394 enforceNotIsolatedCaller("stopService"); 20395 // Refuse possible leaked file descriptors 20396 if (service != null && service.hasFileDescriptors() == true) { 20397 throw new IllegalArgumentException("File descriptors passed in Intent"); 20398 } 20399 20400 synchronized(this) { 20401 return mServices.stopServiceLocked(caller, service, resolvedType, userId); 20402 } 20403 } 20404 20405 @Override 20406 public IBinder peekService(Intent service, String resolvedType, String callingPackage) { 20407 enforceNotIsolatedCaller("peekService"); 20408 // Refuse possible leaked file descriptors 20409 if (service != null && service.hasFileDescriptors() == true) { 20410 throw new IllegalArgumentException("File descriptors passed in Intent"); 20411 } 20412 20413 if (callingPackage == null) { 20414 throw new IllegalArgumentException("callingPackage cannot be null"); 20415 } 20416 20417 synchronized(this) { 20418 return mServices.peekServiceLocked(service, resolvedType, callingPackage); 20419 } 20420 } 20421 20422 @Override 20423 public boolean stopServiceToken(ComponentName className, IBinder token, 20424 int startId) { 20425 synchronized(this) { 20426 return mServices.stopServiceTokenLocked(className, token, startId); 20427 } 20428 } 20429 20430 @Override 20431 public void setServiceForeground(ComponentName className, IBinder token, 20432 int id, Notification notification, int flags) { 20433 synchronized(this) { 20434 mServices.setServiceForegroundLocked(className, token, id, notification, flags); 20435 } 20436 } 20437 20438 @Override 20439 public int handleIncomingUser(int callingPid, int callingUid, int userId, boolean allowAll, 20440 boolean requireFull, String name, String callerPackage) { 20441 return mUserController.handleIncomingUser(callingPid, callingUid, userId, allowAll, 20442 requireFull ? ALLOW_FULL_ONLY : ALLOW_NON_FULL, name, callerPackage); 20443 } 20444 20445 boolean isSingleton(String componentProcessName, ApplicationInfo aInfo, 20446 String className, int flags) { 20447 boolean result = false; 20448 // For apps that don't have pre-defined UIDs, check for permission 20449 if (UserHandle.getAppId(aInfo.uid) >= FIRST_APPLICATION_UID) { 20450 if ((flags & ServiceInfo.FLAG_SINGLE_USER) != 0) { 20451 if (ActivityManager.checkUidPermission( 20452 INTERACT_ACROSS_USERS, 20453 aInfo.uid) != PackageManager.PERMISSION_GRANTED) { 20454 ComponentName comp = new ComponentName(aInfo.packageName, className); 20455 String msg = "Permission Denial: Component " + comp.flattenToShortString() 20456 + " requests FLAG_SINGLE_USER, but app does not hold " 20457 + INTERACT_ACROSS_USERS; 20458 Slog.w(TAG, msg); 20459 throw new SecurityException(msg); 20460 } 20461 // Permission passed 20462 result = true; 20463 } 20464 } else if ("system".equals(componentProcessName)) { 20465 result = true; 20466 } else if ((flags & ServiceInfo.FLAG_SINGLE_USER) != 0) { 20467 // Phone app and persistent apps are allowed to export singleuser providers. 20468 result = UserHandle.isSameApp(aInfo.uid, PHONE_UID) 20469 || (aInfo.flags & ApplicationInfo.FLAG_PERSISTENT) != 0; 20470 } 20471 if (DEBUG_MU) Slog.v(TAG_MU, 20472 "isSingleton(" + componentProcessName + ", " + aInfo + ", " + className + ", 0x" 20473 + Integer.toHexString(flags) + ") = " + result); 20474 return result; 20475 } 20476 20477 /** 20478 * Checks to see if the caller is in the same app as the singleton 20479 * component, or the component is in a special app. It allows special apps 20480 * to export singleton components but prevents exporting singleton 20481 * components for regular apps. 20482 */ 20483 boolean isValidSingletonCall(int callingUid, int componentUid) { 20484 int componentAppId = UserHandle.getAppId(componentUid); 20485 return UserHandle.isSameApp(callingUid, componentUid) 20486 || componentAppId == SYSTEM_UID 20487 || componentAppId == PHONE_UID 20488 || ActivityManager.checkUidPermission(INTERACT_ACROSS_USERS_FULL, componentUid) 20489 == PackageManager.PERMISSION_GRANTED; 20490 } 20491 20492 public int bindService(IApplicationThread caller, IBinder token, Intent service, 20493 String resolvedType, IServiceConnection connection, int flags, String callingPackage, 20494 int userId) throws TransactionTooLargeException { 20495 enforceNotIsolatedCaller("bindService"); 20496 20497 // Refuse possible leaked file descriptors 20498 if (service != null && service.hasFileDescriptors() == true) { 20499 throw new IllegalArgumentException("File descriptors passed in Intent"); 20500 } 20501 20502 if (callingPackage == null) { 20503 throw new IllegalArgumentException("callingPackage cannot be null"); 20504 } 20505 20506 synchronized(this) { 20507 return mServices.bindServiceLocked(caller, token, service, 20508 resolvedType, connection, flags, callingPackage, userId); 20509 } 20510 } 20511 20512 public boolean unbindService(IServiceConnection connection) { 20513 synchronized (this) { 20514 return mServices.unbindServiceLocked(connection); 20515 } 20516 } 20517 20518 public void publishService(IBinder token, Intent intent, IBinder service) { 20519 // Refuse possible leaked file descriptors 20520 if (intent != null && intent.hasFileDescriptors() == true) { 20521 throw new IllegalArgumentException("File descriptors passed in Intent"); 20522 } 20523 20524 synchronized(this) { 20525 if (!(token instanceof ServiceRecord)) { 20526 throw new IllegalArgumentException("Invalid service token"); 20527 } 20528 mServices.publishServiceLocked((ServiceRecord)token, intent, service); 20529 } 20530 } 20531 20532 public void unbindFinished(IBinder token, Intent intent, boolean doRebind) { 20533 // Refuse possible leaked file descriptors 20534 if (intent != null && intent.hasFileDescriptors() == true) { 20535 throw new IllegalArgumentException("File descriptors passed in Intent"); 20536 } 20537 20538 synchronized(this) { 20539 mServices.unbindFinishedLocked((ServiceRecord)token, intent, doRebind); 20540 } 20541 } 20542 20543 public void serviceDoneExecuting(IBinder token, int type, int startId, int res) { 20544 synchronized(this) { 20545 if (!(token instanceof ServiceRecord)) { 20546 Slog.e(TAG, "serviceDoneExecuting: Invalid service token=" + token); 20547 throw new IllegalArgumentException("Invalid service token"); 20548 } 20549 mServices.serviceDoneExecutingLocked((ServiceRecord)token, type, startId, res); 20550 } 20551 } 20552 20553 // ========================================================= 20554 // BACKUP AND RESTORE 20555 // ========================================================= 20556 20557 // Cause the target app to be launched if necessary and its backup agent 20558 // instantiated. The backup agent will invoke backupAgentCreated() on the 20559 // activity manager to announce its creation. 20560 public boolean bindBackupAgent(String packageName, int backupMode, int userId) { 20561 if (DEBUG_BACKUP) Slog.v(TAG, "bindBackupAgent: app=" + packageName + " mode=" + backupMode); 20562 enforceCallingPermission("android.permission.CONFIRM_FULL_BACKUP", "bindBackupAgent"); 20563 20564 IPackageManager pm = AppGlobals.getPackageManager(); 20565 ApplicationInfo app = null; 20566 try { 20567 app = pm.getApplicationInfo(packageName, STOCK_PM_FLAGS, userId); 20568 } catch (RemoteException e) { 20569 // can't happen; package manager is process-local 20570 } 20571 if (app == null) { 20572 Slog.w(TAG, "Unable to bind backup agent for " + packageName); 20573 return false; 20574 } 20575 20576 int oldBackupUid; 20577 int newBackupUid; 20578 20579 synchronized(this) { 20580 // !!! TODO: currently no check here that we're already bound 20581 BatteryStatsImpl.Uid.Pkg.Serv ss = null; 20582 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 20583 synchronized (stats) { 20584 ss = stats.getServiceStatsLocked(app.uid, app.packageName, app.name); 20585 } 20586 20587 // Backup agent is now in use, its package can't be stopped. 20588 try { 20589 AppGlobals.getPackageManager().setPackageStoppedState( 20590 app.packageName, false, UserHandle.getUserId(app.uid)); 20591 } catch (RemoteException e) { 20592 } catch (IllegalArgumentException e) { 20593 Slog.w(TAG, "Failed trying to unstop package " 20594 + app.packageName + ": " + e); 20595 } 20596 20597 BackupRecord r = new BackupRecord(ss, app, backupMode); 20598 ComponentName hostingName = 20599 (backupMode == ApplicationThreadConstants.BACKUP_MODE_INCREMENTAL) 20600 ? new ComponentName(app.packageName, app.backupAgentName) 20601 : new ComponentName("android", "FullBackupAgent"); 20602 // startProcessLocked() returns existing proc's record if it's already running 20603 ProcessRecord proc = startProcessLocked(app.processName, app, 20604 false, 0, "backup", hostingName, false, false, false); 20605 if (proc == null) { 20606 Slog.e(TAG, "Unable to start backup agent process " + r); 20607 return false; 20608 } 20609 20610 // If the app is a regular app (uid >= 10000) and not the system server or phone 20611 // process, etc, then mark it as being in full backup so that certain calls to the 20612 // process can be blocked. This is not reset to false anywhere because we kill the 20613 // process after the full backup is done and the ProcessRecord will vaporize anyway. 20614 if (UserHandle.isApp(app.uid) && 20615 backupMode == ApplicationThreadConstants.BACKUP_MODE_FULL) { 20616 proc.inFullBackup = true; 20617 } 20618 r.app = proc; 20619 oldBackupUid = mBackupTarget != null ? mBackupTarget.appInfo.uid : -1; 20620 newBackupUid = proc.inFullBackup ? r.appInfo.uid : -1; 20621 mBackupTarget = r; 20622 mBackupAppName = app.packageName; 20623 20624 // Try not to kill the process during backup 20625 updateOomAdjLocked(proc, true); 20626 20627 // If the process is already attached, schedule the creation of the backup agent now. 20628 // If it is not yet live, this will be done when it attaches to the framework. 20629 if (proc.thread != null) { 20630 if (DEBUG_BACKUP) Slog.v(TAG_BACKUP, "Agent proc already running: " + proc); 20631 try { 20632 proc.thread.scheduleCreateBackupAgent(app, 20633 compatibilityInfoForPackageLocked(app), backupMode); 20634 } catch (RemoteException e) { 20635 // Will time out on the backup manager side 20636 } 20637 } else { 20638 if (DEBUG_BACKUP) Slog.v(TAG_BACKUP, "Agent proc not running, waiting for attach"); 20639 } 20640 // Invariants: at this point, the target app process exists and the application 20641 // is either already running or in the process of coming up. mBackupTarget and 20642 // mBackupAppName describe the app, so that when it binds back to the AM we 20643 // know that it's scheduled for a backup-agent operation. 20644 } 20645 20646 JobSchedulerInternal js = LocalServices.getService(JobSchedulerInternal.class); 20647 if (oldBackupUid != -1) { 20648 js.removeBackingUpUid(oldBackupUid); 20649 } 20650 if (newBackupUid != -1) { 20651 js.addBackingUpUid(newBackupUid); 20652 } 20653 20654 return true; 20655 } 20656 20657 @Override 20658 public void clearPendingBackup() { 20659 if (DEBUG_BACKUP) Slog.v(TAG_BACKUP, "clearPendingBackup"); 20660 enforceCallingPermission("android.permission.BACKUP", "clearPendingBackup"); 20661 20662 synchronized (this) { 20663 mBackupTarget = null; 20664 mBackupAppName = null; 20665 } 20666 20667 JobSchedulerInternal js = LocalServices.getService(JobSchedulerInternal.class); 20668 js.clearAllBackingUpUids(); 20669 } 20670 20671 // A backup agent has just come up 20672 public void backupAgentCreated(String agentPackageName, IBinder agent) { 20673 if (DEBUG_BACKUP) Slog.v(TAG_BACKUP, "backupAgentCreated: " + agentPackageName 20674 + " = " + agent); 20675 20676 synchronized(this) { 20677 if (!agentPackageName.equals(mBackupAppName)) { 20678 Slog.e(TAG, "Backup agent created for " + agentPackageName + " but not requested!"); 20679 return; 20680 } 20681 } 20682 20683 long oldIdent = Binder.clearCallingIdentity(); 20684 try { 20685 IBackupManager bm = IBackupManager.Stub.asInterface( 20686 ServiceManager.getService(Context.BACKUP_SERVICE)); 20687 bm.agentConnected(agentPackageName, agent); 20688 } catch (RemoteException e) { 20689 // can't happen; the backup manager service is local 20690 } catch (Exception e) { 20691 Slog.w(TAG, "Exception trying to deliver BackupAgent binding: "); 20692 e.printStackTrace(); 20693 } finally { 20694 Binder.restoreCallingIdentity(oldIdent); 20695 } 20696 } 20697 20698 // done with this agent 20699 public void unbindBackupAgent(ApplicationInfo appInfo) { 20700 if (DEBUG_BACKUP) Slog.v(TAG_BACKUP, "unbindBackupAgent: " + appInfo); 20701 if (appInfo == null) { 20702 Slog.w(TAG, "unbind backup agent for null app"); 20703 return; 20704 } 20705 20706 int oldBackupUid; 20707 20708 synchronized(this) { 20709 try { 20710 if (mBackupAppName == null) { 20711 Slog.w(TAG, "Unbinding backup agent with no active backup"); 20712 return; 20713 } 20714 20715 if (!mBackupAppName.equals(appInfo.packageName)) { 20716 Slog.e(TAG, "Unbind of " + appInfo + " but is not the current backup target"); 20717 return; 20718 } 20719 20720 // Not backing this app up any more; reset its OOM adjustment 20721 final ProcessRecord proc = mBackupTarget.app; 20722 updateOomAdjLocked(proc, true); 20723 proc.inFullBackup = false; 20724 20725 oldBackupUid = mBackupTarget != null ? mBackupTarget.appInfo.uid : -1; 20726 20727 // If the app crashed during backup, 'thread' will be null here 20728 if (proc.thread != null) { 20729 try { 20730 proc.thread.scheduleDestroyBackupAgent(appInfo, 20731 compatibilityInfoForPackageLocked(appInfo)); 20732 } catch (Exception e) { 20733 Slog.e(TAG, "Exception when unbinding backup agent:"); 20734 e.printStackTrace(); 20735 } 20736 } 20737 } finally { 20738 mBackupTarget = null; 20739 mBackupAppName = null; 20740 } 20741 } 20742 20743 if (oldBackupUid != -1) { 20744 JobSchedulerInternal js = LocalServices.getService(JobSchedulerInternal.class); 20745 js.removeBackingUpUid(oldBackupUid); 20746 } 20747 } 20748 20749 // ========================================================= 20750 // BROADCASTS 20751 // ========================================================= 20752 20753 private boolean isInstantApp(ProcessRecord record, @Nullable String callerPackage, int uid) { 20754 if (UserHandle.getAppId(uid) < FIRST_APPLICATION_UID) { 20755 return false; 20756 } 20757 // Easy case -- we have the app's ProcessRecord. 20758 if (record != null) { 20759 return record.info.isInstantApp(); 20760 } 20761 // Otherwise check with PackageManager. 20762 IPackageManager pm = AppGlobals.getPackageManager(); 20763 try { 20764 if (callerPackage == null) { 20765 final String[] packageNames = pm.getPackagesForUid(uid); 20766 if (packageNames == null || packageNames.length == 0) { 20767 throw new IllegalArgumentException("Unable to determine caller package name"); 20768 } 20769 // Instant Apps can't use shared uids, so its safe to only check the first package. 20770 callerPackage = packageNames[0]; 20771 } 20772 mAppOpsService.checkPackage(uid, callerPackage); 20773 return pm.isInstantApp(callerPackage, UserHandle.getUserId(uid)); 20774 } catch (RemoteException e) { 20775 Slog.e(TAG, "Error looking up if " + callerPackage + " is an instant app.", e); 20776 return true; 20777 } 20778 } 20779 20780 boolean isPendingBroadcastProcessLocked(int pid) { 20781 return mFgBroadcastQueue.isPendingBroadcastProcessLocked(pid) 20782 || mBgBroadcastQueue.isPendingBroadcastProcessLocked(pid); 20783 } 20784 20785 void skipPendingBroadcastLocked(int pid) { 20786 Slog.w(TAG, "Unattached app died before broadcast acknowledged, skipping"); 20787 for (BroadcastQueue queue : mBroadcastQueues) { 20788 queue.skipPendingBroadcastLocked(pid); 20789 } 20790 } 20791 20792 // The app just attached; send any pending broadcasts that it should receive 20793 boolean sendPendingBroadcastsLocked(ProcessRecord app) { 20794 boolean didSomething = false; 20795 for (BroadcastQueue queue : mBroadcastQueues) { 20796 didSomething |= queue.sendPendingBroadcastsLocked(app); 20797 } 20798 return didSomething; 20799 } 20800 20801 public Intent registerReceiver(IApplicationThread caller, String callerPackage, 20802 IIntentReceiver receiver, IntentFilter filter, String permission, int userId, 20803 int flags) { 20804 enforceNotIsolatedCaller("registerReceiver"); 20805 ArrayList<Intent> stickyIntents = null; 20806 ProcessRecord callerApp = null; 20807 final boolean visibleToInstantApps 20808 = (flags & Context.RECEIVER_VISIBLE_TO_INSTANT_APPS) != 0; 20809 int callingUid; 20810 int callingPid; 20811 boolean instantApp; 20812 synchronized(this) { 20813 if (caller != null) { 20814 callerApp = getRecordForAppLocked(caller); 20815 if (callerApp == null) { 20816 throw new SecurityException( 20817 "Unable to find app for caller " + caller 20818 + " (pid=" + Binder.getCallingPid() 20819 + ") when registering receiver " + receiver); 20820 } 20821 if (callerApp.info.uid != SYSTEM_UID && 20822 !callerApp.pkgList.containsKey(callerPackage) && 20823 !"android".equals(callerPackage)) { 20824 throw new SecurityException("Given caller package " + callerPackage 20825 + " is not running in process " + callerApp); 20826 } 20827 callingUid = callerApp.info.uid; 20828 callingPid = callerApp.pid; 20829 } else { 20830 callerPackage = null; 20831 callingUid = Binder.getCallingUid(); 20832 callingPid = Binder.getCallingPid(); 20833 } 20834 20835 instantApp = isInstantApp(callerApp, callerPackage, callingUid); 20836 userId = mUserController.handleIncomingUser(callingPid, callingUid, userId, true, 20837 ALLOW_FULL_ONLY, "registerReceiver", callerPackage); 20838 20839 Iterator<String> actions = filter.actionsIterator(); 20840 if (actions == null) { 20841 ArrayList<String> noAction = new ArrayList<String>(1); 20842 noAction.add(null); 20843 actions = noAction.iterator(); 20844 } 20845 20846 // Collect stickies of users 20847 int[] userIds = { UserHandle.USER_ALL, UserHandle.getUserId(callingUid) }; 20848 while (actions.hasNext()) { 20849 String action = actions.next(); 20850 for (int id : userIds) { 20851 ArrayMap<String, ArrayList<Intent>> stickies = mStickyBroadcasts.get(id); 20852 if (stickies != null) { 20853 ArrayList<Intent> intents = stickies.get(action); 20854 if (intents != null) { 20855 if (stickyIntents == null) { 20856 stickyIntents = new ArrayList<Intent>(); 20857 } 20858 stickyIntents.addAll(intents); 20859 } 20860 } 20861 } 20862 } 20863 } 20864 20865 ArrayList<Intent> allSticky = null; 20866 if (stickyIntents != null) { 20867 final ContentResolver resolver = mContext.getContentResolver(); 20868 // Look for any matching sticky broadcasts... 20869 for (int i = 0, N = stickyIntents.size(); i < N; i++) { 20870 Intent intent = stickyIntents.get(i); 20871 // Don't provided intents that aren't available to instant apps. 20872 if (instantApp && 20873 (intent.getFlags() & Intent.FLAG_RECEIVER_VISIBLE_TO_INSTANT_APPS) == 0) { 20874 continue; 20875 } 20876 // If intent has scheme "content", it will need to acccess 20877 // provider that needs to lock mProviderMap in ActivityThread 20878 // and also it may need to wait application response, so we 20879 // cannot lock ActivityManagerService here. 20880 if (filter.match(resolver, intent, true, TAG) >= 0) { 20881 if (allSticky == null) { 20882 allSticky = new ArrayList<Intent>(); 20883 } 20884 allSticky.add(intent); 20885 } 20886 } 20887 } 20888 20889 // The first sticky in the list is returned directly back to the client. 20890 Intent sticky = allSticky != null ? allSticky.get(0) : null; 20891 if (DEBUG_BROADCAST) Slog.v(TAG_BROADCAST, "Register receiver " + filter + ": " + sticky); 20892 if (receiver == null) { 20893 return sticky; 20894 } 20895 20896 synchronized (this) { 20897 if (callerApp != null && (callerApp.thread == null 20898 || callerApp.thread.asBinder() != caller.asBinder())) { 20899 // Original caller already died 20900 return null; 20901 } 20902 ReceiverList rl = mRegisteredReceivers.get(receiver.asBinder()); 20903 if (rl == null) { 20904 rl = new ReceiverList(this, callerApp, callingPid, callingUid, 20905 userId, receiver); 20906 if (rl.app != null) { 20907 final int totalReceiversForApp = rl.app.receivers.size(); 20908 if (totalReceiversForApp >= MAX_RECEIVERS_ALLOWED_PER_APP) { 20909 throw new IllegalStateException("Too many receivers, total of " 20910 + totalReceiversForApp + ", registered for pid: " 20911 + rl.pid + ", callerPackage: " + callerPackage); 20912 } 20913 rl.app.receivers.add(rl); 20914 } else { 20915 try { 20916 receiver.asBinder().linkToDeath(rl, 0); 20917 } catch (RemoteException e) { 20918 return sticky; 20919 } 20920 rl.linkedToDeath = true; 20921 } 20922 mRegisteredReceivers.put(receiver.asBinder(), rl); 20923 } else if (rl.uid != callingUid) { 20924 throw new IllegalArgumentException( 20925 "Receiver requested to register for uid " + callingUid 20926 + " was previously registered for uid " + rl.uid 20927 + " callerPackage is " + callerPackage); 20928 } else if (rl.pid != callingPid) { 20929 throw new IllegalArgumentException( 20930 "Receiver requested to register for pid " + callingPid 20931 + " was previously registered for pid " + rl.pid 20932 + " callerPackage is " + callerPackage); 20933 } else if (rl.userId != userId) { 20934 throw new IllegalArgumentException( 20935 "Receiver requested to register for user " + userId 20936 + " was previously registered for user " + rl.userId 20937 + " callerPackage is " + callerPackage); 20938 } 20939 BroadcastFilter bf = new BroadcastFilter(filter, rl, callerPackage, 20940 permission, callingUid, userId, instantApp, visibleToInstantApps); 20941 if (rl.containsFilter(filter)) { 20942 Slog.w(TAG, "Receiver with filter " + filter 20943 + " already registered for pid " + rl.pid 20944 + ", callerPackage is " + callerPackage); 20945 } else { 20946 rl.add(bf); 20947 if (!bf.debugCheck()) { 20948 Slog.w(TAG, "==> For Dynamic broadcast"); 20949 } 20950 mReceiverResolver.addFilter(bf); 20951 } 20952 20953 // Enqueue broadcasts for all existing stickies that match 20954 // this filter. 20955 if (allSticky != null) { 20956 ArrayList receivers = new ArrayList(); 20957 receivers.add(bf); 20958 20959 final int stickyCount = allSticky.size(); 20960 for (int i = 0; i < stickyCount; i++) { 20961 Intent intent = allSticky.get(i); 20962 BroadcastQueue queue = broadcastQueueForIntent(intent); 20963 BroadcastRecord r = new BroadcastRecord(queue, intent, null, 20964 null, -1, -1, false, null, null, OP_NONE, null, receivers, 20965 null, 0, null, null, false, true, true, -1); 20966 queue.enqueueParallelBroadcastLocked(r); 20967 queue.scheduleBroadcastsLocked(); 20968 } 20969 } 20970 20971 return sticky; 20972 } 20973 } 20974 20975 public void unregisterReceiver(IIntentReceiver receiver) { 20976 if (DEBUG_BROADCAST) Slog.v(TAG_BROADCAST, "Unregister receiver: " + receiver); 20977 20978 final long origId = Binder.clearCallingIdentity(); 20979 try { 20980 boolean doTrim = false; 20981 20982 synchronized(this) { 20983 ReceiverList rl = mRegisteredReceivers.get(receiver.asBinder()); 20984 if (rl != null) { 20985 final BroadcastRecord r = rl.curBroadcast; 20986 if (r != null && r == r.queue.getMatchingOrderedReceiver(r)) { 20987 final boolean doNext = r.queue.finishReceiverLocked( 20988 r, r.resultCode, r.resultData, r.resultExtras, 20989 r.resultAbort, false); 20990 if (doNext) { 20991 doTrim = true; 20992 r.queue.processNextBroadcast(false); 20993 } 20994 } 20995 20996 if (rl.app != null) { 20997 rl.app.receivers.remove(rl); 20998 } 20999 removeReceiverLocked(rl); 21000 if (rl.linkedToDeath) { 21001 rl.linkedToDeath = false; 21002 rl.receiver.asBinder().unlinkToDeath(rl, 0); 21003 } 21004 } 21005 } 21006 21007 // If we actually concluded any broadcasts, we might now be able 21008 // to trim the recipients' apps from our working set 21009 if (doTrim) { 21010 trimApplications(); 21011 return; 21012 } 21013 21014 } finally { 21015 Binder.restoreCallingIdentity(origId); 21016 } 21017 } 21018 21019 void removeReceiverLocked(ReceiverList rl) { 21020 mRegisteredReceivers.remove(rl.receiver.asBinder()); 21021 for (int i = rl.size() - 1; i >= 0; i--) { 21022 mReceiverResolver.removeFilter(rl.get(i)); 21023 } 21024 } 21025 21026 private final void sendPackageBroadcastLocked(int cmd, String[] packages, int userId) { 21027 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 21028 ProcessRecord r = mLruProcesses.get(i); 21029 if (r.thread != null && (userId == UserHandle.USER_ALL || r.userId == userId)) { 21030 try { 21031 r.thread.dispatchPackageBroadcast(cmd, packages); 21032 } catch (RemoteException ex) { 21033 } 21034 } 21035 } 21036 } 21037 21038 private List<ResolveInfo> collectReceiverComponents(Intent intent, String resolvedType, 21039 int callingUid, int[] users) { 21040 // TODO: come back and remove this assumption to triage all broadcasts 21041 int pmFlags = STOCK_PM_FLAGS | MATCH_DEBUG_TRIAGED_MISSING; 21042 21043 List<ResolveInfo> receivers = null; 21044 try { 21045 HashSet<ComponentName> singleUserReceivers = null; 21046 boolean scannedFirstReceivers = false; 21047 for (int user : users) { 21048 // Skip users that have Shell restrictions, with exception of always permitted 21049 // Shell broadcasts 21050 if (callingUid == SHELL_UID 21051 && mUserController.hasUserRestriction( 21052 UserManager.DISALLOW_DEBUGGING_FEATURES, user) 21053 && !isPermittedShellBroadcast(intent)) { 21054 continue; 21055 } 21056 List<ResolveInfo> newReceivers = AppGlobals.getPackageManager() 21057 .queryIntentReceivers(intent, resolvedType, pmFlags, user).getList(); 21058 if (user != UserHandle.USER_SYSTEM && newReceivers != null) { 21059 // If this is not the system user, we need to check for 21060 // any receivers that should be filtered out. 21061 for (int i=0; i<newReceivers.size(); i++) { 21062 ResolveInfo ri = newReceivers.get(i); 21063 if ((ri.activityInfo.flags&ActivityInfo.FLAG_SYSTEM_USER_ONLY) != 0) { 21064 newReceivers.remove(i); 21065 i--; 21066 } 21067 } 21068 } 21069 if (newReceivers != null && newReceivers.size() == 0) { 21070 newReceivers = null; 21071 } 21072 if (receivers == null) { 21073 receivers = newReceivers; 21074 } else if (newReceivers != null) { 21075 // We need to concatenate the additional receivers 21076 // found with what we have do far. This would be easy, 21077 // but we also need to de-dup any receivers that are 21078 // singleUser. 21079 if (!scannedFirstReceivers) { 21080 // Collect any single user receivers we had already retrieved. 21081 scannedFirstReceivers = true; 21082 for (int i=0; i<receivers.size(); i++) { 21083 ResolveInfo ri = receivers.get(i); 21084 if ((ri.activityInfo.flags&ActivityInfo.FLAG_SINGLE_USER) != 0) { 21085 ComponentName cn = new ComponentName( 21086 ri.activityInfo.packageName, ri.activityInfo.name); 21087 if (singleUserReceivers == null) { 21088 singleUserReceivers = new HashSet<ComponentName>(); 21089 } 21090 singleUserReceivers.add(cn); 21091 } 21092 } 21093 } 21094 // Add the new results to the existing results, tracking 21095 // and de-dupping single user receivers. 21096 for (int i=0; i<newReceivers.size(); i++) { 21097 ResolveInfo ri = newReceivers.get(i); 21098 if ((ri.activityInfo.flags&ActivityInfo.FLAG_SINGLE_USER) != 0) { 21099 ComponentName cn = new ComponentName( 21100 ri.activityInfo.packageName, ri.activityInfo.name); 21101 if (singleUserReceivers == null) { 21102 singleUserReceivers = new HashSet<ComponentName>(); 21103 } 21104 if (!singleUserReceivers.contains(cn)) { 21105 singleUserReceivers.add(cn); 21106 receivers.add(ri); 21107 } 21108 } else { 21109 receivers.add(ri); 21110 } 21111 } 21112 } 21113 } 21114 } catch (RemoteException ex) { 21115 // pm is in same process, this will never happen. 21116 } 21117 return receivers; 21118 } 21119 21120 private boolean isPermittedShellBroadcast(Intent intent) { 21121 // remote bugreport should always be allowed to be taken 21122 return INTENT_REMOTE_BUGREPORT_FINISHED.equals(intent.getAction()); 21123 } 21124 21125 private void checkBroadcastFromSystem(Intent intent, ProcessRecord callerApp, 21126 String callerPackage, int callingUid, boolean isProtectedBroadcast, List receivers) { 21127 if ((intent.getFlags() & Intent.FLAG_RECEIVER_FROM_SHELL) != 0) { 21128 // Don't yell about broadcasts sent via shell 21129 return; 21130 } 21131 21132 final String action = intent.getAction(); 21133 if (isProtectedBroadcast 21134 || Intent.ACTION_CLOSE_SYSTEM_DIALOGS.equals(action) 21135 || Intent.ACTION_DISMISS_KEYBOARD_SHORTCUTS.equals(action) 21136 || Intent.ACTION_MEDIA_BUTTON.equals(action) 21137 || Intent.ACTION_MEDIA_SCANNER_SCAN_FILE.equals(action) 21138 || Intent.ACTION_SHOW_KEYBOARD_SHORTCUTS.equals(action) 21139 || Intent.ACTION_MASTER_CLEAR.equals(action) 21140 || Intent.ACTION_FACTORY_RESET.equals(action) 21141 || AppWidgetManager.ACTION_APPWIDGET_CONFIGURE.equals(action) 21142 || AppWidgetManager.ACTION_APPWIDGET_UPDATE.equals(action) 21143 || LocationManager.HIGH_POWER_REQUEST_CHANGE_ACTION.equals(action) 21144 || TelephonyIntents.ACTION_REQUEST_OMADM_CONFIGURATION_UPDATE.equals(action) 21145 || SuggestionSpan.ACTION_SUGGESTION_PICKED.equals(action) 21146 || AudioEffect.ACTION_OPEN_AUDIO_EFFECT_CONTROL_SESSION.equals(action) 21147 || AudioEffect.ACTION_CLOSE_AUDIO_EFFECT_CONTROL_SESSION.equals(action)) { 21148 // Broadcast is either protected, or it's a public action that 21149 // we've relaxed, so it's fine for system internals to send. 21150 return; 21151 } 21152 21153 // This broadcast may be a problem... but there are often system components that 21154 // want to send an internal broadcast to themselves, which is annoying to have to 21155 // explicitly list each action as a protected broadcast, so we will check for that 21156 // one safe case and allow it: an explicit broadcast, only being received by something 21157 // that has protected itself. 21158 if (intent.getPackage() != null || intent.getComponent() != null) { 21159 if (receivers == null || receivers.size() == 0) { 21160 // Intent is explicit and there's no receivers. 21161 // This happens, e.g. , when a system component sends a broadcast to 21162 // its own runtime receiver, and there's no manifest receivers for it, 21163 // because this method is called twice for each broadcast, 21164 // for runtime receivers and manifest receivers and the later check would find 21165 // no receivers. 21166 return; 21167 } 21168 boolean allProtected = true; 21169 for (int i = receivers.size()-1; i >= 0; i--) { 21170 Object target = receivers.get(i); 21171 if (target instanceof ResolveInfo) { 21172 ResolveInfo ri = (ResolveInfo)target; 21173 if (ri.activityInfo.exported && ri.activityInfo.permission == null) { 21174 allProtected = false; 21175 break; 21176 } 21177 } else { 21178 BroadcastFilter bf = (BroadcastFilter)target; 21179 if (bf.requiredPermission == null) { 21180 allProtected = false; 21181 break; 21182 } 21183 } 21184 } 21185 if (allProtected) { 21186 // All safe! 21187 return; 21188 } 21189 } 21190 21191 // The vast majority of broadcasts sent from system internals 21192 // should be protected to avoid security holes, so yell loudly 21193 // to ensure we examine these cases. 21194 if (callerApp != null) { 21195 Log.wtf(TAG, "Sending non-protected broadcast " + action 21196 + " from system " + callerApp.toShortString() + " pkg " + callerPackage, 21197 new Throwable()); 21198 } else { 21199 Log.wtf(TAG, "Sending non-protected broadcast " + action 21200 + " from system uid " + UserHandle.formatUid(callingUid) 21201 + " pkg " + callerPackage, 21202 new Throwable()); 21203 } 21204 } 21205 21206 @GuardedBy("this") 21207 final int broadcastIntentLocked(ProcessRecord callerApp, 21208 String callerPackage, Intent intent, String resolvedType, 21209 IIntentReceiver resultTo, int resultCode, String resultData, 21210 Bundle resultExtras, String[] requiredPermissions, int appOp, Bundle bOptions, 21211 boolean ordered, boolean sticky, int callingPid, int callingUid, int userId) { 21212 intent = new Intent(intent); 21213 21214 final boolean callerInstantApp = isInstantApp(callerApp, callerPackage, callingUid); 21215 // Instant Apps cannot use FLAG_RECEIVER_VISIBLE_TO_INSTANT_APPS 21216 if (callerInstantApp) { 21217 intent.setFlags(intent.getFlags() & ~Intent.FLAG_RECEIVER_VISIBLE_TO_INSTANT_APPS); 21218 } 21219 21220 // By default broadcasts do not go to stopped apps. 21221 intent.addFlags(Intent.FLAG_EXCLUDE_STOPPED_PACKAGES); 21222 21223 // If we have not finished booting, don't allow this to launch new processes. 21224 if (!mProcessesReady && (intent.getFlags()&Intent.FLAG_RECEIVER_BOOT_UPGRADE) == 0) { 21225 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 21226 } 21227 21228 if (DEBUG_BROADCAST_LIGHT) Slog.v(TAG_BROADCAST, 21229 (sticky ? "Broadcast sticky: ": "Broadcast: ") + intent 21230 + " ordered=" + ordered + " userid=" + userId); 21231 if ((resultTo != null) && !ordered) { 21232 Slog.w(TAG, "Broadcast " + intent + " not ordered but result callback requested!"); 21233 } 21234 21235 userId = mUserController.handleIncomingUser(callingPid, callingUid, userId, true, 21236 ALLOW_NON_FULL, "broadcast", callerPackage); 21237 21238 // Make sure that the user who is receiving this broadcast or its parent is running. 21239 // If not, we will just skip it. Make an exception for shutdown broadcasts, upgrade steps. 21240 if (userId != UserHandle.USER_ALL && !mUserController.isUserOrItsParentRunning(userId)) { 21241 if ((callingUid != SYSTEM_UID 21242 || (intent.getFlags() & Intent.FLAG_RECEIVER_BOOT_UPGRADE) == 0) 21243 && !Intent.ACTION_SHUTDOWN.equals(intent.getAction())) { 21244 Slog.w(TAG, "Skipping broadcast of " + intent 21245 + ": user " + userId + " and its parent (if any) are stopped"); 21246 return ActivityManager.BROADCAST_FAILED_USER_STOPPED; 21247 } 21248 } 21249 21250 final String action = intent.getAction(); 21251 BroadcastOptions brOptions = null; 21252 if (bOptions != null) { 21253 brOptions = new BroadcastOptions(bOptions); 21254 if (brOptions.getTemporaryAppWhitelistDuration() > 0) { 21255 // See if the caller is allowed to do this. Note we are checking against 21256 // the actual real caller (not whoever provided the operation as say a 21257 // PendingIntent), because that who is actually supplied the arguments. 21258 if (checkComponentPermission( 21259 android.Manifest.permission.CHANGE_DEVICE_IDLE_TEMP_WHITELIST, 21260 Binder.getCallingPid(), Binder.getCallingUid(), -1, true) 21261 != PackageManager.PERMISSION_GRANTED) { 21262 String msg = "Permission Denial: " + intent.getAction() 21263 + " broadcast from " + callerPackage + " (pid=" + callingPid 21264 + ", uid=" + callingUid + ")" 21265 + " requires " 21266 + android.Manifest.permission.CHANGE_DEVICE_IDLE_TEMP_WHITELIST; 21267 Slog.w(TAG, msg); 21268 throw new SecurityException(msg); 21269 } 21270 } 21271 if (brOptions.isDontSendToRestrictedApps() 21272 && !isUidActiveLocked(callingUid) 21273 && isBackgroundRestrictedNoCheck(callingUid, callerPackage)) { 21274 Slog.i(TAG, "Not sending broadcast " + action + " - app " + callerPackage 21275 + " has background restrictions"); 21276 return ActivityManager.START_CANCELED; 21277 } 21278 } 21279 21280 // Verify that protected broadcasts are only being sent by system code, 21281 // and that system code is only sending protected broadcasts. 21282 final boolean isProtectedBroadcast; 21283 try { 21284 isProtectedBroadcast = AppGlobals.getPackageManager().isProtectedBroadcast(action); 21285 } catch (RemoteException e) { 21286 Slog.w(TAG, "Remote exception", e); 21287 return ActivityManager.BROADCAST_SUCCESS; 21288 } 21289 21290 final boolean isCallerSystem; 21291 switch (UserHandle.getAppId(callingUid)) { 21292 case ROOT_UID: 21293 case SYSTEM_UID: 21294 case PHONE_UID: 21295 case BLUETOOTH_UID: 21296 case NFC_UID: 21297 case SE_UID: 21298 isCallerSystem = true; 21299 break; 21300 default: 21301 isCallerSystem = (callerApp != null) && callerApp.persistent; 21302 break; 21303 } 21304 21305 // First line security check before anything else: stop non-system apps from 21306 // sending protected broadcasts. 21307 if (!isCallerSystem) { 21308 if (isProtectedBroadcast) { 21309 String msg = "Permission Denial: not allowed to send broadcast " 21310 + action + " from pid=" 21311 + callingPid + ", uid=" + callingUid; 21312 Slog.w(TAG, msg); 21313 throw new SecurityException(msg); 21314 21315 } else if (AppWidgetManager.ACTION_APPWIDGET_CONFIGURE.equals(action) 21316 || AppWidgetManager.ACTION_APPWIDGET_UPDATE.equals(action)) { 21317 // Special case for compatibility: we don't want apps to send this, 21318 // but historically it has not been protected and apps may be using it 21319 // to poke their own app widget. So, instead of making it protected, 21320 // just limit it to the caller. 21321 if (callerPackage == null) { 21322 String msg = "Permission Denial: not allowed to send broadcast " 21323 + action + " from unknown caller."; 21324 Slog.w(TAG, msg); 21325 throw new SecurityException(msg); 21326 } else if (intent.getComponent() != null) { 21327 // They are good enough to send to an explicit component... verify 21328 // it is being sent to the calling app. 21329 if (!intent.getComponent().getPackageName().equals( 21330 callerPackage)) { 21331 String msg = "Permission Denial: not allowed to send broadcast " 21332 + action + " to " 21333 + intent.getComponent().getPackageName() + " from " 21334 + callerPackage; 21335 Slog.w(TAG, msg); 21336 throw new SecurityException(msg); 21337 } 21338 } else { 21339 // Limit broadcast to their own package. 21340 intent.setPackage(callerPackage); 21341 } 21342 } 21343 } 21344 21345 if (action != null) { 21346 if (getBackgroundLaunchBroadcasts().contains(action)) { 21347 if (DEBUG_BACKGROUND_CHECK) { 21348 Slog.i(TAG, "Broadcast action " + action + " forcing include-background"); 21349 } 21350 intent.addFlags(Intent.FLAG_RECEIVER_INCLUDE_BACKGROUND); 21351 } 21352 21353 switch (action) { 21354 case Intent.ACTION_UID_REMOVED: 21355 case Intent.ACTION_PACKAGE_REMOVED: 21356 case Intent.ACTION_PACKAGE_CHANGED: 21357 case Intent.ACTION_EXTERNAL_APPLICATIONS_UNAVAILABLE: 21358 case Intent.ACTION_EXTERNAL_APPLICATIONS_AVAILABLE: 21359 case Intent.ACTION_PACKAGES_SUSPENDED: 21360 case Intent.ACTION_PACKAGES_UNSUSPENDED: 21361 // Handle special intents: if this broadcast is from the package 21362 // manager about a package being removed, we need to remove all of 21363 // its activities from the history stack. 21364 if (checkComponentPermission( 21365 android.Manifest.permission.BROADCAST_PACKAGE_REMOVED, 21366 callingPid, callingUid, -1, true) 21367 != PackageManager.PERMISSION_GRANTED) { 21368 String msg = "Permission Denial: " + intent.getAction() 21369 + " broadcast from " + callerPackage + " (pid=" + callingPid 21370 + ", uid=" + callingUid + ")" 21371 + " requires " 21372 + android.Manifest.permission.BROADCAST_PACKAGE_REMOVED; 21373 Slog.w(TAG, msg); 21374 throw new SecurityException(msg); 21375 } 21376 switch (action) { 21377 case Intent.ACTION_UID_REMOVED: 21378 final int uid = getUidFromIntent(intent); 21379 if (uid >= 0) { 21380 mBatteryStatsService.removeUid(uid); 21381 mAppOpsService.uidRemoved(uid); 21382 } 21383 break; 21384 case Intent.ACTION_EXTERNAL_APPLICATIONS_UNAVAILABLE: 21385 // If resources are unavailable just force stop all those packages 21386 // and flush the attribute cache as well. 21387 String list[] = 21388 intent.getStringArrayExtra(Intent.EXTRA_CHANGED_PACKAGE_LIST); 21389 if (list != null && list.length > 0) { 21390 for (int i = 0; i < list.length; i++) { 21391 forceStopPackageLocked(list[i], -1, false, true, true, 21392 false, false, userId, "storage unmount"); 21393 } 21394 mRecentTasks.cleanupLocked(UserHandle.USER_ALL); 21395 sendPackageBroadcastLocked( 21396 ApplicationThreadConstants.EXTERNAL_STORAGE_UNAVAILABLE, 21397 list, userId); 21398 } 21399 break; 21400 case Intent.ACTION_EXTERNAL_APPLICATIONS_AVAILABLE: 21401 mRecentTasks.cleanupLocked(UserHandle.USER_ALL); 21402 break; 21403 case Intent.ACTION_PACKAGE_REMOVED: 21404 case Intent.ACTION_PACKAGE_CHANGED: 21405 Uri data = intent.getData(); 21406 String ssp; 21407 if (data != null && (ssp=data.getSchemeSpecificPart()) != null) { 21408 boolean removed = Intent.ACTION_PACKAGE_REMOVED.equals(action); 21409 final boolean replacing = 21410 intent.getBooleanExtra(Intent.EXTRA_REPLACING, false); 21411 final boolean killProcess = 21412 !intent.getBooleanExtra(Intent.EXTRA_DONT_KILL_APP, false); 21413 final boolean fullUninstall = removed && !replacing; 21414 if (removed) { 21415 if (killProcess) { 21416 forceStopPackageLocked(ssp, UserHandle.getAppId( 21417 intent.getIntExtra(Intent.EXTRA_UID, -1)), 21418 false, true, true, false, fullUninstall, userId, 21419 removed ? "pkg removed" : "pkg changed"); 21420 } 21421 final int cmd = killProcess 21422 ? ApplicationThreadConstants.PACKAGE_REMOVED 21423 : ApplicationThreadConstants.PACKAGE_REMOVED_DONT_KILL; 21424 sendPackageBroadcastLocked(cmd, 21425 new String[] {ssp}, userId); 21426 if (fullUninstall) { 21427 mAppOpsService.packageRemoved( 21428 intent.getIntExtra(Intent.EXTRA_UID, -1), ssp); 21429 21430 // Remove all permissions granted from/to this package 21431 removeUriPermissionsForPackageLocked(ssp, userId, true, 21432 false); 21433 21434 mRecentTasks.removeTasksByPackageName(ssp, userId); 21435 21436 mServices.forceStopPackageLocked(ssp, userId); 21437 mAppWarnings.onPackageUninstalled(ssp); 21438 mCompatModePackages.handlePackageUninstalledLocked(ssp); 21439 mBatteryStatsService.notePackageUninstalled(ssp); 21440 } 21441 } else { 21442 if (killProcess) { 21443 killPackageProcessesLocked(ssp, UserHandle.getAppId( 21444 intent.getIntExtra(Intent.EXTRA_UID, -1)), 21445 userId, ProcessList.INVALID_ADJ, 21446 false, true, true, false, "change " + ssp); 21447 } 21448 cleanupDisabledPackageComponentsLocked(ssp, userId, killProcess, 21449 intent.getStringArrayExtra( 21450 Intent.EXTRA_CHANGED_COMPONENT_NAME_LIST)); 21451 } 21452 } 21453 break; 21454 case Intent.ACTION_PACKAGES_SUSPENDED: 21455 case Intent.ACTION_PACKAGES_UNSUSPENDED: 21456 final boolean suspended = Intent.ACTION_PACKAGES_SUSPENDED.equals( 21457 intent.getAction()); 21458 final String[] packageNames = intent.getStringArrayExtra( 21459 Intent.EXTRA_CHANGED_PACKAGE_LIST); 21460 final int userHandle = intent.getIntExtra( 21461 Intent.EXTRA_USER_HANDLE, UserHandle.USER_NULL); 21462 21463 synchronized(ActivityManagerService.this) { 21464 mRecentTasks.onPackagesSuspendedChanged( 21465 packageNames, suspended, userHandle); 21466 } 21467 break; 21468 } 21469 break; 21470 case Intent.ACTION_PACKAGE_REPLACED: 21471 { 21472 final Uri data = intent.getData(); 21473 final String ssp; 21474 if (data != null && (ssp = data.getSchemeSpecificPart()) != null) { 21475 ApplicationInfo aInfo = null; 21476 try { 21477 aInfo = AppGlobals.getPackageManager() 21478 .getApplicationInfo(ssp, STOCK_PM_FLAGS, userId); 21479 } catch (RemoteException ignore) {} 21480 if (aInfo == null) { 21481 Slog.w(TAG, "Dropping ACTION_PACKAGE_REPLACED for non-existent pkg:" 21482 + " ssp=" + ssp + " data=" + data); 21483 return ActivityManager.BROADCAST_SUCCESS; 21484 } 21485 mStackSupervisor.updateActivityApplicationInfoLocked(aInfo); 21486 mServices.updateServiceApplicationInfoLocked(aInfo); 21487 sendPackageBroadcastLocked(ApplicationThreadConstants.PACKAGE_REPLACED, 21488 new String[] {ssp}, userId); 21489 } 21490 break; 21491 } 21492 case Intent.ACTION_PACKAGE_ADDED: 21493 { 21494 // Special case for adding a package: by default turn on compatibility mode. 21495 Uri data = intent.getData(); 21496 String ssp; 21497 if (data != null && (ssp = data.getSchemeSpecificPart()) != null) { 21498 final boolean replacing = 21499 intent.getBooleanExtra(Intent.EXTRA_REPLACING, false); 21500 mCompatModePackages.handlePackageAddedLocked(ssp, replacing); 21501 21502 try { 21503 ApplicationInfo ai = AppGlobals.getPackageManager(). 21504 getApplicationInfo(ssp, STOCK_PM_FLAGS, 0); 21505 mBatteryStatsService.notePackageInstalled(ssp, 21506 ai != null ? ai.versionCode : 0); 21507 } catch (RemoteException e) { 21508 } 21509 } 21510 break; 21511 } 21512 case Intent.ACTION_PACKAGE_DATA_CLEARED: 21513 { 21514 Uri data = intent.getData(); 21515 String ssp; 21516 if (data != null && (ssp = data.getSchemeSpecificPart()) != null) { 21517 mCompatModePackages.handlePackageDataClearedLocked(ssp); 21518 mAppWarnings.onPackageDataCleared(ssp); 21519 } 21520 break; 21521 } 21522 case Intent.ACTION_TIMEZONE_CHANGED: 21523 // If this is the time zone changed action, queue up a message that will reset 21524 // the timezone of all currently running processes. This message will get 21525 // queued up before the broadcast happens. 21526 mHandler.sendEmptyMessage(UPDATE_TIME_ZONE); 21527 break; 21528 case Intent.ACTION_TIME_CHANGED: 21529 // EXTRA_TIME_PREF_24_HOUR_FORMAT is optional so we must distinguish between 21530 // the tri-state value it may contain and "unknown". 21531 // For convenience we re-use the Intent extra values. 21532 final int NO_EXTRA_VALUE_FOUND = -1; 21533 final int timeFormatPreferenceMsgValue = intent.getIntExtra( 21534 Intent.EXTRA_TIME_PREF_24_HOUR_FORMAT, 21535 NO_EXTRA_VALUE_FOUND /* defaultValue */); 21536 // Only send a message if the time preference is available. 21537 if (timeFormatPreferenceMsgValue != NO_EXTRA_VALUE_FOUND) { 21538 Message updateTimePreferenceMsg = 21539 mHandler.obtainMessage(UPDATE_TIME_PREFERENCE_MSG, 21540 timeFormatPreferenceMsgValue, 0); 21541 mHandler.sendMessage(updateTimePreferenceMsg); 21542 } 21543 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 21544 synchronized (stats) { 21545 stats.noteCurrentTimeChangedLocked(); 21546 } 21547 break; 21548 case Intent.ACTION_CLEAR_DNS_CACHE: 21549 mHandler.sendEmptyMessage(CLEAR_DNS_CACHE_MSG); 21550 break; 21551 case Proxy.PROXY_CHANGE_ACTION: 21552 ProxyInfo proxy = intent.getParcelableExtra(Proxy.EXTRA_PROXY_INFO); 21553 mHandler.sendMessage(mHandler.obtainMessage(UPDATE_HTTP_PROXY_MSG, proxy)); 21554 break; 21555 case android.hardware.Camera.ACTION_NEW_PICTURE: 21556 case android.hardware.Camera.ACTION_NEW_VIDEO: 21557 // In N we just turned these off; in O we are turing them back on partly, 21558 // only for registered receivers. This will still address the main problem 21559 // (a spam of apps waking up when a picture is taken putting significant 21560 // memory pressure on the system at a bad point), while still allowing apps 21561 // that are already actively running to know about this happening. 21562 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 21563 break; 21564 case android.security.KeyChain.ACTION_TRUST_STORE_CHANGED: 21565 mHandler.sendEmptyMessage(HANDLE_TRUST_STORAGE_UPDATE_MSG); 21566 break; 21567 case "com.android.launcher.action.INSTALL_SHORTCUT": 21568 // As of O, we no longer support this broadcasts, even for pre-O apps. 21569 // Apps should now be using ShortcutManager.pinRequestShortcut(). 21570 Log.w(TAG, "Broadcast " + action 21571 + " no longer supported. It will not be delivered."); 21572 return ActivityManager.BROADCAST_SUCCESS; 21573 } 21574 21575 if (Intent.ACTION_PACKAGE_ADDED.equals(action) || 21576 Intent.ACTION_PACKAGE_REMOVED.equals(action) || 21577 Intent.ACTION_PACKAGE_REPLACED.equals(action)) { 21578 final int uid = getUidFromIntent(intent); 21579 if (uid != -1) { 21580 final UidRecord uidRec = mActiveUids.get(uid); 21581 if (uidRec != null) { 21582 uidRec.updateHasInternetPermission(); 21583 } 21584 } 21585 } 21586 } 21587 21588 // Add to the sticky list if requested. 21589 if (sticky) { 21590 if (checkPermission(android.Manifest.permission.BROADCAST_STICKY, 21591 callingPid, callingUid) 21592 != PackageManager.PERMISSION_GRANTED) { 21593 String msg = "Permission Denial: broadcastIntent() requesting a sticky broadcast from pid=" 21594 + callingPid + ", uid=" + callingUid 21595 + " requires " + android.Manifest.permission.BROADCAST_STICKY; 21596 Slog.w(TAG, msg); 21597 throw new SecurityException(msg); 21598 } 21599 if (requiredPermissions != null && requiredPermissions.length > 0) { 21600 Slog.w(TAG, "Can't broadcast sticky intent " + intent 21601 + " and enforce permissions " + Arrays.toString(requiredPermissions)); 21602 return ActivityManager.BROADCAST_STICKY_CANT_HAVE_PERMISSION; 21603 } 21604 if (intent.getComponent() != null) { 21605 throw new SecurityException( 21606 "Sticky broadcasts can't target a specific component"); 21607 } 21608 // We use userId directly here, since the "all" target is maintained 21609 // as a separate set of sticky broadcasts. 21610 if (userId != UserHandle.USER_ALL) { 21611 // But first, if this is not a broadcast to all users, then 21612 // make sure it doesn't conflict with an existing broadcast to 21613 // all users. 21614 ArrayMap<String, ArrayList<Intent>> stickies = mStickyBroadcasts.get( 21615 UserHandle.USER_ALL); 21616 if (stickies != null) { 21617 ArrayList<Intent> list = stickies.get(intent.getAction()); 21618 if (list != null) { 21619 int N = list.size(); 21620 int i; 21621 for (i=0; i<N; i++) { 21622 if (intent.filterEquals(list.get(i))) { 21623 throw new IllegalArgumentException( 21624 "Sticky broadcast " + intent + " for user " 21625 + userId + " conflicts with existing global broadcast"); 21626 } 21627 } 21628 } 21629 } 21630 } 21631 ArrayMap<String, ArrayList<Intent>> stickies = mStickyBroadcasts.get(userId); 21632 if (stickies == null) { 21633 stickies = new ArrayMap<>(); 21634 mStickyBroadcasts.put(userId, stickies); 21635 } 21636 ArrayList<Intent> list = stickies.get(intent.getAction()); 21637 if (list == null) { 21638 list = new ArrayList<>(); 21639 stickies.put(intent.getAction(), list); 21640 } 21641 final int stickiesCount = list.size(); 21642 int i; 21643 for (i = 0; i < stickiesCount; i++) { 21644 if (intent.filterEquals(list.get(i))) { 21645 // This sticky already exists, replace it. 21646 list.set(i, new Intent(intent)); 21647 break; 21648 } 21649 } 21650 if (i >= stickiesCount) { 21651 list.add(new Intent(intent)); 21652 } 21653 } 21654 21655 int[] users; 21656 if (userId == UserHandle.USER_ALL) { 21657 // Caller wants broadcast to go to all started users. 21658 users = mUserController.getStartedUserArray(); 21659 } else { 21660 // Caller wants broadcast to go to one specific user. 21661 users = new int[] {userId}; 21662 } 21663 21664 // Figure out who all will receive this broadcast. 21665 List receivers = null; 21666 List<BroadcastFilter> registeredReceivers = null; 21667 // Need to resolve the intent to interested receivers... 21668 if ((intent.getFlags()&Intent.FLAG_RECEIVER_REGISTERED_ONLY) 21669 == 0) { 21670 receivers = collectReceiverComponents(intent, resolvedType, callingUid, users); 21671 } 21672 if (intent.getComponent() == null) { 21673 if (userId == UserHandle.USER_ALL && callingUid == SHELL_UID) { 21674 // Query one target user at a time, excluding shell-restricted users 21675 for (int i = 0; i < users.length; i++) { 21676 if (mUserController.hasUserRestriction( 21677 UserManager.DISALLOW_DEBUGGING_FEATURES, users[i])) { 21678 continue; 21679 } 21680 List<BroadcastFilter> registeredReceiversForUser = 21681 mReceiverResolver.queryIntent(intent, 21682 resolvedType, false /*defaultOnly*/, users[i]); 21683 if (registeredReceivers == null) { 21684 registeredReceivers = registeredReceiversForUser; 21685 } else if (registeredReceiversForUser != null) { 21686 registeredReceivers.addAll(registeredReceiversForUser); 21687 } 21688 } 21689 } else { 21690 registeredReceivers = mReceiverResolver.queryIntent(intent, 21691 resolvedType, false /*defaultOnly*/, userId); 21692 } 21693 } 21694 21695 final boolean replacePending = 21696 (intent.getFlags()&Intent.FLAG_RECEIVER_REPLACE_PENDING) != 0; 21697 21698 if (DEBUG_BROADCAST) Slog.v(TAG_BROADCAST, "Enqueueing broadcast: " + intent.getAction() 21699 + " replacePending=" + replacePending); 21700 21701 int NR = registeredReceivers != null ? registeredReceivers.size() : 0; 21702 if (!ordered && NR > 0) { 21703 // If we are not serializing this broadcast, then send the 21704 // registered receivers separately so they don't wait for the 21705 // components to be launched. 21706 if (isCallerSystem) { 21707 checkBroadcastFromSystem(intent, callerApp, callerPackage, callingUid, 21708 isProtectedBroadcast, registeredReceivers); 21709 } 21710 final BroadcastQueue queue = broadcastQueueForIntent(intent); 21711 BroadcastRecord r = new BroadcastRecord(queue, intent, callerApp, 21712 callerPackage, callingPid, callingUid, callerInstantApp, resolvedType, 21713 requiredPermissions, appOp, brOptions, registeredReceivers, resultTo, 21714 resultCode, resultData, resultExtras, ordered, sticky, false, userId); 21715 if (DEBUG_BROADCAST) Slog.v(TAG_BROADCAST, "Enqueueing parallel broadcast " + r); 21716 final boolean replaced = replacePending 21717 && (queue.replaceParallelBroadcastLocked(r) != null); 21718 // Note: We assume resultTo is null for non-ordered broadcasts. 21719 if (!replaced) { 21720 queue.enqueueParallelBroadcastLocked(r); 21721 queue.scheduleBroadcastsLocked(); 21722 } 21723 registeredReceivers = null; 21724 NR = 0; 21725 } 21726 21727 // Merge into one list. 21728 int ir = 0; 21729 if (receivers != null) { 21730 // A special case for PACKAGE_ADDED: do not allow the package 21731 // being added to see this broadcast. This prevents them from 21732 // using this as a back door to get run as soon as they are 21733 // installed. Maybe in the future we want to have a special install 21734 // broadcast or such for apps, but we'd like to deliberately make 21735 // this decision. 21736 String skipPackages[] = null; 21737 if (Intent.ACTION_PACKAGE_ADDED.equals(intent.getAction()) 21738 || Intent.ACTION_PACKAGE_RESTARTED.equals(intent.getAction()) 21739 || Intent.ACTION_PACKAGE_DATA_CLEARED.equals(intent.getAction())) { 21740 Uri data = intent.getData(); 21741 if (data != null) { 21742 String pkgName = data.getSchemeSpecificPart(); 21743 if (pkgName != null) { 21744 skipPackages = new String[] { pkgName }; 21745 } 21746 } 21747 } else if (Intent.ACTION_EXTERNAL_APPLICATIONS_AVAILABLE.equals(intent.getAction())) { 21748 skipPackages = intent.getStringArrayExtra(Intent.EXTRA_CHANGED_PACKAGE_LIST); 21749 } 21750 if (skipPackages != null && (skipPackages.length > 0)) { 21751 for (String skipPackage : skipPackages) { 21752 if (skipPackage != null) { 21753 int NT = receivers.size(); 21754 for (int it=0; it<NT; it++) { 21755 ResolveInfo curt = (ResolveInfo)receivers.get(it); 21756 if (curt.activityInfo.packageName.equals(skipPackage)) { 21757 receivers.remove(it); 21758 it--; 21759 NT--; 21760 } 21761 } 21762 } 21763 } 21764 } 21765 21766 int NT = receivers != null ? receivers.size() : 0; 21767 int it = 0; 21768 ResolveInfo curt = null; 21769 BroadcastFilter curr = null; 21770 while (it < NT && ir < NR) { 21771 if (curt == null) { 21772 curt = (ResolveInfo)receivers.get(it); 21773 } 21774 if (curr == null) { 21775 curr = registeredReceivers.get(ir); 21776 } 21777 if (curr.getPriority() >= curt.priority) { 21778 // Insert this broadcast record into the final list. 21779 receivers.add(it, curr); 21780 ir++; 21781 curr = null; 21782 it++; 21783 NT++; 21784 } else { 21785 // Skip to the next ResolveInfo in the final list. 21786 it++; 21787 curt = null; 21788 } 21789 } 21790 } 21791 while (ir < NR) { 21792 if (receivers == null) { 21793 receivers = new ArrayList(); 21794 } 21795 receivers.add(registeredReceivers.get(ir)); 21796 ir++; 21797 } 21798 21799 if (isCallerSystem) { 21800 checkBroadcastFromSystem(intent, callerApp, callerPackage, callingUid, 21801 isProtectedBroadcast, receivers); 21802 } 21803 21804 if ((receivers != null && receivers.size() > 0) 21805 || resultTo != null) { 21806 BroadcastQueue queue = broadcastQueueForIntent(intent); 21807 BroadcastRecord r = new BroadcastRecord(queue, intent, callerApp, 21808 callerPackage, callingPid, callingUid, callerInstantApp, resolvedType, 21809 requiredPermissions, appOp, brOptions, receivers, resultTo, resultCode, 21810 resultData, resultExtras, ordered, sticky, false, userId); 21811 21812 if (DEBUG_BROADCAST) Slog.v(TAG_BROADCAST, "Enqueueing ordered broadcast " + r 21813 + ": prev had " + queue.mOrderedBroadcasts.size()); 21814 if (DEBUG_BROADCAST) Slog.i(TAG_BROADCAST, 21815 "Enqueueing broadcast " + r.intent.getAction()); 21816 21817 final BroadcastRecord oldRecord = 21818 replacePending ? queue.replaceOrderedBroadcastLocked(r) : null; 21819 if (oldRecord != null) { 21820 // Replaced, fire the result-to receiver. 21821 if (oldRecord.resultTo != null) { 21822 final BroadcastQueue oldQueue = broadcastQueueForIntent(oldRecord.intent); 21823 try { 21824 oldQueue.performReceiveLocked(oldRecord.callerApp, oldRecord.resultTo, 21825 oldRecord.intent, 21826 Activity.RESULT_CANCELED, null, null, 21827 false, false, oldRecord.userId); 21828 } catch (RemoteException e) { 21829 Slog.w(TAG, "Failure [" 21830 + queue.mQueueName + "] sending broadcast result of " 21831 + intent, e); 21832 21833 } 21834 } 21835 } else { 21836 queue.enqueueOrderedBroadcastLocked(r); 21837 queue.scheduleBroadcastsLocked(); 21838 } 21839 } else { 21840 // There was nobody interested in the broadcast, but we still want to record 21841 // that it happened. 21842 if (intent.getComponent() == null && intent.getPackage() == null 21843 && (intent.getFlags()&Intent.FLAG_RECEIVER_REGISTERED_ONLY) == 0) { 21844 // This was an implicit broadcast... let's record it for posterity. 21845 addBroadcastStatLocked(intent.getAction(), callerPackage, 0, 0, 0); 21846 } 21847 } 21848 21849 return ActivityManager.BROADCAST_SUCCESS; 21850 } 21851 21852 /** 21853 * @return uid from the extra field {@link Intent#EXTRA_UID} if present, Otherwise -1 21854 */ 21855 private int getUidFromIntent(Intent intent) { 21856 if (intent == null) { 21857 return -1; 21858 } 21859 final Bundle intentExtras = intent.getExtras(); 21860 return intent.hasExtra(Intent.EXTRA_UID) 21861 ? intentExtras.getInt(Intent.EXTRA_UID) : -1; 21862 } 21863 21864 final void rotateBroadcastStatsIfNeededLocked() { 21865 final long now = SystemClock.elapsedRealtime(); 21866 if (mCurBroadcastStats == null || 21867 (mCurBroadcastStats.mStartRealtime +(24*60*60*1000) < now)) { 21868 mLastBroadcastStats = mCurBroadcastStats; 21869 if (mLastBroadcastStats != null) { 21870 mLastBroadcastStats.mEndRealtime = SystemClock.elapsedRealtime(); 21871 mLastBroadcastStats.mEndUptime = SystemClock.uptimeMillis(); 21872 } 21873 mCurBroadcastStats = new BroadcastStats(); 21874 } 21875 } 21876 21877 final void addBroadcastStatLocked(String action, String srcPackage, int receiveCount, 21878 int skipCount, long dispatchTime) { 21879 rotateBroadcastStatsIfNeededLocked(); 21880 mCurBroadcastStats.addBroadcast(action, srcPackage, receiveCount, skipCount, dispatchTime); 21881 } 21882 21883 final void addBackgroundCheckViolationLocked(String action, String targetPackage) { 21884 rotateBroadcastStatsIfNeededLocked(); 21885 mCurBroadcastStats.addBackgroundCheckViolation(action, targetPackage); 21886 } 21887 21888 final Intent verifyBroadcastLocked(Intent intent) { 21889 // Refuse possible leaked file descriptors 21890 if (intent != null && intent.hasFileDescriptors() == true) { 21891 throw new IllegalArgumentException("File descriptors passed in Intent"); 21892 } 21893 21894 int flags = intent.getFlags(); 21895 21896 if (!mProcessesReady) { 21897 // if the caller really truly claims to know what they're doing, go 21898 // ahead and allow the broadcast without launching any receivers 21899 if ((flags&Intent.FLAG_RECEIVER_REGISTERED_ONLY_BEFORE_BOOT) != 0) { 21900 // This will be turned into a FLAG_RECEIVER_REGISTERED_ONLY later on if needed. 21901 } else if ((flags&Intent.FLAG_RECEIVER_REGISTERED_ONLY) == 0) { 21902 Slog.e(TAG, "Attempt to launch receivers of broadcast intent " + intent 21903 + " before boot completion"); 21904 throw new IllegalStateException("Cannot broadcast before boot completed"); 21905 } 21906 } 21907 21908 if ((flags&Intent.FLAG_RECEIVER_BOOT_UPGRADE) != 0) { 21909 throw new IllegalArgumentException( 21910 "Can't use FLAG_RECEIVER_BOOT_UPGRADE here"); 21911 } 21912 21913 if ((flags & Intent.FLAG_RECEIVER_FROM_SHELL) != 0) { 21914 switch (Binder.getCallingUid()) { 21915 case ROOT_UID: 21916 case SHELL_UID: 21917 break; 21918 default: 21919 Slog.w(TAG, "Removing FLAG_RECEIVER_FROM_SHELL because caller is UID " 21920 + Binder.getCallingUid()); 21921 intent.removeFlags(Intent.FLAG_RECEIVER_FROM_SHELL); 21922 break; 21923 } 21924 } 21925 21926 return intent; 21927 } 21928 21929 public final int broadcastIntent(IApplicationThread caller, 21930 Intent intent, String resolvedType, IIntentReceiver resultTo, 21931 int resultCode, String resultData, Bundle resultExtras, 21932 String[] requiredPermissions, int appOp, Bundle bOptions, 21933 boolean serialized, boolean sticky, int userId) { 21934 enforceNotIsolatedCaller("broadcastIntent"); 21935 synchronized(this) { 21936 intent = verifyBroadcastLocked(intent); 21937 21938 final ProcessRecord callerApp = getRecordForAppLocked(caller); 21939 final int callingPid = Binder.getCallingPid(); 21940 final int callingUid = Binder.getCallingUid(); 21941 final long origId = Binder.clearCallingIdentity(); 21942 int res = broadcastIntentLocked(callerApp, 21943 callerApp != null ? callerApp.info.packageName : null, 21944 intent, resolvedType, resultTo, resultCode, resultData, resultExtras, 21945 requiredPermissions, appOp, bOptions, serialized, sticky, 21946 callingPid, callingUid, userId); 21947 Binder.restoreCallingIdentity(origId); 21948 return res; 21949 } 21950 } 21951 21952 21953 int broadcastIntentInPackage(String packageName, int uid, 21954 Intent intent, String resolvedType, IIntentReceiver resultTo, 21955 int resultCode, String resultData, Bundle resultExtras, 21956 String requiredPermission, Bundle bOptions, boolean serialized, boolean sticky, 21957 int userId) { 21958 synchronized(this) { 21959 intent = verifyBroadcastLocked(intent); 21960 21961 final long origId = Binder.clearCallingIdentity(); 21962 String[] requiredPermissions = requiredPermission == null ? null 21963 : new String[] {requiredPermission}; 21964 int res = broadcastIntentLocked(null, packageName, intent, resolvedType, 21965 resultTo, resultCode, resultData, resultExtras, 21966 requiredPermissions, OP_NONE, bOptions, serialized, 21967 sticky, -1, uid, userId); 21968 Binder.restoreCallingIdentity(origId); 21969 return res; 21970 } 21971 } 21972 21973 public final void unbroadcastIntent(IApplicationThread caller, Intent intent, int userId) { 21974 // Refuse possible leaked file descriptors 21975 if (intent != null && intent.hasFileDescriptors() == true) { 21976 throw new IllegalArgumentException("File descriptors passed in Intent"); 21977 } 21978 21979 userId = mUserController.handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 21980 userId, true, ALLOW_NON_FULL, "removeStickyBroadcast", null); 21981 21982 synchronized(this) { 21983 if (checkCallingPermission(android.Manifest.permission.BROADCAST_STICKY) 21984 != PackageManager.PERMISSION_GRANTED) { 21985 String msg = "Permission Denial: unbroadcastIntent() from pid=" 21986 + Binder.getCallingPid() 21987 + ", uid=" + Binder.getCallingUid() 21988 + " requires " + android.Manifest.permission.BROADCAST_STICKY; 21989 Slog.w(TAG, msg); 21990 throw new SecurityException(msg); 21991 } 21992 ArrayMap<String, ArrayList<Intent>> stickies = mStickyBroadcasts.get(userId); 21993 if (stickies != null) { 21994 ArrayList<Intent> list = stickies.get(intent.getAction()); 21995 if (list != null) { 21996 int N = list.size(); 21997 int i; 21998 for (i=0; i<N; i++) { 21999 if (intent.filterEquals(list.get(i))) { 22000 list.remove(i); 22001 break; 22002 } 22003 } 22004 if (list.size() <= 0) { 22005 stickies.remove(intent.getAction()); 22006 } 22007 } 22008 if (stickies.size() <= 0) { 22009 mStickyBroadcasts.remove(userId); 22010 } 22011 } 22012 } 22013 } 22014 22015 void backgroundServicesFinishedLocked(int userId) { 22016 for (BroadcastQueue queue : mBroadcastQueues) { 22017 queue.backgroundServicesFinishedLocked(userId); 22018 } 22019 } 22020 22021 public void finishReceiver(IBinder who, int resultCode, String resultData, 22022 Bundle resultExtras, boolean resultAbort, int flags) { 22023 if (DEBUG_BROADCAST) Slog.v(TAG_BROADCAST, "Finish receiver: " + who); 22024 22025 // Refuse possible leaked file descriptors 22026 if (resultExtras != null && resultExtras.hasFileDescriptors()) { 22027 throw new IllegalArgumentException("File descriptors passed in Bundle"); 22028 } 22029 22030 final long origId = Binder.clearCallingIdentity(); 22031 try { 22032 boolean doNext = false; 22033 BroadcastRecord r; 22034 22035 synchronized(this) { 22036 BroadcastQueue queue = (flags & Intent.FLAG_RECEIVER_FOREGROUND) != 0 22037 ? mFgBroadcastQueue : mBgBroadcastQueue; 22038 r = queue.getMatchingOrderedReceiver(who); 22039 if (r != null) { 22040 doNext = r.queue.finishReceiverLocked(r, resultCode, 22041 resultData, resultExtras, resultAbort, true); 22042 } 22043 if (doNext) { 22044 r.queue.processNextBroadcastLocked(/*fromMsg=*/ false, /*skipOomAdj=*/ true); 22045 } 22046 // updateOomAdjLocked() will be done here 22047 trimApplicationsLocked(); 22048 } 22049 22050 } finally { 22051 Binder.restoreCallingIdentity(origId); 22052 } 22053 } 22054 22055 // ========================================================= 22056 // INSTRUMENTATION 22057 // ========================================================= 22058 22059 public boolean startInstrumentation(ComponentName className, 22060 String profileFile, int flags, Bundle arguments, 22061 IInstrumentationWatcher watcher, IUiAutomationConnection uiAutomationConnection, 22062 int userId, String abiOverride) { 22063 enforceNotIsolatedCaller("startInstrumentation"); 22064 userId = mUserController.handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 22065 userId, false, ALLOW_FULL_ONLY, "startInstrumentation", null); 22066 // Refuse possible leaked file descriptors 22067 if (arguments != null && arguments.hasFileDescriptors()) { 22068 throw new IllegalArgumentException("File descriptors passed in Bundle"); 22069 } 22070 22071 synchronized(this) { 22072 InstrumentationInfo ii = null; 22073 ApplicationInfo ai = null; 22074 try { 22075 ii = mContext.getPackageManager().getInstrumentationInfo( 22076 className, STOCK_PM_FLAGS); 22077 ai = AppGlobals.getPackageManager().getApplicationInfo( 22078 ii.targetPackage, STOCK_PM_FLAGS, userId); 22079 } catch (PackageManager.NameNotFoundException e) { 22080 } catch (RemoteException e) { 22081 } 22082 if (ii == null) { 22083 reportStartInstrumentationFailureLocked(watcher, className, 22084 "Unable to find instrumentation info for: " + className); 22085 return false; 22086 } 22087 if (ai == null) { 22088 reportStartInstrumentationFailureLocked(watcher, className, 22089 "Unable to find instrumentation target package: " + ii.targetPackage); 22090 return false; 22091 } 22092 if (!ai.hasCode()) { 22093 reportStartInstrumentationFailureLocked(watcher, className, 22094 "Instrumentation target has no code: " + ii.targetPackage); 22095 return false; 22096 } 22097 22098 int match = mContext.getPackageManager().checkSignatures( 22099 ii.targetPackage, ii.packageName); 22100 if (match < 0 && match != PackageManager.SIGNATURE_FIRST_NOT_SIGNED) { 22101 String msg = "Permission Denial: starting instrumentation " 22102 + className + " from pid=" 22103 + Binder.getCallingPid() 22104 + ", uid=" + Binder.getCallingPid() 22105 + " not allowed because package " + ii.packageName 22106 + " does not have a signature matching the target " 22107 + ii.targetPackage; 22108 reportStartInstrumentationFailureLocked(watcher, className, msg); 22109 throw new SecurityException(msg); 22110 } 22111 22112 ActiveInstrumentation activeInstr = new ActiveInstrumentation(this); 22113 activeInstr.mClass = className; 22114 String defProcess = ai.processName;; 22115 if (ii.targetProcesses == null) { 22116 activeInstr.mTargetProcesses = new String[]{ai.processName}; 22117 } else if (ii.targetProcesses.equals("*")) { 22118 activeInstr.mTargetProcesses = new String[0]; 22119 } else { 22120 activeInstr.mTargetProcesses = ii.targetProcesses.split(","); 22121 defProcess = activeInstr.mTargetProcesses[0]; 22122 } 22123 activeInstr.mTargetInfo = ai; 22124 activeInstr.mProfileFile = profileFile; 22125 activeInstr.mArguments = arguments; 22126 activeInstr.mWatcher = watcher; 22127 activeInstr.mUiAutomationConnection = uiAutomationConnection; 22128 activeInstr.mResultClass = className; 22129 22130 boolean disableHiddenApiChecks = 22131 (flags & INSTRUMENTATION_FLAG_DISABLE_HIDDEN_API_CHECKS) != 0; 22132 if (disableHiddenApiChecks) { 22133 enforceCallingPermission(android.Manifest.permission.DISABLE_HIDDEN_API_CHECKS, 22134 "disable hidden API checks"); 22135 } 22136 22137 final long origId = Binder.clearCallingIdentity(); 22138 // Instrumentation can kill and relaunch even persistent processes 22139 forceStopPackageLocked(ii.targetPackage, -1, true, false, true, true, false, userId, 22140 "start instr"); 22141 // Inform usage stats to make the target package active 22142 if (mUsageStatsService != null) { 22143 mUsageStatsService.reportEvent(ii.targetPackage, userId, 22144 UsageEvents.Event.SYSTEM_INTERACTION); 22145 } 22146 22147 ProcessRecord app = addAppLocked(ai, defProcess, false, disableHiddenApiChecks, 22148 abiOverride); 22149 app.instr = activeInstr; 22150 activeInstr.mFinished = false; 22151 activeInstr.mRunningProcesses.add(app); 22152 if (!mActiveInstrumentation.contains(activeInstr)) { 22153 mActiveInstrumentation.add(activeInstr); 22154 } 22155 Binder.restoreCallingIdentity(origId); 22156 } 22157 22158 return true; 22159 } 22160 22161 /** 22162 * Report errors that occur while attempting to start Instrumentation. Always writes the 22163 * error to the logs, but if somebody is watching, send the report there too. This enables 22164 * the "am" command to report errors with more information. 22165 * 22166 * @param watcher The IInstrumentationWatcher. Null if there isn't one. 22167 * @param cn The component name of the instrumentation. 22168 * @param report The error report. 22169 */ 22170 private void reportStartInstrumentationFailureLocked(IInstrumentationWatcher watcher, 22171 ComponentName cn, String report) { 22172 Slog.w(TAG, report); 22173 if (watcher != null) { 22174 Bundle results = new Bundle(); 22175 results.putString(Instrumentation.REPORT_KEY_IDENTIFIER, "ActivityManagerService"); 22176 results.putString("Error", report); 22177 mInstrumentationReporter.reportStatus(watcher, cn, -1, results); 22178 } 22179 } 22180 22181 void addInstrumentationResultsLocked(ProcessRecord app, Bundle results) { 22182 if (app.instr == null) { 22183 Slog.w(TAG, "finishInstrumentation called on non-instrumented: " + app); 22184 return; 22185 } 22186 22187 if (!app.instr.mFinished && results != null) { 22188 if (app.instr.mCurResults == null) { 22189 app.instr.mCurResults = new Bundle(results); 22190 } else { 22191 app.instr.mCurResults.putAll(results); 22192 } 22193 } 22194 } 22195 22196 public void addInstrumentationResults(IApplicationThread target, Bundle results) { 22197 int userId = UserHandle.getCallingUserId(); 22198 // Refuse possible leaked file descriptors 22199 if (results != null && results.hasFileDescriptors()) { 22200 throw new IllegalArgumentException("File descriptors passed in Intent"); 22201 } 22202 22203 synchronized(this) { 22204 ProcessRecord app = getRecordForAppLocked(target); 22205 if (app == null) { 22206 Slog.w(TAG, "addInstrumentationResults: no app for " + target); 22207 return; 22208 } 22209 final long origId = Binder.clearCallingIdentity(); 22210 addInstrumentationResultsLocked(app, results); 22211 Binder.restoreCallingIdentity(origId); 22212 } 22213 } 22214 22215 @GuardedBy("this") 22216 void finishInstrumentationLocked(ProcessRecord app, int resultCode, Bundle results) { 22217 if (app.instr == null) { 22218 Slog.w(TAG, "finishInstrumentation called on non-instrumented: " + app); 22219 return; 22220 } 22221 22222 if (!app.instr.mFinished) { 22223 if (app.instr.mWatcher != null) { 22224 Bundle finalResults = app.instr.mCurResults; 22225 if (finalResults != null) { 22226 if (app.instr.mCurResults != null && results != null) { 22227 finalResults.putAll(results); 22228 } 22229 } else { 22230 finalResults = results; 22231 } 22232 mInstrumentationReporter.reportFinished(app.instr.mWatcher, 22233 app.instr.mClass, resultCode, finalResults); 22234 } 22235 22236 // Can't call out of the system process with a lock held, so post a message. 22237 if (app.instr.mUiAutomationConnection != null) { 22238 mHandler.obtainMessage(SHUTDOWN_UI_AUTOMATION_CONNECTION_MSG, 22239 app.instr.mUiAutomationConnection).sendToTarget(); 22240 } 22241 app.instr.mFinished = true; 22242 } 22243 22244 app.instr.removeProcess(app); 22245 app.instr = null; 22246 22247 forceStopPackageLocked(app.info.packageName, -1, false, false, true, true, false, app.userId, 22248 "finished inst"); 22249 } 22250 22251 public void finishInstrumentation(IApplicationThread target, 22252 int resultCode, Bundle results) { 22253 int userId = UserHandle.getCallingUserId(); 22254 // Refuse possible leaked file descriptors 22255 if (results != null && results.hasFileDescriptors()) { 22256 throw new IllegalArgumentException("File descriptors passed in Intent"); 22257 } 22258 22259 synchronized(this) { 22260 ProcessRecord app = getRecordForAppLocked(target); 22261 if (app == null) { 22262 Slog.w(TAG, "finishInstrumentation: no app for " + target); 22263 return; 22264 } 22265 final long origId = Binder.clearCallingIdentity(); 22266 finishInstrumentationLocked(app, resultCode, results); 22267 Binder.restoreCallingIdentity(origId); 22268 } 22269 } 22270 22271 // ========================================================= 22272 // CONFIGURATION 22273 // ========================================================= 22274 22275 public ConfigurationInfo getDeviceConfigurationInfo() { 22276 ConfigurationInfo config = new ConfigurationInfo(); 22277 synchronized (this) { 22278 final Configuration globalConfig = getGlobalConfiguration(); 22279 config.reqTouchScreen = globalConfig.touchscreen; 22280 config.reqKeyboardType = globalConfig.keyboard; 22281 config.reqNavigation = globalConfig.navigation; 22282 if (globalConfig.navigation == Configuration.NAVIGATION_DPAD 22283 || globalConfig.navigation == Configuration.NAVIGATION_TRACKBALL) { 22284 config.reqInputFeatures |= ConfigurationInfo.INPUT_FEATURE_FIVE_WAY_NAV; 22285 } 22286 if (globalConfig.keyboard != Configuration.KEYBOARD_UNDEFINED 22287 && globalConfig.keyboard != Configuration.KEYBOARD_NOKEYS) { 22288 config.reqInputFeatures |= ConfigurationInfo.INPUT_FEATURE_HARD_KEYBOARD; 22289 } 22290 config.reqGlEsVersion = GL_ES_VERSION; 22291 } 22292 return config; 22293 } 22294 22295 ActivityStack getFocusedStack() { 22296 return mStackSupervisor.getFocusedStack(); 22297 } 22298 22299 @Override 22300 public StackInfo getFocusedStackInfo() throws RemoteException { 22301 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS, "getStackInfo()"); 22302 long ident = Binder.clearCallingIdentity(); 22303 try { 22304 synchronized (this) { 22305 ActivityStack focusedStack = getFocusedStack(); 22306 if (focusedStack != null) { 22307 return mStackSupervisor.getStackInfo(focusedStack.mStackId); 22308 } 22309 return null; 22310 } 22311 } finally { 22312 Binder.restoreCallingIdentity(ident); 22313 } 22314 } 22315 22316 public Configuration getConfiguration() { 22317 Configuration ci; 22318 synchronized(this) { 22319 ci = new Configuration(getGlobalConfiguration()); 22320 ci.userSetLocale = false; 22321 } 22322 return ci; 22323 } 22324 22325 @Override 22326 public void suppressResizeConfigChanges(boolean suppress) throws RemoteException { 22327 enforceCallingPermission(MANAGE_ACTIVITY_STACKS, "suppressResizeConfigChanges()"); 22328 synchronized (this) { 22329 mSuppressResizeConfigChanges = suppress; 22330 } 22331 } 22332 22333 /** 22334 * NOTE: For the pinned stack, this method is usually called after the bounds animation has 22335 * animated the stack to the fullscreen, but can also be called if we are relaunching an 22336 * activity and clearing the task at the same time. 22337 */ 22338 @Override 22339 // TODO: API should just be about changing windowing modes... 22340 public void moveTasksToFullscreenStack(int fromStackId, boolean onTop) { 22341 enforceCallerIsRecentsOrHasPermission(MANAGE_ACTIVITY_STACKS, 22342 "moveTasksToFullscreenStack()"); 22343 synchronized (this) { 22344 final long origId = Binder.clearCallingIdentity(); 22345 try { 22346 final ActivityStack stack = mStackSupervisor.getStack(fromStackId); 22347 if (stack != null){ 22348 if (!stack.isActivityTypeStandardOrUndefined()) { 22349 throw new IllegalArgumentException( 22350 "You can't move tasks from non-standard stacks."); 22351 } 22352 mStackSupervisor.moveTasksToFullscreenStackLocked(stack, onTop); 22353 } 22354 } finally { 22355 Binder.restoreCallingIdentity(origId); 22356 } 22357 } 22358 } 22359 22360 @Override 22361 public void updatePersistentConfiguration(Configuration values) { 22362 enforceCallingPermission(CHANGE_CONFIGURATION, "updatePersistentConfiguration()"); 22363 enforceWriteSettingsPermission("updatePersistentConfiguration()"); 22364 if (values == null) { 22365 throw new NullPointerException("Configuration must not be null"); 22366 } 22367 22368 int userId = UserHandle.getCallingUserId(); 22369 22370 synchronized(this) { 22371 updatePersistentConfigurationLocked(values, userId); 22372 } 22373 } 22374 22375 private void updatePersistentConfigurationLocked(Configuration values, @UserIdInt int userId) { 22376 final long origId = Binder.clearCallingIdentity(); 22377 try { 22378 updateConfigurationLocked(values, null, false, true, userId, false /* deferResume */); 22379 } finally { 22380 Binder.restoreCallingIdentity(origId); 22381 } 22382 } 22383 22384 private void updateFontScaleIfNeeded(@UserIdInt int userId) { 22385 final float scaleFactor = Settings.System.getFloatForUser(mContext.getContentResolver(), 22386 FONT_SCALE, 1.0f, userId); 22387 22388 synchronized (this) { 22389 if (getGlobalConfiguration().fontScale == scaleFactor) { 22390 return; 22391 } 22392 22393 final Configuration configuration 22394 = mWindowManager.computeNewConfiguration(DEFAULT_DISPLAY); 22395 configuration.fontScale = scaleFactor; 22396 updatePersistentConfigurationLocked(configuration, userId); 22397 } 22398 } 22399 22400 private void enforceWriteSettingsPermission(String func) { 22401 int uid = Binder.getCallingUid(); 22402 if (uid == ROOT_UID) { 22403 return; 22404 } 22405 22406 if (Settings.checkAndNoteWriteSettingsOperation(mContext, uid, 22407 Settings.getPackageNameForUid(mContext, uid), false)) { 22408 return; 22409 } 22410 22411 String msg = "Permission Denial: " + func + " from pid=" 22412 + Binder.getCallingPid() 22413 + ", uid=" + uid 22414 + " requires " + android.Manifest.permission.WRITE_SETTINGS; 22415 Slog.w(TAG, msg); 22416 throw new SecurityException(msg); 22417 } 22418 22419 @Override 22420 public boolean updateConfiguration(Configuration values) { 22421 enforceCallingPermission(CHANGE_CONFIGURATION, "updateConfiguration()"); 22422 22423 synchronized(this) { 22424 if (values == null && mWindowManager != null) { 22425 // sentinel: fetch the current configuration from the window manager 22426 values = mWindowManager.computeNewConfiguration(DEFAULT_DISPLAY); 22427 } 22428 22429 if (mWindowManager != null) { 22430 // Update OOM levels based on display size. 22431 mProcessList.applyDisplaySize(mWindowManager); 22432 } 22433 22434 final long origId = Binder.clearCallingIdentity(); 22435 try { 22436 if (values != null) { 22437 Settings.System.clearConfiguration(values); 22438 } 22439 updateConfigurationLocked(values, null, false, false /* persistent */, 22440 UserHandle.USER_NULL, false /* deferResume */, 22441 mTmpUpdateConfigurationResult); 22442 return mTmpUpdateConfigurationResult.changes != 0; 22443 } finally { 22444 Binder.restoreCallingIdentity(origId); 22445 } 22446 } 22447 } 22448 22449 void updateUserConfigurationLocked() { 22450 final Configuration configuration = new Configuration(getGlobalConfiguration()); 22451 final int currentUserId = mUserController.getCurrentUserId(); 22452 Settings.System.adjustConfigurationForUser(mContext.getContentResolver(), configuration, 22453 currentUserId, Settings.System.canWrite(mContext)); 22454 updateConfigurationLocked(configuration, null /* starting */, false /* initLocale */, 22455 false /* persistent */, currentUserId, false /* deferResume */); 22456 } 22457 22458 boolean updateConfigurationLocked(Configuration values, ActivityRecord starting, 22459 boolean initLocale) { 22460 return updateConfigurationLocked(values, starting, initLocale, false /* deferResume */); 22461 } 22462 22463 boolean updateConfigurationLocked(Configuration values, ActivityRecord starting, 22464 boolean initLocale, boolean deferResume) { 22465 // pass UserHandle.USER_NULL as userId because we don't persist configuration for any user 22466 return updateConfigurationLocked(values, starting, initLocale, false /* persistent */, 22467 UserHandle.USER_NULL, deferResume); 22468 } 22469 22470 // To cache the list of supported system locales 22471 private String[] mSupportedSystemLocales = null; 22472 22473 private boolean updateConfigurationLocked(Configuration values, ActivityRecord starting, 22474 boolean initLocale, boolean persistent, int userId, boolean deferResume) { 22475 return updateConfigurationLocked(values, starting, initLocale, persistent, userId, 22476 deferResume, null /* result */); 22477 } 22478 22479 /** 22480 * Do either or both things: (1) change the current configuration, and (2) 22481 * make sure the given activity is running with the (now) current 22482 * configuration. Returns true if the activity has been left running, or 22483 * false if <var>starting</var> is being destroyed to match the new 22484 * configuration. 22485 * 22486 * @param userId is only used when persistent parameter is set to true to persist configuration 22487 * for that particular user 22488 */ 22489 private boolean updateConfigurationLocked(Configuration values, ActivityRecord starting, 22490 boolean initLocale, boolean persistent, int userId, boolean deferResume, 22491 UpdateConfigurationResult result) { 22492 int changes = 0; 22493 boolean kept = true; 22494 22495 if (mWindowManager != null) { 22496 mWindowManager.deferSurfaceLayout(); 22497 } 22498 try { 22499 if (values != null) { 22500 changes = updateGlobalConfigurationLocked(values, initLocale, persistent, userId, 22501 deferResume); 22502 } 22503 22504 kept = ensureConfigAndVisibilityAfterUpdate(starting, changes); 22505 } finally { 22506 if (mWindowManager != null) { 22507 mWindowManager.continueSurfaceLayout(); 22508 } 22509 } 22510 22511 if (result != null) { 22512 result.changes = changes; 22513 result.activityRelaunched = !kept; 22514 } 22515 return kept; 22516 } 22517 22518 /** 22519 * Returns true if this configuration change is interesting enough to send an 22520 * {@link Intent#ACTION_SPLIT_CONFIGURATION_CHANGED} broadcast. 22521 */ 22522 private static boolean isSplitConfigurationChange(int configDiff) { 22523 return (configDiff & (ActivityInfo.CONFIG_LOCALE | ActivityInfo.CONFIG_DENSITY)) != 0; 22524 } 22525 22526 /** Update default (global) configuration and notify listeners about changes. */ 22527 private int updateGlobalConfigurationLocked(@NonNull Configuration values, boolean initLocale, 22528 boolean persistent, int userId, boolean deferResume) { 22529 mTempConfig.setTo(getGlobalConfiguration()); 22530 final int changes = mTempConfig.updateFrom(values); 22531 if (changes == 0) { 22532 // Since calling to Activity.setRequestedOrientation leads to freezing the window with 22533 // setting WindowManagerService.mWaitingForConfig to true, it is important that we call 22534 // performDisplayOverrideConfigUpdate in order to send the new display configuration 22535 // (even if there are no actual changes) to unfreeze the window. 22536 performDisplayOverrideConfigUpdate(values, deferResume, DEFAULT_DISPLAY); 22537 return 0; 22538 } 22539 22540 if (DEBUG_SWITCH || DEBUG_CONFIGURATION) Slog.i(TAG_CONFIGURATION, 22541 "Updating global configuration to: " + values); 22542 22543 EventLog.writeEvent(EventLogTags.CONFIGURATION_CHANGED, changes); 22544 StatsLog.write(StatsLog.RESOURCE_CONFIGURATION_CHANGED, 22545 values.colorMode, 22546 values.densityDpi, 22547 values.fontScale, 22548 values.hardKeyboardHidden, 22549 values.keyboard, 22550 values.keyboardHidden, 22551 values.mcc, 22552 values.mnc, 22553 values.navigation, 22554 values.navigationHidden, 22555 values.orientation, 22556 values.screenHeightDp, 22557 values.screenLayout, 22558 values.screenWidthDp, 22559 values.smallestScreenWidthDp, 22560 values.touchscreen, 22561 values.uiMode); 22562 22563 22564 if (!initLocale && !values.getLocales().isEmpty() && values.userSetLocale) { 22565 final LocaleList locales = values.getLocales(); 22566 int bestLocaleIndex = 0; 22567 if (locales.size() > 1) { 22568 if (mSupportedSystemLocales == null) { 22569 mSupportedSystemLocales = Resources.getSystem().getAssets().getLocales(); 22570 } 22571 bestLocaleIndex = Math.max(0, locales.getFirstMatchIndex(mSupportedSystemLocales)); 22572 } 22573 SystemProperties.set("persist.sys.locale", 22574 locales.get(bestLocaleIndex).toLanguageTag()); 22575 LocaleList.setDefault(locales, bestLocaleIndex); 22576 mHandler.sendMessage(mHandler.obtainMessage(SEND_LOCALE_TO_MOUNT_DAEMON_MSG, 22577 locales.get(bestLocaleIndex))); 22578 } 22579 22580 mConfigurationSeq = Math.max(++mConfigurationSeq, 1); 22581 mTempConfig.seq = mConfigurationSeq; 22582 22583 // Update stored global config and notify everyone about the change. 22584 mStackSupervisor.onConfigurationChanged(mTempConfig); 22585 22586 Slog.i(TAG, "Config changes=" + Integer.toHexString(changes) + " " + mTempConfig); 22587 // TODO(multi-display): Update UsageEvents#Event to include displayId. 22588 mUsageStatsService.reportConfigurationChange(mTempConfig, 22589 mUserController.getCurrentUserId()); 22590 22591 // TODO: If our config changes, should we auto dismiss any currently showing dialogs? 22592 updateShouldShowDialogsLocked(mTempConfig); 22593 22594 AttributeCache ac = AttributeCache.instance(); 22595 if (ac != null) { 22596 ac.updateConfiguration(mTempConfig); 22597 } 22598 22599 // Make sure all resources in our process are updated right now, so that anyone who is going 22600 // to retrieve resource values after we return will be sure to get the new ones. This is 22601 // especially important during boot, where the first config change needs to guarantee all 22602 // resources have that config before following boot code is executed. 22603 mSystemThread.applyConfigurationToResources(mTempConfig); 22604 22605 // We need another copy of global config because we're scheduling some calls instead of 22606 // running them in place. We need to be sure that object we send will be handled unchanged. 22607 final Configuration configCopy = new Configuration(mTempConfig); 22608 if (persistent && Settings.System.hasInterestingConfigurationChanges(changes)) { 22609 Message msg = mHandler.obtainMessage(UPDATE_CONFIGURATION_MSG); 22610 msg.obj = configCopy; 22611 msg.arg1 = userId; 22612 mHandler.sendMessage(msg); 22613 } 22614 22615 for (int i = mLruProcesses.size() - 1; i >= 0; i--) { 22616 ProcessRecord app = mLruProcesses.get(i); 22617 try { 22618 if (app.thread != null) { 22619 if (DEBUG_CONFIGURATION) Slog.v(TAG_CONFIGURATION, "Sending to proc " 22620 + app.processName + " new config " + configCopy); 22621 mLifecycleManager.scheduleTransaction(app.thread, 22622 ConfigurationChangeItem.obtain(configCopy)); 22623 } 22624 } catch (Exception e) { 22625 Slog.e(TAG_CONFIGURATION, "Failed to schedule configuration change", e); 22626 } 22627 } 22628 22629 Intent intent = new Intent(Intent.ACTION_CONFIGURATION_CHANGED); 22630 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY | Intent.FLAG_RECEIVER_REPLACE_PENDING 22631 | Intent.FLAG_RECEIVER_FOREGROUND 22632 | Intent.FLAG_RECEIVER_VISIBLE_TO_INSTANT_APPS); 22633 broadcastIntentLocked(null, null, intent, null, null, 0, null, null, null, 22634 OP_NONE, null, false, false, MY_PID, SYSTEM_UID, 22635 UserHandle.USER_ALL); 22636 if ((changes & ActivityInfo.CONFIG_LOCALE) != 0) { 22637 intent = new Intent(Intent.ACTION_LOCALE_CHANGED); 22638 intent.addFlags(Intent.FLAG_RECEIVER_FOREGROUND 22639 | Intent.FLAG_RECEIVER_INCLUDE_BACKGROUND 22640 | Intent.FLAG_RECEIVER_VISIBLE_TO_INSTANT_APPS); 22641 if (initLocale || !mProcessesReady) { 22642 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 22643 } 22644 broadcastIntentLocked(null, null, intent, null, null, 0, null, null, null, 22645 OP_NONE, null, false, false, MY_PID, SYSTEM_UID, 22646 UserHandle.USER_ALL); 22647 } 22648 22649 // Send a broadcast to PackageInstallers if the configuration change is interesting 22650 // for the purposes of installing additional splits. 22651 if (!initLocale && isSplitConfigurationChange(changes)) { 22652 intent = new Intent(Intent.ACTION_SPLIT_CONFIGURATION_CHANGED); 22653 intent.addFlags(Intent.FLAG_RECEIVER_REPLACE_PENDING 22654 | Intent.FLAG_RECEIVER_INCLUDE_BACKGROUND); 22655 22656 // Typically only app stores will have this permission. 22657 String[] permissions = new String[] { android.Manifest.permission.INSTALL_PACKAGES }; 22658 broadcastIntentLocked(null, null, intent, null, null, 0, null, null, permissions, 22659 OP_NONE, null, false, false, MY_PID, SYSTEM_UID, UserHandle.USER_ALL); 22660 } 22661 22662 // Override configuration of the default display duplicates global config, so we need to 22663 // update it also. This will also notify WindowManager about changes. 22664 performDisplayOverrideConfigUpdate(mStackSupervisor.getConfiguration(), deferResume, 22665 DEFAULT_DISPLAY); 22666 22667 return changes; 22668 } 22669 22670 @Override 22671 public boolean updateDisplayOverrideConfiguration(Configuration values, int displayId) { 22672 enforceCallingPermission(CHANGE_CONFIGURATION, "updateDisplayOverrideConfiguration()"); 22673 22674 synchronized (this) { 22675 // Check if display is initialized in AM. 22676 if (!mStackSupervisor.isDisplayAdded(displayId)) { 22677 // Call might come when display is not yet added or has already been removed. 22678 if (DEBUG_CONFIGURATION) { 22679 Slog.w(TAG, "Trying to update display configuration for non-existing displayId=" 22680 + displayId); 22681 } 22682 return false; 22683 } 22684 22685 if (values == null && mWindowManager != null) { 22686 // sentinel: fetch the current configuration from the window manager 22687 values = mWindowManager.computeNewConfiguration(displayId); 22688 } 22689 22690 if (mWindowManager != null) { 22691 // Update OOM levels based on display size. 22692 mProcessList.applyDisplaySize(mWindowManager); 22693 } 22694 22695 final long origId = Binder.clearCallingIdentity(); 22696 try { 22697 if (values != null) { 22698 Settings.System.clearConfiguration(values); 22699 } 22700 updateDisplayOverrideConfigurationLocked(values, null /* starting */, 22701 false /* deferResume */, displayId, mTmpUpdateConfigurationResult); 22702 return mTmpUpdateConfigurationResult.changes != 0; 22703 } finally { 22704 Binder.restoreCallingIdentity(origId); 22705 } 22706 } 22707 } 22708 22709 boolean updateDisplayOverrideConfigurationLocked(Configuration values, ActivityRecord starting, 22710 boolean deferResume, int displayId) { 22711 return updateDisplayOverrideConfigurationLocked(values, starting, deferResume /* deferResume */, 22712 displayId, null /* result */); 22713 } 22714 22715 /** 22716 * Updates override configuration specific for the selected display. If no config is provided, 22717 * new one will be computed in WM based on current display info. 22718 */ 22719 private boolean updateDisplayOverrideConfigurationLocked(Configuration values, 22720 ActivityRecord starting, boolean deferResume, int displayId, 22721 UpdateConfigurationResult result) { 22722 int changes = 0; 22723 boolean kept = true; 22724 22725 if (mWindowManager != null) { 22726 mWindowManager.deferSurfaceLayout(); 22727 } 22728 try { 22729 if (values != null) { 22730 if (displayId == DEFAULT_DISPLAY) { 22731 // Override configuration of the default display duplicates global config, so 22732 // we're calling global config update instead for default display. It will also 22733 // apply the correct override config. 22734 changes = updateGlobalConfigurationLocked(values, false /* initLocale */, 22735 false /* persistent */, UserHandle.USER_NULL /* userId */, deferResume); 22736 } else { 22737 changes = performDisplayOverrideConfigUpdate(values, deferResume, displayId); 22738 } 22739 } 22740 22741 kept = ensureConfigAndVisibilityAfterUpdate(starting, changes); 22742 } finally { 22743 if (mWindowManager != null) { 22744 mWindowManager.continueSurfaceLayout(); 22745 } 22746 } 22747 22748 if (result != null) { 22749 result.changes = changes; 22750 result.activityRelaunched = !kept; 22751 } 22752 return kept; 22753 } 22754 22755 private int performDisplayOverrideConfigUpdate(Configuration values, boolean deferResume, 22756 int displayId) { 22757 mTempConfig.setTo(mStackSupervisor.getDisplayOverrideConfiguration(displayId)); 22758 final int changes = mTempConfig.updateFrom(values); 22759 if (changes != 0) { 22760 Slog.i(TAG, "Override config changes=" + Integer.toHexString(changes) + " " 22761 + mTempConfig + " for displayId=" + displayId); 22762 mStackSupervisor.setDisplayOverrideConfiguration(mTempConfig, displayId); 22763 22764 final boolean isDensityChange = (changes & ActivityInfo.CONFIG_DENSITY) != 0; 22765 if (isDensityChange && displayId == DEFAULT_DISPLAY) { 22766 mAppWarnings.onDensityChanged(); 22767 22768 killAllBackgroundProcessesExcept(N, 22769 ActivityManager.PROCESS_STATE_BOUND_FOREGROUND_SERVICE); 22770 } 22771 } 22772 22773 // Update the configuration with WM first and check if any of the stacks need to be resized 22774 // due to the configuration change. If so, resize the stacks now and do any relaunches if 22775 // necessary. This way we don't need to relaunch again afterwards in 22776 // ensureActivityConfiguration(). 22777 if (mWindowManager != null) { 22778 final int[] resizedStacks = 22779 mWindowManager.setNewDisplayOverrideConfiguration(mTempConfig, displayId); 22780 if (resizedStacks != null) { 22781 for (int stackId : resizedStacks) { 22782 resizeStackWithBoundsFromWindowManager(stackId, deferResume); 22783 } 22784 } 22785 } 22786 22787 return changes; 22788 } 22789 22790 /** Applies latest configuration and/or visibility updates if needed. */ 22791 private boolean ensureConfigAndVisibilityAfterUpdate(ActivityRecord starting, int changes) { 22792 boolean kept = true; 22793 final ActivityStack mainStack = mStackSupervisor.getFocusedStack(); 22794 // mainStack is null during startup. 22795 if (mainStack != null) { 22796 if (changes != 0 && starting == null) { 22797 // If the configuration changed, and the caller is not already 22798 // in the process of starting an activity, then find the top 22799 // activity to check if its configuration needs to change. 22800 starting = mainStack.topRunningActivityLocked(); 22801 } 22802 22803 if (starting != null) { 22804 kept = starting.ensureActivityConfiguration(changes, 22805 false /* preserveWindow */); 22806 // And we need to make sure at this point that all other activities 22807 // are made visible with the correct configuration. 22808 mStackSupervisor.ensureActivitiesVisibleLocked(starting, changes, 22809 !PRESERVE_WINDOWS); 22810 } 22811 } 22812 22813 return kept; 22814 } 22815 22816 /** Helper method that requests bounds from WM and applies them to stack. */ 22817 private void resizeStackWithBoundsFromWindowManager(int stackId, boolean deferResume) { 22818 final Rect newStackBounds = new Rect(); 22819 final ActivityStack stack = mStackSupervisor.getStack(stackId); 22820 22821 // TODO(b/71548119): Revert CL introducing below once cause of mismatch is found. 22822 if (stack == null) { 22823 final StringWriter writer = new StringWriter(); 22824 final PrintWriter printWriter = new PrintWriter(writer); 22825 mStackSupervisor.dumpDisplays(printWriter); 22826 printWriter.flush(); 22827 22828 Log.wtf(TAG, "stack not found:" + stackId + " displays:" + writer); 22829 } 22830 22831 stack.getBoundsForNewConfiguration(newStackBounds); 22832 mStackSupervisor.resizeStackLocked( 22833 stack, !newStackBounds.isEmpty() ? newStackBounds : null /* bounds */, 22834 null /* tempTaskBounds */, null /* tempTaskInsetBounds */, 22835 false /* preserveWindows */, false /* allowResizeInDockedMode */, deferResume); 22836 } 22837 22838 /** 22839 * Decide based on the configuration whether we should show the ANR, 22840 * crash, etc dialogs. The idea is that if there is no affordance to 22841 * press the on-screen buttons, or the user experience would be more 22842 * greatly impacted than the crash itself, we shouldn't show the dialog. 22843 * 22844 * A thought: SystemUI might also want to get told about this, the Power 22845 * dialog / global actions also might want different behaviors. 22846 */ 22847 private void updateShouldShowDialogsLocked(Configuration config) { 22848 final boolean inputMethodExists = !(config.keyboard == Configuration.KEYBOARD_NOKEYS 22849 && config.touchscreen == Configuration.TOUCHSCREEN_NOTOUCH 22850 && config.navigation == Configuration.NAVIGATION_NONAV); 22851 int modeType = config.uiMode & Configuration.UI_MODE_TYPE_MASK; 22852 final boolean uiModeSupportsDialogs = (modeType != Configuration.UI_MODE_TYPE_CAR 22853 && !(modeType == Configuration.UI_MODE_TYPE_WATCH && Build.IS_USER) 22854 && modeType != Configuration.UI_MODE_TYPE_TELEVISION 22855 && modeType != Configuration.UI_MODE_TYPE_VR_HEADSET); 22856 final boolean hideDialogsSet = Settings.Global.getInt(mContext.getContentResolver(), 22857 HIDE_ERROR_DIALOGS, 0) != 0; 22858 mShowDialogs = inputMethodExists && uiModeSupportsDialogs && !hideDialogsSet; 22859 } 22860 22861 @Override 22862 public boolean shouldUpRecreateTask(IBinder token, String destAffinity) { 22863 synchronized (this) { 22864 ActivityRecord srec = ActivityRecord.forTokenLocked(token); 22865 if (srec != null) { 22866 return srec.getStack().shouldUpRecreateTaskLocked(srec, destAffinity); 22867 } 22868 } 22869 return false; 22870 } 22871 22872 public boolean navigateUpTo(IBinder token, Intent destIntent, int resultCode, 22873 Intent resultData) { 22874 22875 synchronized (this) { 22876 final ActivityRecord r = ActivityRecord.forTokenLocked(token); 22877 if (r != null) { 22878 return r.getStack().navigateUpToLocked(r, destIntent, resultCode, resultData); 22879 } 22880 return false; 22881 } 22882 } 22883 22884 public int getLaunchedFromUid(IBinder activityToken) { 22885 ActivityRecord srec; 22886 synchronized (this) { 22887 srec = ActivityRecord.forTokenLocked(activityToken); 22888 } 22889 if (srec == null) { 22890 return -1; 22891 } 22892 return srec.launchedFromUid; 22893 } 22894 22895 public String getLaunchedFromPackage(IBinder activityToken) { 22896 ActivityRecord srec; 22897 synchronized (this) { 22898 srec = ActivityRecord.forTokenLocked(activityToken); 22899 } 22900 if (srec == null) { 22901 return null; 22902 } 22903 return srec.launchedFromPackage; 22904 } 22905 22906 // ========================================================= 22907 // LIFETIME MANAGEMENT 22908 // ========================================================= 22909 22910 // Returns whether the app is receiving broadcast. 22911 // If receiving, fetch all broadcast queues which the app is 22912 // the current [or imminent] receiver on. 22913 private boolean isReceivingBroadcastLocked(ProcessRecord app, 22914 ArraySet<BroadcastQueue> receivingQueues) { 22915 final int N = app.curReceivers.size(); 22916 if (N > 0) { 22917 for (int i = 0; i < N; i++) { 22918 receivingQueues.add(app.curReceivers.valueAt(i).queue); 22919 } 22920 return true; 22921 } 22922 22923 // It's not the current receiver, but it might be starting up to become one 22924 for (BroadcastQueue queue : mBroadcastQueues) { 22925 final BroadcastRecord r = queue.mPendingBroadcast; 22926 if (r != null && r.curApp == app) { 22927 // found it; report which queue it's in 22928 receivingQueues.add(queue); 22929 } 22930 } 22931 22932 return !receivingQueues.isEmpty(); 22933 } 22934 22935 Association startAssociationLocked(int sourceUid, String sourceProcess, int sourceState, 22936 int targetUid, ComponentName targetComponent, String targetProcess) { 22937 if (!mTrackingAssociations) { 22938 return null; 22939 } 22940 ArrayMap<ComponentName, SparseArray<ArrayMap<String, Association>>> components 22941 = mAssociations.get(targetUid); 22942 if (components == null) { 22943 components = new ArrayMap<>(); 22944 mAssociations.put(targetUid, components); 22945 } 22946 SparseArray<ArrayMap<String, Association>> sourceUids = components.get(targetComponent); 22947 if (sourceUids == null) { 22948 sourceUids = new SparseArray<>(); 22949 components.put(targetComponent, sourceUids); 22950 } 22951 ArrayMap<String, Association> sourceProcesses = sourceUids.get(sourceUid); 22952 if (sourceProcesses == null) { 22953 sourceProcesses = new ArrayMap<>(); 22954 sourceUids.put(sourceUid, sourceProcesses); 22955 } 22956 Association ass = sourceProcesses.get(sourceProcess); 22957 if (ass == null) { 22958 ass = new Association(sourceUid, sourceProcess, targetUid, targetComponent, 22959 targetProcess); 22960 sourceProcesses.put(sourceProcess, ass); 22961 } 22962 ass.mCount++; 22963 ass.mNesting++; 22964 if (ass.mNesting == 1) { 22965 ass.mStartTime = ass.mLastStateUptime = SystemClock.uptimeMillis(); 22966 ass.mLastState = sourceState; 22967 } 22968 return ass; 22969 } 22970 22971 void stopAssociationLocked(int sourceUid, String sourceProcess, int targetUid, 22972 ComponentName targetComponent) { 22973 if (!mTrackingAssociations) { 22974 return; 22975 } 22976 ArrayMap<ComponentName, SparseArray<ArrayMap<String, Association>>> components 22977 = mAssociations.get(targetUid); 22978 if (components == null) { 22979 return; 22980 } 22981 SparseArray<ArrayMap<String, Association>> sourceUids = components.get(targetComponent); 22982 if (sourceUids == null) { 22983 return; 22984 } 22985 ArrayMap<String, Association> sourceProcesses = sourceUids.get(sourceUid); 22986 if (sourceProcesses == null) { 22987 return; 22988 } 22989 Association ass = sourceProcesses.get(sourceProcess); 22990 if (ass == null || ass.mNesting <= 0) { 22991 return; 22992 } 22993 ass.mNesting--; 22994 if (ass.mNesting == 0) { 22995 long uptime = SystemClock.uptimeMillis(); 22996 ass.mTime += uptime - ass.mStartTime; 22997 ass.mStateTimes[ass.mLastState-ActivityManager.MIN_PROCESS_STATE] 22998 += uptime - ass.mLastStateUptime; 22999 ass.mLastState = ActivityManager.MAX_PROCESS_STATE + 2; 23000 } 23001 } 23002 23003 private void noteUidProcessState(final int uid, final int state) { 23004 mBatteryStatsService.noteUidProcessState(uid, state); 23005 mAppOpsService.updateUidProcState(uid, state); 23006 if (mTrackingAssociations) { 23007 for (int i1=0, N1=mAssociations.size(); i1<N1; i1++) { 23008 ArrayMap<ComponentName, SparseArray<ArrayMap<String, Association>>> targetComponents 23009 = mAssociations.valueAt(i1); 23010 for (int i2=0, N2=targetComponents.size(); i2<N2; i2++) { 23011 SparseArray<ArrayMap<String, Association>> sourceUids 23012 = targetComponents.valueAt(i2); 23013 ArrayMap<String, Association> sourceProcesses = sourceUids.get(uid); 23014 if (sourceProcesses != null) { 23015 for (int i4=0, N4=sourceProcesses.size(); i4<N4; i4++) { 23016 Association ass = sourceProcesses.valueAt(i4); 23017 if (ass.mNesting >= 1) { 23018 // currently associated 23019 long uptime = SystemClock.uptimeMillis(); 23020 ass.mStateTimes[ass.mLastState-ActivityManager.MIN_PROCESS_STATE] 23021 += uptime - ass.mLastStateUptime; 23022 ass.mLastState = state; 23023 ass.mLastStateUptime = uptime; 23024 } 23025 } 23026 } 23027 } 23028 } 23029 } 23030 } 23031 23032 private final boolean computeOomAdjLocked(ProcessRecord app, int cachedAdj, ProcessRecord TOP_APP, 23033 boolean doingAll, long now) { 23034 if (mAdjSeq == app.adjSeq) { 23035 if (app.adjSeq == app.completedAdjSeq) { 23036 // This adjustment has already been computed successfully. 23037 return false; 23038 } else { 23039 // The process is being computed, so there is a cycle. We cannot 23040 // rely on this process's state. 23041 app.containsCycle = true; 23042 return false; 23043 } 23044 } 23045 23046 if (app.thread == null) { 23047 app.adjSeq = mAdjSeq; 23048 app.curSchedGroup = ProcessList.SCHED_GROUP_BACKGROUND; 23049 app.curProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 23050 app.curAdj=app.curRawAdj=ProcessList.CACHED_APP_MAX_ADJ; 23051 app.completedAdjSeq = app.adjSeq; 23052 return false; 23053 } 23054 23055 app.adjTypeCode = ActivityManager.RunningAppProcessInfo.REASON_UNKNOWN; 23056 app.adjSource = null; 23057 app.adjTarget = null; 23058 app.empty = false; 23059 app.cached = false; 23060 23061 final int activitiesSize = app.activities.size(); 23062 final int appUid = app.info.uid; 23063 final int logUid = mCurOomAdjUid; 23064 23065 int prevAppAdj = app.curAdj; 23066 23067 if (app.maxAdj <= ProcessList.FOREGROUND_APP_ADJ) { 23068 // The max adjustment doesn't allow this app to be anything 23069 // below foreground, so it is not worth doing work for it. 23070 if (DEBUG_OOM_ADJ_REASON || logUid == appUid) { 23071 reportOomAdjMessageLocked(TAG_OOM_ADJ, "Making fixed: " + app); 23072 } 23073 app.adjType = "fixed"; 23074 app.adjSeq = mAdjSeq; 23075 app.curRawAdj = app.maxAdj; 23076 app.foregroundActivities = false; 23077 app.curSchedGroup = ProcessList.SCHED_GROUP_DEFAULT; 23078 app.curProcState = ActivityManager.PROCESS_STATE_PERSISTENT; 23079 // System processes can do UI, and when they do we want to have 23080 // them trim their memory after the user leaves the UI. To 23081 // facilitate this, here we need to determine whether or not it 23082 // is currently showing UI. 23083 app.systemNoUi = true; 23084 if (app == TOP_APP) { 23085 app.systemNoUi = false; 23086 app.curSchedGroup = ProcessList.SCHED_GROUP_TOP_APP; 23087 app.adjType = "pers-top-activity"; 23088 } else if (app.hasTopUi) { 23089 // sched group/proc state adjustment is below 23090 app.systemNoUi = false; 23091 app.adjType = "pers-top-ui"; 23092 } else if (activitiesSize > 0) { 23093 for (int j = 0; j < activitiesSize; j++) { 23094 final ActivityRecord r = app.activities.get(j); 23095 if (r.visible) { 23096 app.systemNoUi = false; 23097 } 23098 } 23099 } 23100 if (!app.systemNoUi) { 23101 if (mWakefulness == PowerManagerInternal.WAKEFULNESS_AWAKE) { 23102 // screen on, promote UI 23103 app.curProcState = ActivityManager.PROCESS_STATE_PERSISTENT_UI; 23104 app.curSchedGroup = ProcessList.SCHED_GROUP_TOP_APP; 23105 } else { 23106 // screen off, restrict UI scheduling 23107 app.curProcState = ActivityManager.PROCESS_STATE_BOUND_FOREGROUND_SERVICE; 23108 app.curSchedGroup = ProcessList.SCHED_GROUP_RESTRICTED; 23109 } 23110 } 23111 app.curAdj = app.maxAdj; 23112 app.completedAdjSeq = app.adjSeq; 23113 // if curAdj is less than prevAppAdj, then this process was promoted 23114 return app.curAdj < prevAppAdj; 23115 } 23116 23117 app.systemNoUi = false; 23118 23119 final int PROCESS_STATE_CUR_TOP = mTopProcessState; 23120 23121 // Determine the importance of the process, starting with most 23122 // important to least, and assign an appropriate OOM adjustment. 23123 int adj; 23124 int schedGroup; 23125 int procState; 23126 int cachedAdjSeq; 23127 23128 boolean foregroundActivities = false; 23129 mTmpBroadcastQueue.clear(); 23130 if (PROCESS_STATE_CUR_TOP == ActivityManager.PROCESS_STATE_TOP && app == TOP_APP) { 23131 // The last app on the list is the foreground app. 23132 adj = ProcessList.FOREGROUND_APP_ADJ; 23133 schedGroup = ProcessList.SCHED_GROUP_TOP_APP; 23134 app.adjType = "top-activity"; 23135 foregroundActivities = true; 23136 procState = PROCESS_STATE_CUR_TOP; 23137 if (DEBUG_OOM_ADJ_REASON || logUid == appUid) { 23138 reportOomAdjMessageLocked(TAG_OOM_ADJ, "Making top: " + app); 23139 } 23140 } else if (app.runningRemoteAnimation) { 23141 adj = ProcessList.VISIBLE_APP_ADJ; 23142 schedGroup = ProcessList.SCHED_GROUP_TOP_APP; 23143 app.adjType = "running-remote-anim"; 23144 procState = PROCESS_STATE_CUR_TOP; 23145 if (DEBUG_OOM_ADJ_REASON || logUid == appUid) { 23146 reportOomAdjMessageLocked(TAG_OOM_ADJ, "Making running remote anim: " + app); 23147 } 23148 } else if (app.instr != null) { 23149 // Don't want to kill running instrumentation. 23150 adj = ProcessList.FOREGROUND_APP_ADJ; 23151 schedGroup = ProcessList.SCHED_GROUP_DEFAULT; 23152 app.adjType = "instrumentation"; 23153 procState = ActivityManager.PROCESS_STATE_FOREGROUND_SERVICE; 23154 if (DEBUG_OOM_ADJ_REASON || logUid == appUid) { 23155 reportOomAdjMessageLocked(TAG_OOM_ADJ, "Making instrumentation: " + app); 23156 } 23157 } else if (isReceivingBroadcastLocked(app, mTmpBroadcastQueue)) { 23158 // An app that is currently receiving a broadcast also 23159 // counts as being in the foreground for OOM killer purposes. 23160 // It's placed in a sched group based on the nature of the 23161 // broadcast as reflected by which queue it's active in. 23162 adj = ProcessList.FOREGROUND_APP_ADJ; 23163 schedGroup = (mTmpBroadcastQueue.contains(mFgBroadcastQueue)) 23164 ? ProcessList.SCHED_GROUP_DEFAULT : ProcessList.SCHED_GROUP_BACKGROUND; 23165 app.adjType = "broadcast"; 23166 procState = ActivityManager.PROCESS_STATE_RECEIVER; 23167 if (DEBUG_OOM_ADJ_REASON || logUid == appUid) { 23168 reportOomAdjMessageLocked(TAG_OOM_ADJ, "Making broadcast: " + app); 23169 } 23170 } else if (app.executingServices.size() > 0) { 23171 // An app that is currently executing a service callback also 23172 // counts as being in the foreground. 23173 adj = ProcessList.FOREGROUND_APP_ADJ; 23174 schedGroup = app.execServicesFg ? 23175 ProcessList.SCHED_GROUP_DEFAULT : ProcessList.SCHED_GROUP_BACKGROUND; 23176 app.adjType = "exec-service"; 23177 procState = ActivityManager.PROCESS_STATE_SERVICE; 23178 if (DEBUG_OOM_ADJ_REASON || logUid == appUid) { 23179 reportOomAdjMessageLocked(TAG_OOM_ADJ, "Making exec-service: " + app); 23180 } 23181 //Slog.i(TAG, "EXEC " + (app.execServicesFg ? "FG" : "BG") + ": " + app); 23182 } else if (app == TOP_APP) { 23183 adj = ProcessList.FOREGROUND_APP_ADJ; 23184 schedGroup = ProcessList.SCHED_GROUP_BACKGROUND; 23185 app.adjType = "top-sleeping"; 23186 foregroundActivities = true; 23187 procState = PROCESS_STATE_CUR_TOP; 23188 if (DEBUG_OOM_ADJ_REASON || logUid == appUid) { 23189 reportOomAdjMessageLocked(TAG_OOM_ADJ, "Making top (sleeping): " + app); 23190 } 23191 } else { 23192 // As far as we know the process is empty. We may change our mind later. 23193 schedGroup = ProcessList.SCHED_GROUP_BACKGROUND; 23194 // At this point we don't actually know the adjustment. Use the cached adj 23195 // value that the caller wants us to. 23196 adj = cachedAdj; 23197 procState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 23198 app.cached = true; 23199 app.empty = true; 23200 app.adjType = "cch-empty"; 23201 if (DEBUG_OOM_ADJ_REASON || logUid == appUid) { 23202 reportOomAdjMessageLocked(TAG_OOM_ADJ, "Making empty: " + app); 23203 } 23204 } 23205 23206 // Examine all activities if not already foreground. 23207 if (!foregroundActivities && activitiesSize > 0) { 23208 int minLayer = ProcessList.VISIBLE_APP_LAYER_MAX; 23209 for (int j = 0; j < activitiesSize; j++) { 23210 final ActivityRecord r = app.activities.get(j); 23211 if (r.app != app) { 23212 Log.e(TAG, "Found activity " + r + " in proc activity list using " + r.app 23213 + " instead of expected " + app); 23214 if (r.app == null || (r.app.uid == app.uid)) { 23215 // Only fix things up when they look sane 23216 r.setProcess(app); 23217 } else { 23218 continue; 23219 } 23220 } 23221 if (r.visible) { 23222 // App has a visible activity; only upgrade adjustment. 23223 if (adj > ProcessList.VISIBLE_APP_ADJ) { 23224 adj = ProcessList.VISIBLE_APP_ADJ; 23225 app.adjType = "vis-activity"; 23226 if (DEBUG_OOM_ADJ_REASON || logUid == appUid) { 23227 reportOomAdjMessageLocked(TAG_OOM_ADJ, 23228 "Raise adj to vis-activity: " + app); 23229 } 23230 } 23231 if (procState > PROCESS_STATE_CUR_TOP) { 23232 procState = PROCESS_STATE_CUR_TOP; 23233 app.adjType = "vis-activity"; 23234 if (DEBUG_OOM_ADJ_REASON || logUid == appUid) { 23235 reportOomAdjMessageLocked(TAG_OOM_ADJ, 23236 "Raise procstate to vis-activity (top): " + app); 23237 } 23238 } 23239 if (schedGroup < ProcessList.SCHED_GROUP_DEFAULT) { 23240 schedGroup = ProcessList.SCHED_GROUP_DEFAULT; 23241 } 23242 app.cached = false; 23243 app.empty = false; 23244 foregroundActivities = true; 23245 final TaskRecord task = r.getTask(); 23246 if (task != null && minLayer > 0) { 23247 final int layer = task.mLayerRank; 23248 if (layer >= 0 && minLayer > layer) { 23249 minLayer = layer; 23250 } 23251 } 23252 break; 23253 } else if (r.isState(ActivityState.PAUSING, ActivityState.PAUSED)) { 23254 if (adj > ProcessList.PERCEPTIBLE_APP_ADJ) { 23255 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 23256 app.adjType = "pause-activity"; 23257 if (DEBUG_OOM_ADJ_REASON || logUid == appUid) { 23258 reportOomAdjMessageLocked(TAG_OOM_ADJ, 23259 "Raise adj to pause-activity: " + app); 23260 } 23261 } 23262 if (procState > PROCESS_STATE_CUR_TOP) { 23263 procState = PROCESS_STATE_CUR_TOP; 23264 app.adjType = "pause-activity"; 23265 if (DEBUG_OOM_ADJ_REASON || logUid == appUid) { 23266 reportOomAdjMessageLocked(TAG_OOM_ADJ, 23267 "Raise procstate to pause-activity (top): " + app); 23268 } 23269 } 23270 if (schedGroup < ProcessList.SCHED_GROUP_DEFAULT) { 23271 schedGroup = ProcessList.SCHED_GROUP_DEFAULT; 23272 } 23273 app.cached = false; 23274 app.empty = false; 23275 foregroundActivities = true; 23276 } else if (r.isState(ActivityState.STOPPING)) { 23277 if (adj > ProcessList.PERCEPTIBLE_APP_ADJ) { 23278 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 23279 app.adjType = "stop-activity"; 23280 if (DEBUG_OOM_ADJ_REASON || logUid == appUid) { 23281 reportOomAdjMessageLocked(TAG_OOM_ADJ, 23282 "Raise adj to stop-activity: " + app); 23283 } 23284 } 23285 // For the process state, we will at this point consider the 23286 // process to be cached. It will be cached either as an activity 23287 // or empty depending on whether the activity is finishing. We do 23288 // this so that we can treat the process as cached for purposes of 23289 // memory trimming (determing current memory level, trim command to 23290 // send to process) since there can be an arbitrary number of stopping 23291 // processes and they should soon all go into the cached state. 23292 if (!r.finishing) { 23293 if (procState > ActivityManager.PROCESS_STATE_LAST_ACTIVITY) { 23294 procState = ActivityManager.PROCESS_STATE_LAST_ACTIVITY; 23295 app.adjType = "stop-activity"; 23296 if (DEBUG_OOM_ADJ_REASON || logUid == appUid) { 23297 reportOomAdjMessageLocked(TAG_OOM_ADJ, 23298 "Raise procstate to stop-activity: " + app); 23299 } 23300 } 23301 } 23302 app.cached = false; 23303 app.empty = false; 23304 foregroundActivities = true; 23305 } else { 23306 if (procState > ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 23307 procState = ActivityManager.PROCESS_STATE_CACHED_ACTIVITY; 23308 app.adjType = "cch-act"; 23309 if (DEBUG_OOM_ADJ_REASON || logUid == appUid) { 23310 reportOomAdjMessageLocked(TAG_OOM_ADJ, 23311 "Raise procstate to cached activity: " + app); 23312 } 23313 } 23314 } 23315 } 23316 if (adj == ProcessList.VISIBLE_APP_ADJ) { 23317 adj += minLayer; 23318 } 23319 } 23320 if (procState > ActivityManager.PROCESS_STATE_CACHED_RECENT && app.recentTasks.size() > 0) { 23321 procState = ActivityManager.PROCESS_STATE_CACHED_RECENT; 23322 app.adjType = "cch-rec"; 23323 if (DEBUG_OOM_ADJ_REASON || logUid == appUid) { 23324 reportOomAdjMessageLocked(TAG_OOM_ADJ, "Raise procstate to cached recent: " + app); 23325 } 23326 } 23327 23328 if (adj > ProcessList.PERCEPTIBLE_APP_ADJ 23329 || procState > ActivityManager.PROCESS_STATE_FOREGROUND_SERVICE) { 23330 if (app.foregroundServices) { 23331 // The user is aware of this app, so make it visible. 23332 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 23333 procState = ActivityManager.PROCESS_STATE_FOREGROUND_SERVICE; 23334 app.cached = false; 23335 app.adjType = "fg-service"; 23336 schedGroup = ProcessList.SCHED_GROUP_DEFAULT; 23337 if (DEBUG_OOM_ADJ_REASON || logUid == appUid) { 23338 reportOomAdjMessageLocked(TAG_OOM_ADJ, "Raise to fg service: " + app); 23339 } 23340 } else if (app.hasOverlayUi) { 23341 // The process is display an overlay UI. 23342 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 23343 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 23344 app.cached = false; 23345 app.adjType = "has-overlay-ui"; 23346 schedGroup = ProcessList.SCHED_GROUP_DEFAULT; 23347 if (DEBUG_OOM_ADJ_REASON || logUid == appUid) { 23348 reportOomAdjMessageLocked(TAG_OOM_ADJ, "Raise to overlay ui: " + app); 23349 } 23350 } 23351 } 23352 23353 if (adj > ProcessList.PERCEPTIBLE_APP_ADJ 23354 || procState > ActivityManager.PROCESS_STATE_TRANSIENT_BACKGROUND) { 23355 if (app.forcingToImportant != null) { 23356 // This is currently used for toasts... they are not interactive, and 23357 // we don't want them to cause the app to become fully foreground (and 23358 // thus out of background check), so we yes the best background level we can. 23359 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 23360 procState = ActivityManager.PROCESS_STATE_TRANSIENT_BACKGROUND; 23361 app.cached = false; 23362 app.adjType = "force-imp"; 23363 app.adjSource = app.forcingToImportant; 23364 schedGroup = ProcessList.SCHED_GROUP_DEFAULT; 23365 if (DEBUG_OOM_ADJ_REASON || logUid == appUid) { 23366 reportOomAdjMessageLocked(TAG_OOM_ADJ, "Raise to force imp: " + app); 23367 } 23368 } 23369 } 23370 23371 if (app == mHeavyWeightProcess) { 23372 if (adj > ProcessList.HEAVY_WEIGHT_APP_ADJ) { 23373 // We don't want to kill the current heavy-weight process. 23374 adj = ProcessList.HEAVY_WEIGHT_APP_ADJ; 23375 schedGroup = ProcessList.SCHED_GROUP_BACKGROUND; 23376 app.cached = false; 23377 app.adjType = "heavy"; 23378 if (DEBUG_OOM_ADJ_REASON || logUid == appUid) { 23379 reportOomAdjMessageLocked(TAG_OOM_ADJ, "Raise adj to heavy: " + app); 23380 } 23381 } 23382 if (procState > ActivityManager.PROCESS_STATE_HEAVY_WEIGHT) { 23383 procState = ActivityManager.PROCESS_STATE_HEAVY_WEIGHT; 23384 app.adjType = "heavy"; 23385 if (DEBUG_OOM_ADJ_REASON || logUid == appUid) { 23386 reportOomAdjMessageLocked(TAG_OOM_ADJ, "Raise procstate to heavy: " + app); 23387 } 23388 } 23389 } 23390 23391 if (app == mHomeProcess) { 23392 if (adj > ProcessList.HOME_APP_ADJ) { 23393 // This process is hosting what we currently consider to be the 23394 // home app, so we don't want to let it go into the background. 23395 adj = ProcessList.HOME_APP_ADJ; 23396 schedGroup = ProcessList.SCHED_GROUP_BACKGROUND; 23397 app.cached = false; 23398 app.adjType = "home"; 23399 if (DEBUG_OOM_ADJ_REASON || logUid == appUid) { 23400 reportOomAdjMessageLocked(TAG_OOM_ADJ, "Raise adj to home: " + app); 23401 } 23402 } 23403 if (procState > ActivityManager.PROCESS_STATE_HOME) { 23404 procState = ActivityManager.PROCESS_STATE_HOME; 23405 app.adjType = "home"; 23406 if (DEBUG_OOM_ADJ_REASON || logUid == appUid) { 23407 reportOomAdjMessageLocked(TAG_OOM_ADJ, "Raise procstate to home: " + app); 23408 } 23409 } 23410 } 23411 23412 if (app == mPreviousProcess && app.activities.size() > 0) { 23413 if (adj > ProcessList.PREVIOUS_APP_ADJ) { 23414 // This was the previous process that showed UI to the user. 23415 // We want to try to keep it around more aggressively, to give 23416 // a good experience around switching between two apps. 23417 adj = ProcessList.PREVIOUS_APP_ADJ; 23418 schedGroup = ProcessList.SCHED_GROUP_BACKGROUND; 23419 app.cached = false; 23420 app.adjType = "previous"; 23421 if (DEBUG_OOM_ADJ_REASON || logUid == appUid) { 23422 reportOomAdjMessageLocked(TAG_OOM_ADJ, "Raise adj to prev: " + app); 23423 } 23424 } 23425 if (procState > ActivityManager.PROCESS_STATE_LAST_ACTIVITY) { 23426 procState = ActivityManager.PROCESS_STATE_LAST_ACTIVITY; 23427 app.adjType = "previous"; 23428 if (DEBUG_OOM_ADJ_REASON || logUid == appUid) { 23429 reportOomAdjMessageLocked(TAG_OOM_ADJ, "Raise procstate to prev: " + app); 23430 } 23431 } 23432 } 23433 23434 if (false) Slog.i(TAG, "OOM " + app + ": initial adj=" + adj 23435 + " reason=" + app.adjType); 23436 23437 // By default, we use the computed adjustment. It may be changed if 23438 // there are applications dependent on our services or providers, but 23439 // this gives us a baseline and makes sure we don't get into an 23440 // infinite recursion. 23441 app.curRawAdj = adj; 23442 app.hasStartedServices = false; 23443 app.adjSeq = mAdjSeq; 23444 23445 if (mBackupTarget != null && app == mBackupTarget.app) { 23446 // If possible we want to avoid killing apps while they're being backed up 23447 if (adj > ProcessList.BACKUP_APP_ADJ) { 23448 if (DEBUG_BACKUP) Slog.v(TAG_BACKUP, "oom BACKUP_APP_ADJ for " + app); 23449 adj = ProcessList.BACKUP_APP_ADJ; 23450 if (procState > ActivityManager.PROCESS_STATE_TRANSIENT_BACKGROUND) { 23451 procState = ActivityManager.PROCESS_STATE_TRANSIENT_BACKGROUND; 23452 } 23453 app.adjType = "backup"; 23454 if (DEBUG_OOM_ADJ_REASON || logUid == appUid) { 23455 reportOomAdjMessageLocked(TAG_OOM_ADJ, "Raise adj to backup: " + app); 23456 } 23457 app.cached = false; 23458 } 23459 if (procState > ActivityManager.PROCESS_STATE_BACKUP) { 23460 procState = ActivityManager.PROCESS_STATE_BACKUP; 23461 app.adjType = "backup"; 23462 if (DEBUG_OOM_ADJ_REASON || logUid == appUid) { 23463 reportOomAdjMessageLocked(TAG_OOM_ADJ, "Raise procstate to backup: " + app); 23464 } 23465 } 23466 } 23467 23468 boolean mayBeTop = false; 23469 String mayBeTopType = null; 23470 Object mayBeTopSource = null; 23471 Object mayBeTopTarget = null; 23472 23473 for (int is = app.services.size()-1; 23474 is >= 0 && (adj > ProcessList.FOREGROUND_APP_ADJ 23475 || schedGroup == ProcessList.SCHED_GROUP_BACKGROUND 23476 || procState > ActivityManager.PROCESS_STATE_TOP); 23477 is--) { 23478 ServiceRecord s = app.services.valueAt(is); 23479 if (s.startRequested) { 23480 app.hasStartedServices = true; 23481 if (procState > ActivityManager.PROCESS_STATE_SERVICE) { 23482 procState = ActivityManager.PROCESS_STATE_SERVICE; 23483 app.adjType = "started-services"; 23484 if (DEBUG_OOM_ADJ_REASON || logUid == appUid) { 23485 reportOomAdjMessageLocked(TAG_OOM_ADJ, 23486 "Raise procstate to started service: " + app); 23487 } 23488 } 23489 if (app.hasShownUi && app != mHomeProcess) { 23490 // If this process has shown some UI, let it immediately 23491 // go to the LRU list because it may be pretty heavy with 23492 // UI stuff. We'll tag it with a label just to help 23493 // debug and understand what is going on. 23494 if (adj > ProcessList.SERVICE_ADJ) { 23495 app.adjType = "cch-started-ui-services"; 23496 } 23497 } else { 23498 if (now < (s.lastActivity + mConstants.MAX_SERVICE_INACTIVITY)) { 23499 // This service has seen some activity within 23500 // recent memory, so we will keep its process ahead 23501 // of the background processes. 23502 if (adj > ProcessList.SERVICE_ADJ) { 23503 adj = ProcessList.SERVICE_ADJ; 23504 app.adjType = "started-services"; 23505 if (DEBUG_OOM_ADJ_REASON || logUid == appUid) { 23506 reportOomAdjMessageLocked(TAG_OOM_ADJ, 23507 "Raise adj to started service: " + app); 23508 } 23509 app.cached = false; 23510 } 23511 } 23512 // If we have let the service slide into the background 23513 // state, still have some text describing what it is doing 23514 // even though the service no longer has an impact. 23515 if (adj > ProcessList.SERVICE_ADJ) { 23516 app.adjType = "cch-started-services"; 23517 } 23518 } 23519 } 23520 23521 for (int conni = s.connections.size()-1; 23522 conni >= 0 && (adj > ProcessList.FOREGROUND_APP_ADJ 23523 || schedGroup == ProcessList.SCHED_GROUP_BACKGROUND 23524 || procState > ActivityManager.PROCESS_STATE_TOP); 23525 conni--) { 23526 ArrayList<ConnectionRecord> clist = s.connections.valueAt(conni); 23527 for (int i = 0; 23528 i < clist.size() && (adj > ProcessList.FOREGROUND_APP_ADJ 23529 || schedGroup == ProcessList.SCHED_GROUP_BACKGROUND 23530 || procState > ActivityManager.PROCESS_STATE_TOP); 23531 i++) { 23532 // XXX should compute this based on the max of 23533 // all connected clients. 23534 ConnectionRecord cr = clist.get(i); 23535 if (cr.binding.client == app) { 23536 // Binding to ourself is not interesting. 23537 continue; 23538 } 23539 23540 if ((cr.flags&Context.BIND_WAIVE_PRIORITY) == 0) { 23541 ProcessRecord client = cr.binding.client; 23542 computeOomAdjLocked(client, cachedAdj, TOP_APP, doingAll, now); 23543 if (client.containsCycle) { 23544 // We've detected a cycle. We should ignore this connection and allow 23545 // this process to retry computeOomAdjLocked later in case a later-checked 23546 // connection from a client would raise its priority legitimately. 23547 app.containsCycle = true; 23548 continue; 23549 } 23550 int clientAdj = client.curRawAdj; 23551 int clientProcState = client.curProcState; 23552 if (clientProcState >= ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 23553 // If the other app is cached for any reason, for purposes here 23554 // we are going to consider it empty. The specific cached state 23555 // doesn't propagate except under certain conditions. 23556 clientProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 23557 } 23558 String adjType = null; 23559 if ((cr.flags&Context.BIND_ALLOW_OOM_MANAGEMENT) != 0) { 23560 // Not doing bind OOM management, so treat 23561 // this guy more like a started service. 23562 if (app.hasShownUi && app != mHomeProcess) { 23563 // If this process has shown some UI, let it immediately 23564 // go to the LRU list because it may be pretty heavy with 23565 // UI stuff. We'll tag it with a label just to help 23566 // debug and understand what is going on. 23567 if (adj > clientAdj) { 23568 adjType = "cch-bound-ui-services"; 23569 } 23570 app.cached = false; 23571 clientAdj = adj; 23572 clientProcState = procState; 23573 } else { 23574 if (now >= (s.lastActivity + mConstants.MAX_SERVICE_INACTIVITY)) { 23575 // This service has not seen activity within 23576 // recent memory, so allow it to drop to the 23577 // LRU list if there is no other reason to keep 23578 // it around. We'll also tag it with a label just 23579 // to help debug and undertand what is going on. 23580 if (adj > clientAdj) { 23581 adjType = "cch-bound-services"; 23582 } 23583 clientAdj = adj; 23584 } 23585 } 23586 } 23587 if (adj > clientAdj) { 23588 // If this process has recently shown UI, and 23589 // the process that is binding to it is less 23590 // important than being visible, then we don't 23591 // care about the binding as much as we care 23592 // about letting this process get into the LRU 23593 // list to be killed and restarted if needed for 23594 // memory. 23595 if (app.hasShownUi && app != mHomeProcess 23596 && clientAdj > ProcessList.PERCEPTIBLE_APP_ADJ) { 23597 if (adj >= ProcessList.CACHED_APP_MIN_ADJ) { 23598 adjType = "cch-bound-ui-services"; 23599 } 23600 } else { 23601 int newAdj; 23602 if ((cr.flags&(Context.BIND_ABOVE_CLIENT 23603 |Context.BIND_IMPORTANT)) != 0) { 23604 if (clientAdj >= ProcessList.PERSISTENT_SERVICE_ADJ) { 23605 newAdj = clientAdj; 23606 } else { 23607 // make this service persistent 23608 newAdj = ProcessList.PERSISTENT_SERVICE_ADJ; 23609 schedGroup = ProcessList.SCHED_GROUP_DEFAULT; 23610 procState = ActivityManager.PROCESS_STATE_PERSISTENT; 23611 } 23612 } else if ((cr.flags&Context.BIND_NOT_VISIBLE) != 0 23613 && clientAdj < ProcessList.PERCEPTIBLE_APP_ADJ 23614 && adj > ProcessList.PERCEPTIBLE_APP_ADJ) { 23615 newAdj = ProcessList.PERCEPTIBLE_APP_ADJ; 23616 } else if (clientAdj >= ProcessList.PERCEPTIBLE_APP_ADJ) { 23617 newAdj = clientAdj; 23618 } else { 23619 if (adj > ProcessList.VISIBLE_APP_ADJ) { 23620 newAdj = Math.max(clientAdj, ProcessList.VISIBLE_APP_ADJ); 23621 } else { 23622 newAdj = adj; 23623 } 23624 } 23625 if (!client.cached) { 23626 app.cached = false; 23627 } 23628 if (adj > newAdj) { 23629 adj = newAdj; 23630 adjType = "service"; 23631 } 23632 } 23633 } 23634 if ((cr.flags & (Context.BIND_NOT_FOREGROUND 23635 | Context.BIND_IMPORTANT_BACKGROUND)) == 0) { 23636 // This will treat important bound services identically to 23637 // the top app, which may behave differently than generic 23638 // foreground work. 23639 if (client.curSchedGroup > schedGroup) { 23640 if ((cr.flags&Context.BIND_IMPORTANT) != 0) { 23641 schedGroup = client.curSchedGroup; 23642 } else { 23643 schedGroup = ProcessList.SCHED_GROUP_DEFAULT; 23644 } 23645 } 23646 if (clientProcState <= ActivityManager.PROCESS_STATE_TOP) { 23647 if (clientProcState == ActivityManager.PROCESS_STATE_TOP) { 23648 // Special handling of clients who are in the top state. 23649 // We *may* want to consider this process to be in the 23650 // top state as well, but only if there is not another 23651 // reason for it to be running. Being on the top is a 23652 // special state, meaning you are specifically running 23653 // for the current top app. If the process is already 23654 // running in the background for some other reason, it 23655 // is more important to continue considering it to be 23656 // in the background state. 23657 mayBeTop = true; 23658 mayBeTopType = "service"; 23659 mayBeTopSource = cr.binding.client; 23660 mayBeTopTarget = s.name; 23661 clientProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 23662 } else { 23663 // Special handling for above-top states (persistent 23664 // processes). These should not bring the current process 23665 // into the top state, since they are not on top. Instead 23666 // give them the best state after that. 23667 if ((cr.flags&Context.BIND_FOREGROUND_SERVICE) != 0) { 23668 clientProcState = 23669 ActivityManager.PROCESS_STATE_BOUND_FOREGROUND_SERVICE; 23670 } else if (mWakefulness 23671 == PowerManagerInternal.WAKEFULNESS_AWAKE && 23672 (cr.flags&Context.BIND_FOREGROUND_SERVICE_WHILE_AWAKE) 23673 != 0) { 23674 clientProcState = 23675 ActivityManager.PROCESS_STATE_BOUND_FOREGROUND_SERVICE; 23676 } else { 23677 clientProcState = 23678 ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 23679 } 23680 } 23681 } 23682 } else if ((cr.flags & Context.BIND_IMPORTANT_BACKGROUND) == 0) { 23683 if (clientProcState < 23684 ActivityManager.PROCESS_STATE_TRANSIENT_BACKGROUND) { 23685 clientProcState = 23686 ActivityManager.PROCESS_STATE_TRANSIENT_BACKGROUND; 23687 } 23688 } else { 23689 if (clientProcState < 23690 ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND) { 23691 clientProcState = 23692 ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND; 23693 } 23694 } 23695 if (procState > clientProcState) { 23696 procState = clientProcState; 23697 if (adjType == null) { 23698 adjType = "service"; 23699 } 23700 } 23701 if (procState < ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND 23702 && (cr.flags&Context.BIND_SHOWING_UI) != 0) { 23703 app.pendingUiClean = true; 23704 } 23705 if (adjType != null) { 23706 app.adjType = adjType; 23707 app.adjTypeCode = ActivityManager.RunningAppProcessInfo 23708 .REASON_SERVICE_IN_USE; 23709 app.adjSource = cr.binding.client; 23710 app.adjSourceProcState = clientProcState; 23711 app.adjTarget = s.name; 23712 if (DEBUG_OOM_ADJ_REASON || logUid == appUid) { 23713 reportOomAdjMessageLocked(TAG_OOM_ADJ, "Raise to " + adjType 23714 + ": " + app + ", due to " + cr.binding.client 23715 + " adj=" + adj + " procState=" 23716 + ProcessList.makeProcStateString(procState)); 23717 } 23718 } 23719 } 23720 if ((cr.flags&Context.BIND_TREAT_LIKE_ACTIVITY) != 0) { 23721 app.treatLikeActivity = true; 23722 } 23723 final ActivityRecord a = cr.activity; 23724 if ((cr.flags&Context.BIND_ADJUST_WITH_ACTIVITY) != 0) { 23725 if (a != null && adj > ProcessList.FOREGROUND_APP_ADJ && (a.visible 23726 || a.isState(ActivityState.RESUMED, ActivityState.PAUSING))) { 23727 adj = ProcessList.FOREGROUND_APP_ADJ; 23728 if ((cr.flags&Context.BIND_NOT_FOREGROUND) == 0) { 23729 if ((cr.flags&Context.BIND_IMPORTANT) != 0) { 23730 schedGroup = ProcessList.SCHED_GROUP_TOP_APP_BOUND; 23731 } else { 23732 schedGroup = ProcessList.SCHED_GROUP_DEFAULT; 23733 } 23734 } 23735 app.cached = false; 23736 app.adjType = "service"; 23737 app.adjTypeCode = ActivityManager.RunningAppProcessInfo 23738 .REASON_SERVICE_IN_USE; 23739 app.adjSource = a; 23740 app.adjSourceProcState = procState; 23741 app.adjTarget = s.name; 23742 if (DEBUG_OOM_ADJ_REASON || logUid == appUid) { 23743 reportOomAdjMessageLocked(TAG_OOM_ADJ, 23744 "Raise to service w/activity: " + app); 23745 } 23746 } 23747 } 23748 } 23749 } 23750 } 23751 23752 for (int provi = app.pubProviders.size()-1; 23753 provi >= 0 && (adj > ProcessList.FOREGROUND_APP_ADJ 23754 || schedGroup == ProcessList.SCHED_GROUP_BACKGROUND 23755 || procState > ActivityManager.PROCESS_STATE_TOP); 23756 provi--) { 23757 ContentProviderRecord cpr = app.pubProviders.valueAt(provi); 23758 for (int i = cpr.connections.size()-1; 23759 i >= 0 && (adj > ProcessList.FOREGROUND_APP_ADJ 23760 || schedGroup == ProcessList.SCHED_GROUP_BACKGROUND 23761 || procState > ActivityManager.PROCESS_STATE_TOP); 23762 i--) { 23763 ContentProviderConnection conn = cpr.connections.get(i); 23764 ProcessRecord client = conn.client; 23765 if (client == app) { 23766 // Being our own client is not interesting. 23767 continue; 23768 } 23769 computeOomAdjLocked(client, cachedAdj, TOP_APP, doingAll, now); 23770 if (client.containsCycle) { 23771 // We've detected a cycle. We should ignore this connection and allow 23772 // this process to retry computeOomAdjLocked later in case a later-checked 23773 // connection from a client would raise its priority legitimately. 23774 app.containsCycle = true; 23775 continue; 23776 } 23777 int clientAdj = client.curRawAdj; 23778 int clientProcState = client.curProcState; 23779 if (clientProcState >= ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 23780 // If the other app is cached for any reason, for purposes here 23781 // we are going to consider it empty. 23782 clientProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 23783 } 23784 String adjType = null; 23785 if (adj > clientAdj) { 23786 if (app.hasShownUi && app != mHomeProcess 23787 && clientAdj > ProcessList.PERCEPTIBLE_APP_ADJ) { 23788 adjType = "cch-ui-provider"; 23789 } else { 23790 adj = clientAdj > ProcessList.FOREGROUND_APP_ADJ 23791 ? clientAdj : ProcessList.FOREGROUND_APP_ADJ; 23792 adjType = "provider"; 23793 } 23794 app.cached &= client.cached; 23795 } 23796 if (clientProcState <= ActivityManager.PROCESS_STATE_TOP) { 23797 if (clientProcState == ActivityManager.PROCESS_STATE_TOP) { 23798 // Special handling of clients who are in the top state. 23799 // We *may* want to consider this process to be in the 23800 // top state as well, but only if there is not another 23801 // reason for it to be running. Being on the top is a 23802 // special state, meaning you are specifically running 23803 // for the current top app. If the process is already 23804 // running in the background for some other reason, it 23805 // is more important to continue considering it to be 23806 // in the background state. 23807 mayBeTop = true; 23808 clientProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 23809 mayBeTopType = adjType = "provider-top"; 23810 mayBeTopSource = client; 23811 mayBeTopTarget = cpr.name; 23812 } else { 23813 // Special handling for above-top states (persistent 23814 // processes). These should not bring the current process 23815 // into the top state, since they are not on top. Instead 23816 // give them the best state after that. 23817 clientProcState = 23818 ActivityManager.PROCESS_STATE_BOUND_FOREGROUND_SERVICE; 23819 if (adjType == null) { 23820 adjType = "provider"; 23821 } 23822 } 23823 } 23824 if (procState > clientProcState) { 23825 procState = clientProcState; 23826 } 23827 if (client.curSchedGroup > schedGroup) { 23828 schedGroup = ProcessList.SCHED_GROUP_DEFAULT; 23829 } 23830 if (adjType != null) { 23831 app.adjType = adjType; 23832 app.adjTypeCode = ActivityManager.RunningAppProcessInfo 23833 .REASON_PROVIDER_IN_USE; 23834 app.adjSource = client; 23835 app.adjSourceProcState = clientProcState; 23836 app.adjTarget = cpr.name; 23837 if (DEBUG_OOM_ADJ_REASON || logUid == appUid) { 23838 reportOomAdjMessageLocked(TAG_OOM_ADJ, "Raise to " + adjType 23839 + ": " + app + ", due to " + client 23840 + " adj=" + adj + " procState=" 23841 + ProcessList.makeProcStateString(procState)); 23842 } 23843 } 23844 } 23845 // If the provider has external (non-framework) process 23846 // dependencies, ensure that its adjustment is at least 23847 // FOREGROUND_APP_ADJ. 23848 if (cpr.hasExternalProcessHandles()) { 23849 if (adj > ProcessList.FOREGROUND_APP_ADJ) { 23850 adj = ProcessList.FOREGROUND_APP_ADJ; 23851 schedGroup = ProcessList.SCHED_GROUP_DEFAULT; 23852 app.cached = false; 23853 app.adjType = "ext-provider"; 23854 app.adjTarget = cpr.name; 23855 if (DEBUG_OOM_ADJ_REASON || logUid == appUid) { 23856 reportOomAdjMessageLocked(TAG_OOM_ADJ, 23857 "Raise adj to external provider: " + app); 23858 } 23859 } 23860 if (procState > ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND) { 23861 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 23862 reportOomAdjMessageLocked(TAG_OOM_ADJ, 23863 "Raise procstate to external provider: " + app); 23864 } 23865 } 23866 } 23867 23868 if (app.lastProviderTime > 0 && 23869 (app.lastProviderTime+mConstants.CONTENT_PROVIDER_RETAIN_TIME) > now) { 23870 if (adj > ProcessList.PREVIOUS_APP_ADJ) { 23871 adj = ProcessList.PREVIOUS_APP_ADJ; 23872 schedGroup = ProcessList.SCHED_GROUP_BACKGROUND; 23873 app.cached = false; 23874 app.adjType = "recent-provider"; 23875 if (DEBUG_OOM_ADJ_REASON || logUid == appUid) { 23876 reportOomAdjMessageLocked(TAG_OOM_ADJ, 23877 "Raise adj to recent provider: " + app); 23878 } 23879 } 23880 if (procState > ActivityManager.PROCESS_STATE_LAST_ACTIVITY) { 23881 procState = ActivityManager.PROCESS_STATE_LAST_ACTIVITY; 23882 app.adjType = "recent-provider"; 23883 if (DEBUG_OOM_ADJ_REASON || logUid == appUid) { 23884 reportOomAdjMessageLocked(TAG_OOM_ADJ, 23885 "Raise procstate to recent provider: " + app); 23886 } 23887 } 23888 } 23889 23890 if (mayBeTop && procState > ActivityManager.PROCESS_STATE_TOP) { 23891 // A client of one of our services or providers is in the top state. We 23892 // *may* want to be in the top state, but not if we are already running in 23893 // the background for some other reason. For the decision here, we are going 23894 // to pick out a few specific states that we want to remain in when a client 23895 // is top (states that tend to be longer-term) and otherwise allow it to go 23896 // to the top state. 23897 switch (procState) { 23898 case ActivityManager.PROCESS_STATE_BOUND_FOREGROUND_SERVICE: 23899 case ActivityManager.PROCESS_STATE_FOREGROUND_SERVICE: 23900 // Something else is keeping it at this level, just leave it. 23901 break; 23902 case ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND: 23903 case ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND: 23904 case ActivityManager.PROCESS_STATE_TRANSIENT_BACKGROUND: 23905 case ActivityManager.PROCESS_STATE_SERVICE: 23906 // These all are longer-term states, so pull them up to the top 23907 // of the background states, but not all the way to the top state. 23908 procState = ActivityManager.PROCESS_STATE_BOUND_FOREGROUND_SERVICE; 23909 app.adjType = mayBeTopType; 23910 app.adjSource = mayBeTopSource; 23911 app.adjTarget = mayBeTopTarget; 23912 if (DEBUG_OOM_ADJ_REASON || logUid == appUid) { 23913 reportOomAdjMessageLocked(TAG_OOM_ADJ, "May be top raise to " + mayBeTopType 23914 + ": " + app + ", due to " + mayBeTopSource 23915 + " adj=" + adj + " procState=" 23916 + ProcessList.makeProcStateString(procState)); 23917 } 23918 break; 23919 default: 23920 // Otherwise, top is a better choice, so take it. 23921 procState = ActivityManager.PROCESS_STATE_TOP; 23922 app.adjType = mayBeTopType; 23923 app.adjSource = mayBeTopSource; 23924 app.adjTarget = mayBeTopTarget; 23925 if (DEBUG_OOM_ADJ_REASON || logUid == appUid) { 23926 reportOomAdjMessageLocked(TAG_OOM_ADJ, "May be top raise to " + mayBeTopType 23927 + ": " + app + ", due to " + mayBeTopSource 23928 + " adj=" + adj + " procState=" 23929 + ProcessList.makeProcStateString(procState)); 23930 } 23931 break; 23932 } 23933 } 23934 23935 if (procState >= ActivityManager.PROCESS_STATE_CACHED_EMPTY) { 23936 if (app.hasClientActivities) { 23937 // This is a cached process, but with client activities. Mark it so. 23938 procState = ActivityManager.PROCESS_STATE_CACHED_ACTIVITY_CLIENT; 23939 app.adjType = "cch-client-act"; 23940 } else if (app.treatLikeActivity) { 23941 // This is a cached process, but somebody wants us to treat it like it has 23942 // an activity, okay! 23943 procState = ActivityManager.PROCESS_STATE_CACHED_ACTIVITY; 23944 app.adjType = "cch-as-act"; 23945 } 23946 } 23947 23948 if (adj == ProcessList.SERVICE_ADJ) { 23949 if (doingAll) { 23950 app.serviceb = mNewNumAServiceProcs > (mNumServiceProcs/3); 23951 mNewNumServiceProcs++; 23952 //Slog.i(TAG, "ADJ " + app + " serviceb=" + app.serviceb); 23953 if (!app.serviceb) { 23954 // This service isn't far enough down on the LRU list to 23955 // normally be a B service, but if we are low on RAM and it 23956 // is large we want to force it down since we would prefer to 23957 // keep launcher over it. 23958 if (mLastMemoryLevel > ProcessStats.ADJ_MEM_FACTOR_NORMAL 23959 && app.lastPss >= mProcessList.getCachedRestoreThresholdKb()) { 23960 app.serviceHighRam = true; 23961 app.serviceb = true; 23962 //Slog.i(TAG, "ADJ " + app + " high ram!"); 23963 } else { 23964 mNewNumAServiceProcs++; 23965 //Slog.i(TAG, "ADJ " + app + " not high ram!"); 23966 } 23967 } else { 23968 app.serviceHighRam = false; 23969 } 23970 } 23971 if (app.serviceb) { 23972 adj = ProcessList.SERVICE_B_ADJ; 23973 } 23974 } 23975 23976 app.curRawAdj = adj; 23977 23978 //Slog.i(TAG, "OOM ADJ " + app + ": pid=" + app.pid + 23979 // " adj=" + adj + " curAdj=" + app.curAdj + " maxAdj=" + app.maxAdj); 23980 if (adj > app.maxAdj) { 23981 adj = app.maxAdj; 23982 if (app.maxAdj <= ProcessList.PERCEPTIBLE_APP_ADJ) { 23983 schedGroup = ProcessList.SCHED_GROUP_DEFAULT; 23984 } 23985 } 23986 23987 // Put bound foreground services in a special sched group for additional 23988 // restrictions on screen off 23989 if (procState >= ActivityManager.PROCESS_STATE_BOUND_FOREGROUND_SERVICE && 23990 mWakefulness != PowerManagerInternal.WAKEFULNESS_AWAKE) { 23991 if (schedGroup > ProcessList.SCHED_GROUP_RESTRICTED) { 23992 schedGroup = ProcessList.SCHED_GROUP_RESTRICTED; 23993 } 23994 } 23995 23996 // Do final modification to adj. Everything we do between here and applying 23997 // the final setAdj must be done in this function, because we will also use 23998 // it when computing the final cached adj later. Note that we don't need to 23999 // worry about this for max adj above, since max adj will always be used to 24000 // keep it out of the cached vaues. 24001 app.curAdj = app.modifyRawOomAdj(adj); 24002 app.curSchedGroup = schedGroup; 24003 app.curProcState = procState; 24004 app.foregroundActivities = foregroundActivities; 24005 app.completedAdjSeq = mAdjSeq; 24006 24007 // if curAdj is less than prevAppAdj, then this process was promoted 24008 return app.curAdj < prevAppAdj; 24009 } 24010 24011 /** 24012 * Record new PSS sample for a process. 24013 */ 24014 void recordPssSampleLocked(ProcessRecord proc, int procState, long pss, long uss, long swapPss, 24015 long rss, int statType, long pssDuration, long now) { 24016 EventLogTags.writeAmPss(proc.pid, proc.uid, proc.processName, pss * 1024, uss * 1024, 24017 swapPss * 1024, rss * 1024, statType, procState, pssDuration); 24018 proc.lastPssTime = now; 24019 proc.baseProcessTracker.addPss(pss, uss, rss, true, statType, pssDuration, proc.pkgList); 24020 if (DEBUG_PSS) Slog.d(TAG_PSS, 24021 "pss of " + proc.toShortString() + ": " + pss + " lastPss=" + proc.lastPss 24022 + " state=" + ProcessList.makeProcStateString(procState)); 24023 if (proc.initialIdlePss == 0) { 24024 proc.initialIdlePss = pss; 24025 } 24026 proc.lastPss = pss; 24027 proc.lastSwapPss = swapPss; 24028 if (procState >= ActivityManager.PROCESS_STATE_HOME) { 24029 proc.lastCachedPss = pss; 24030 proc.lastCachedSwapPss = swapPss; 24031 } 24032 24033 final SparseArray<Pair<Long, String>> watchUids 24034 = mMemWatchProcesses.getMap().get(proc.processName); 24035 Long check = null; 24036 if (watchUids != null) { 24037 Pair<Long, String> val = watchUids.get(proc.uid); 24038 if (val == null) { 24039 val = watchUids.get(0); 24040 } 24041 if (val != null) { 24042 check = val.first; 24043 } 24044 } 24045 if (check != null) { 24046 if ((pss * 1024) >= check && proc.thread != null && mMemWatchDumpProcName == null) { 24047 boolean isDebuggable = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 24048 if (!isDebuggable) { 24049 if ((proc.info.flags&ApplicationInfo.FLAG_DEBUGGABLE) != 0) { 24050 isDebuggable = true; 24051 } 24052 } 24053 if (isDebuggable) { 24054 Slog.w(TAG, "Process " + proc + " exceeded pss limit " + check + "; reporting"); 24055 final ProcessRecord myProc = proc; 24056 final File heapdumpFile = DumpHeapProvider.getJavaFile(); 24057 mMemWatchDumpProcName = proc.processName; 24058 mMemWatchDumpFile = heapdumpFile.toString(); 24059 mMemWatchDumpPid = proc.pid; 24060 mMemWatchDumpUid = proc.uid; 24061 BackgroundThread.getHandler().post(new Runnable() { 24062 @Override 24063 public void run() { 24064 revokeUriPermission(ActivityThread.currentActivityThread() 24065 .getApplicationThread(), 24066 null, DumpHeapActivity.JAVA_URI, 24067 Intent.FLAG_GRANT_READ_URI_PERMISSION 24068 | Intent.FLAG_GRANT_WRITE_URI_PERMISSION, 24069 UserHandle.myUserId()); 24070 ParcelFileDescriptor fd = null; 24071 try { 24072 heapdumpFile.delete(); 24073 fd = ParcelFileDescriptor.open(heapdumpFile, 24074 ParcelFileDescriptor.MODE_CREATE | 24075 ParcelFileDescriptor.MODE_TRUNCATE | 24076 ParcelFileDescriptor.MODE_WRITE_ONLY | 24077 ParcelFileDescriptor.MODE_APPEND); 24078 IApplicationThread thread = myProc.thread; 24079 if (thread != null) { 24080 try { 24081 if (DEBUG_PSS) Slog.d(TAG_PSS, 24082 "Requesting dump heap from " 24083 + myProc + " to " + heapdumpFile); 24084 thread.dumpHeap(/* managed= */ true, 24085 /* mallocInfo= */ false, /* runGc= */ false, 24086 heapdumpFile.toString(), fd); 24087 } catch (RemoteException e) { 24088 } 24089 } 24090 } catch (FileNotFoundException e) { 24091 e.printStackTrace(); 24092 } finally { 24093 if (fd != null) { 24094 try { 24095 fd.close(); 24096 } catch (IOException e) { 24097 } 24098 } 24099 } 24100 } 24101 }); 24102 } else { 24103 Slog.w(TAG, "Process " + proc + " exceeded pss limit " + check 24104 + ", but debugging not enabled"); 24105 } 24106 } 24107 } 24108 } 24109 24110 /** 24111 * Schedule PSS collection of a process. 24112 */ 24113 boolean requestPssLocked(ProcessRecord proc, int procState) { 24114 if (mPendingPssProcesses.contains(proc)) { 24115 return false; 24116 } 24117 if (mPendingPssProcesses.size() == 0) { 24118 mBgHandler.sendEmptyMessage(COLLECT_PSS_BG_MSG); 24119 } 24120 if (DEBUG_PSS) Slog.d(TAG_PSS, "Requesting pss of: " + proc); 24121 proc.pssProcState = procState; 24122 proc.pssStatType = ProcessStats.ADD_PSS_INTERNAL_SINGLE; 24123 mPendingPssProcesses.add(proc); 24124 return true; 24125 } 24126 24127 /** 24128 * Schedule PSS collection of all processes. 24129 */ 24130 void requestPssAllProcsLocked(long now, boolean always, boolean memLowered) { 24131 if (!always) { 24132 if (now < (mLastFullPssTime + 24133 (memLowered ? mConstants.FULL_PSS_LOWERED_INTERVAL 24134 : mConstants.FULL_PSS_MIN_INTERVAL))) { 24135 return; 24136 } 24137 } 24138 if (DEBUG_PSS) Slog.d(TAG_PSS, "Requesting pss of all procs! memLowered=" + memLowered); 24139 mLastFullPssTime = now; 24140 mFullPssPending = true; 24141 for (int i = mPendingPssProcesses.size() - 1; i >= 0; i--) { 24142 ProcessList.abortNextPssTime(mPendingPssProcesses.get(i).procStateMemTracker);; 24143 } 24144 mPendingPssProcesses.ensureCapacity(mLruProcesses.size()); 24145 mPendingPssProcesses.clear(); 24146 for (int i = mLruProcesses.size() - 1; i >= 0; i--) { 24147 ProcessRecord app = mLruProcesses.get(i); 24148 if (app.thread == null 24149 || app.curProcState == ActivityManager.PROCESS_STATE_NONEXISTENT) { 24150 continue; 24151 } 24152 if (memLowered || (always && now > 24153 app.lastStateTime+ProcessList.PSS_SAFE_TIME_FROM_STATE_CHANGE) 24154 || now > (app.lastStateTime+ProcessList.PSS_ALL_INTERVAL)) { 24155 app.pssProcState = app.setProcState; 24156 app.pssStatType = always ? ProcessStats.ADD_PSS_INTERNAL_ALL_POLL 24157 : ProcessStats.ADD_PSS_INTERNAL_ALL_MEM; 24158 app.nextPssTime = ProcessList.computeNextPssTime(app.curProcState, 24159 app.procStateMemTracker, mTestPssMode, isSleepingLocked(), now); 24160 mPendingPssProcesses.add(app); 24161 } 24162 } 24163 if (!mBgHandler.hasMessages(COLLECT_PSS_BG_MSG)) { 24164 mBgHandler.sendEmptyMessage(COLLECT_PSS_BG_MSG); 24165 } 24166 } 24167 24168 public void setTestPssMode(boolean enabled) { 24169 synchronized (this) { 24170 mTestPssMode = enabled; 24171 if (enabled) { 24172 // Whenever we enable the mode, we want to take a snapshot all of current 24173 // process mem use. 24174 requestPssAllProcsLocked(SystemClock.uptimeMillis(), true, true); 24175 } 24176 } 24177 } 24178 24179 /** 24180 * Ask a given process to GC right now. 24181 */ 24182 final void performAppGcLocked(ProcessRecord app) { 24183 try { 24184 app.lastRequestedGc = SystemClock.uptimeMillis(); 24185 if (app.thread != null) { 24186 if (app.reportLowMemory) { 24187 app.reportLowMemory = false; 24188 app.thread.scheduleLowMemory(); 24189 } else { 24190 app.thread.processInBackground(); 24191 } 24192 } 24193 } catch (Exception e) { 24194 // whatever. 24195 } 24196 } 24197 24198 /** 24199 * Returns true if things are idle enough to perform GCs. 24200 */ 24201 private final boolean canGcNowLocked() { 24202 boolean processingBroadcasts = false; 24203 for (BroadcastQueue q : mBroadcastQueues) { 24204 if (q.mParallelBroadcasts.size() != 0 || q.mOrderedBroadcasts.size() != 0) { 24205 processingBroadcasts = true; 24206 } 24207 } 24208 return !processingBroadcasts 24209 && (isSleepingLocked() || mStackSupervisor.allResumedActivitiesIdle()); 24210 } 24211 24212 /** 24213 * Perform GCs on all processes that are waiting for it, but only 24214 * if things are idle. 24215 */ 24216 final void performAppGcsLocked() { 24217 final int N = mProcessesToGc.size(); 24218 if (N <= 0) { 24219 return; 24220 } 24221 if (canGcNowLocked()) { 24222 while (mProcessesToGc.size() > 0) { 24223 ProcessRecord proc = mProcessesToGc.remove(0); 24224 if (proc.curRawAdj > ProcessList.PERCEPTIBLE_APP_ADJ || proc.reportLowMemory) { 24225 if ((proc.lastRequestedGc+mConstants.GC_MIN_INTERVAL) 24226 <= SystemClock.uptimeMillis()) { 24227 // To avoid spamming the system, we will GC processes one 24228 // at a time, waiting a few seconds between each. 24229 performAppGcLocked(proc); 24230 scheduleAppGcsLocked(); 24231 return; 24232 } else { 24233 // It hasn't been long enough since we last GCed this 24234 // process... put it in the list to wait for its time. 24235 addProcessToGcListLocked(proc); 24236 break; 24237 } 24238 } 24239 } 24240 24241 scheduleAppGcsLocked(); 24242 } 24243 } 24244 24245 /** 24246 * If all looks good, perform GCs on all processes waiting for them. 24247 */ 24248 final void performAppGcsIfAppropriateLocked() { 24249 if (canGcNowLocked()) { 24250 performAppGcsLocked(); 24251 return; 24252 } 24253 // Still not idle, wait some more. 24254 scheduleAppGcsLocked(); 24255 } 24256 24257 /** 24258 * Schedule the execution of all pending app GCs. 24259 */ 24260 final void scheduleAppGcsLocked() { 24261 mHandler.removeMessages(GC_BACKGROUND_PROCESSES_MSG); 24262 24263 if (mProcessesToGc.size() > 0) { 24264 // Schedule a GC for the time to the next process. 24265 ProcessRecord proc = mProcessesToGc.get(0); 24266 Message msg = mHandler.obtainMessage(GC_BACKGROUND_PROCESSES_MSG); 24267 24268 long when = proc.lastRequestedGc + mConstants.GC_MIN_INTERVAL; 24269 long now = SystemClock.uptimeMillis(); 24270 if (when < (now+mConstants.GC_TIMEOUT)) { 24271 when = now + mConstants.GC_TIMEOUT; 24272 } 24273 mHandler.sendMessageAtTime(msg, when); 24274 } 24275 } 24276 24277 /** 24278 * Add a process to the array of processes waiting to be GCed. Keeps the 24279 * list in sorted order by the last GC time. The process can't already be 24280 * on the list. 24281 */ 24282 final void addProcessToGcListLocked(ProcessRecord proc) { 24283 boolean added = false; 24284 for (int i=mProcessesToGc.size()-1; i>=0; i--) { 24285 if (mProcessesToGc.get(i).lastRequestedGc < 24286 proc.lastRequestedGc) { 24287 added = true; 24288 mProcessesToGc.add(i+1, proc); 24289 break; 24290 } 24291 } 24292 if (!added) { 24293 mProcessesToGc.add(0, proc); 24294 } 24295 } 24296 24297 /** 24298 * Set up to ask a process to GC itself. This will either do it 24299 * immediately, or put it on the list of processes to gc the next 24300 * time things are idle. 24301 */ 24302 final void scheduleAppGcLocked(ProcessRecord app) { 24303 long now = SystemClock.uptimeMillis(); 24304 if ((app.lastRequestedGc+mConstants.GC_MIN_INTERVAL) > now) { 24305 return; 24306 } 24307 if (!mProcessesToGc.contains(app)) { 24308 addProcessToGcListLocked(app); 24309 scheduleAppGcsLocked(); 24310 } 24311 } 24312 24313 final void checkExcessivePowerUsageLocked() { 24314 updateCpuStatsNow(); 24315 24316 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 24317 boolean doCpuKills = true; 24318 if (mLastPowerCheckUptime == 0) { 24319 doCpuKills = false; 24320 } 24321 final long curUptime = SystemClock.uptimeMillis(); 24322 final long uptimeSince = curUptime - mLastPowerCheckUptime; 24323 mLastPowerCheckUptime = curUptime; 24324 int i = mLruProcesses.size(); 24325 while (i > 0) { 24326 i--; 24327 ProcessRecord app = mLruProcesses.get(i); 24328 if (app.setProcState >= ActivityManager.PROCESS_STATE_HOME) { 24329 if (app.lastCpuTime <= 0) { 24330 continue; 24331 } 24332 long cputimeUsed = app.curCpuTime - app.lastCpuTime; 24333 if (DEBUG_POWER) { 24334 StringBuilder sb = new StringBuilder(128); 24335 sb.append("CPU for "); 24336 app.toShortString(sb); 24337 sb.append(": over "); 24338 TimeUtils.formatDuration(uptimeSince, sb); 24339 sb.append(" used "); 24340 TimeUtils.formatDuration(cputimeUsed, sb); 24341 sb.append(" ("); 24342 sb.append((cputimeUsed*100)/uptimeSince); 24343 sb.append("%)"); 24344 Slog.i(TAG_POWER, sb.toString()); 24345 } 24346 // If the process has used too much CPU over the last duration, the 24347 // user probably doesn't want this, so kill! 24348 if (doCpuKills && uptimeSince > 0) { 24349 // What is the limit for this process? 24350 int cpuLimit; 24351 long checkDur = curUptime - app.whenUnimportant; 24352 if (checkDur <= mConstants.POWER_CHECK_INTERVAL) { 24353 cpuLimit = mConstants.POWER_CHECK_MAX_CPU_1; 24354 } else if (checkDur <= (mConstants.POWER_CHECK_INTERVAL*2) 24355 || app.setProcState <= ActivityManager.PROCESS_STATE_HOME) { 24356 cpuLimit = mConstants.POWER_CHECK_MAX_CPU_2; 24357 } else if (checkDur <= (mConstants.POWER_CHECK_INTERVAL*3)) { 24358 cpuLimit = mConstants.POWER_CHECK_MAX_CPU_3; 24359 } else { 24360 cpuLimit = mConstants.POWER_CHECK_MAX_CPU_4; 24361 } 24362 if (((cputimeUsed*100)/uptimeSince) >= cpuLimit) { 24363 synchronized (stats) { 24364 stats.reportExcessiveCpuLocked(app.info.uid, app.processName, 24365 uptimeSince, cputimeUsed); 24366 } 24367 app.kill("excessive cpu " + cputimeUsed + " during " + uptimeSince 24368 + " dur=" + checkDur + " limit=" + cpuLimit, true); 24369 app.baseProcessTracker.reportExcessiveCpu(app.pkgList); 24370 } 24371 } 24372 app.lastCpuTime = app.curCpuTime; 24373 } 24374 } 24375 } 24376 24377 private final boolean applyOomAdjLocked(ProcessRecord app, boolean doingAll, long now, 24378 long nowElapsed) { 24379 boolean success = true; 24380 24381 if (app.curRawAdj != app.setRawAdj) { 24382 app.setRawAdj = app.curRawAdj; 24383 } 24384 24385 int changes = 0; 24386 24387 if (app.curAdj != app.setAdj) { 24388 ProcessList.setOomAdj(app.pid, app.uid, app.curAdj); 24389 if (DEBUG_SWITCH || DEBUG_OOM_ADJ || mCurOomAdjUid == app.info.uid) { 24390 String msg = "Set " + app.pid + " " + app.processName + " adj " 24391 + app.curAdj + ": " + app.adjType; 24392 reportOomAdjMessageLocked(TAG_OOM_ADJ, msg); 24393 } 24394 app.setAdj = app.curAdj; 24395 app.verifiedAdj = ProcessList.INVALID_ADJ; 24396 } 24397 24398 if (app.setSchedGroup != app.curSchedGroup) { 24399 int oldSchedGroup = app.setSchedGroup; 24400 app.setSchedGroup = app.curSchedGroup; 24401 if (DEBUG_SWITCH || DEBUG_OOM_ADJ || mCurOomAdjUid == app.uid) { 24402 String msg = "Setting sched group of " + app.processName 24403 + " to " + app.curSchedGroup + ": " + app.adjType; 24404 reportOomAdjMessageLocked(TAG_OOM_ADJ, msg); 24405 } 24406 if (app.waitingToKill != null && app.curReceivers.isEmpty() 24407 && app.setSchedGroup == ProcessList.SCHED_GROUP_BACKGROUND) { 24408 app.kill(app.waitingToKill, true); 24409 success = false; 24410 } else { 24411 int processGroup; 24412 switch (app.curSchedGroup) { 24413 case ProcessList.SCHED_GROUP_BACKGROUND: 24414 processGroup = THREAD_GROUP_BG_NONINTERACTIVE; 24415 break; 24416 case ProcessList.SCHED_GROUP_TOP_APP: 24417 case ProcessList.SCHED_GROUP_TOP_APP_BOUND: 24418 processGroup = THREAD_GROUP_TOP_APP; 24419 break; 24420 case ProcessList.SCHED_GROUP_RESTRICTED: 24421 processGroup = THREAD_GROUP_RESTRICTED; 24422 break; 24423 default: 24424 processGroup = THREAD_GROUP_DEFAULT; 24425 break; 24426 } 24427 long oldId = Binder.clearCallingIdentity(); 24428 try { 24429 setProcessGroup(app.pid, processGroup); 24430 if (app.curSchedGroup == ProcessList.SCHED_GROUP_TOP_APP) { 24431 // do nothing if we already switched to RT 24432 if (oldSchedGroup != ProcessList.SCHED_GROUP_TOP_APP) { 24433 mVrController.onTopProcChangedLocked(app); 24434 if (mUseFifoUiScheduling) { 24435 // Switch UI pipeline for app to SCHED_FIFO 24436 app.savedPriority = Process.getThreadPriority(app.pid); 24437 scheduleAsFifoPriority(app.pid, /* suppressLogs */true); 24438 if (app.renderThreadTid != 0) { 24439 scheduleAsFifoPriority(app.renderThreadTid, 24440 /* suppressLogs */true); 24441 if (DEBUG_OOM_ADJ) { 24442 Slog.d("UI_FIFO", "Set RenderThread (TID " + 24443 app.renderThreadTid + ") to FIFO"); 24444 } 24445 } else { 24446 if (DEBUG_OOM_ADJ) { 24447 Slog.d("UI_FIFO", "Not setting RenderThread TID"); 24448 } 24449 } 24450 } else { 24451 // Boost priority for top app UI and render threads 24452 setThreadPriority(app.pid, TOP_APP_PRIORITY_BOOST); 24453 if (app.renderThreadTid != 0) { 24454 try { 24455 setThreadPriority(app.renderThreadTid, 24456 TOP_APP_PRIORITY_BOOST); 24457 } catch (IllegalArgumentException e) { 24458 // thread died, ignore 24459 } 24460 } 24461 } 24462 } 24463 } else if (oldSchedGroup == ProcessList.SCHED_GROUP_TOP_APP && 24464 app.curSchedGroup != ProcessList.SCHED_GROUP_TOP_APP) { 24465 mVrController.onTopProcChangedLocked(app); 24466 if (mUseFifoUiScheduling) { 24467 try { 24468 // Reset UI pipeline to SCHED_OTHER 24469 setThreadScheduler(app.pid, SCHED_OTHER, 0); 24470 setThreadPriority(app.pid, app.savedPriority); 24471 if (app.renderThreadTid != 0) { 24472 setThreadScheduler(app.renderThreadTid, 24473 SCHED_OTHER, 0); 24474 setThreadPriority(app.renderThreadTid, -4); 24475 } 24476 } catch (IllegalArgumentException e) { 24477 Slog.w(TAG, 24478 "Failed to set scheduling policy, thread does not exist:\n" 24479 + e); 24480 } catch (SecurityException e) { 24481 Slog.w(TAG, "Failed to set scheduling policy, not allowed:\n" + e); 24482 } 24483 } else { 24484 // Reset priority for top app UI and render threads 24485 setThreadPriority(app.pid, 0); 24486 if (app.renderThreadTid != 0) { 24487 setThreadPriority(app.renderThreadTid, 0); 24488 } 24489 } 24490 } 24491 } catch (Exception e) { 24492 if (false) { 24493 Slog.w(TAG, "Failed setting process group of " + app.pid 24494 + " to " + app.curSchedGroup); 24495 Slog.w(TAG, "at location", e); 24496 } 24497 } finally { 24498 Binder.restoreCallingIdentity(oldId); 24499 } 24500 } 24501 } 24502 if (app.repForegroundActivities != app.foregroundActivities) { 24503 app.repForegroundActivities = app.foregroundActivities; 24504 changes |= ProcessChangeItem.CHANGE_ACTIVITIES; 24505 } 24506 if (app.repProcState != app.curProcState) { 24507 app.repProcState = app.curProcState; 24508 if (app.thread != null) { 24509 try { 24510 if (false) { 24511 //RuntimeException h = new RuntimeException("here"); 24512 Slog.i(TAG, "Sending new process state " + app.repProcState 24513 + " to " + app /*, h*/); 24514 } 24515 app.thread.setProcessState(app.repProcState); 24516 } catch (RemoteException e) { 24517 } 24518 } 24519 } 24520 if (app.setProcState == ActivityManager.PROCESS_STATE_NONEXISTENT 24521 || ProcessList.procStatesDifferForMem(app.curProcState, app.setProcState)) { 24522 if (false && mTestPssMode && app.setProcState >= 0 && app.lastStateTime <= (now-200)) { 24523 // Experimental code to more aggressively collect pss while 24524 // running test... the problem is that this tends to collect 24525 // the data right when a process is transitioning between process 24526 // states, which will tend to give noisy data. 24527 long start = SystemClock.uptimeMillis(); 24528 long startTime = SystemClock.currentThreadTimeMillis(); 24529 long pss = Debug.getPss(app.pid, mTmpLong, null); 24530 long endTime = SystemClock.currentThreadTimeMillis(); 24531 recordPssSampleLocked(app, app.curProcState, pss, mTmpLong[0], mTmpLong[1], 24532 mTmpLong[2], ProcessStats.ADD_PSS_INTERNAL_SINGLE, endTime-startTime, now); 24533 mPendingPssProcesses.remove(app); 24534 Slog.i(TAG, "Recorded pss for " + app + " state " + app.setProcState 24535 + " to " + app.curProcState + ": " 24536 + (SystemClock.uptimeMillis()-start) + "ms"); 24537 } 24538 app.lastStateTime = now; 24539 app.nextPssTime = ProcessList.computeNextPssTime(app.curProcState, 24540 app.procStateMemTracker, mTestPssMode, isSleepingLocked(), now); 24541 if (DEBUG_PSS) Slog.d(TAG_PSS, "Process state change from " 24542 + ProcessList.makeProcStateString(app.setProcState) + " to " 24543 + ProcessList.makeProcStateString(app.curProcState) + " next pss in " 24544 + (app.nextPssTime-now) + ": " + app); 24545 } else { 24546 if (now > app.nextPssTime || (now > (app.lastPssTime+ProcessList.PSS_MAX_INTERVAL) 24547 && now > (app.lastStateTime+ProcessList.minTimeFromStateChange( 24548 mTestPssMode)))) { 24549 if (requestPssLocked(app, app.setProcState)) { 24550 app.nextPssTime = ProcessList.computeNextPssTime(app.curProcState, 24551 app.procStateMemTracker, mTestPssMode, isSleepingLocked(), now); 24552 } 24553 } else if (false && DEBUG_PSS) Slog.d(TAG_PSS, 24554 "Not requesting pss of " + app + ": next=" + (app.nextPssTime-now)); 24555 } 24556 if (app.setProcState != app.curProcState) { 24557 if (DEBUG_SWITCH || DEBUG_OOM_ADJ || mCurOomAdjUid == app.uid) { 24558 String msg = "Proc state change of " + app.processName 24559 + " to " + ProcessList.makeProcStateString(app.curProcState) 24560 + " (" + app.curProcState + ")" + ": " + app.adjType; 24561 reportOomAdjMessageLocked(TAG_OOM_ADJ, msg); 24562 } 24563 boolean setImportant = app.setProcState < ActivityManager.PROCESS_STATE_SERVICE; 24564 boolean curImportant = app.curProcState < ActivityManager.PROCESS_STATE_SERVICE; 24565 if (setImportant && !curImportant) { 24566 // This app is no longer something we consider important enough to allow to 24567 // use arbitrary amounts of battery power. Note 24568 // its current CPU time to later know to kill it if 24569 // it is not behaving well. 24570 app.whenUnimportant = now; 24571 app.lastCpuTime = 0; 24572 } 24573 // Inform UsageStats of important process state change 24574 // Must be called before updating setProcState 24575 maybeUpdateUsageStatsLocked(app, nowElapsed); 24576 24577 app.setProcState = app.curProcState; 24578 if (app.setProcState >= ActivityManager.PROCESS_STATE_HOME) { 24579 app.notCachedSinceIdle = false; 24580 } 24581 if (!doingAll) { 24582 setProcessTrackerStateLocked(app, mProcessStats.getMemFactorLocked(), now); 24583 } else { 24584 app.procStateChanged = true; 24585 } 24586 } else if (app.reportedInteraction && (nowElapsed-app.interactionEventTime) 24587 > mConstants.USAGE_STATS_INTERACTION_INTERVAL) { 24588 // For apps that sit around for a long time in the interactive state, we need 24589 // to report this at least once a day so they don't go idle. 24590 maybeUpdateUsageStatsLocked(app, nowElapsed); 24591 } 24592 24593 if (changes != 0) { 24594 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG_PROCESS_OBSERVERS, 24595 "Changes in " + app + ": " + changes); 24596 int i = mPendingProcessChanges.size()-1; 24597 ProcessChangeItem item = null; 24598 while (i >= 0) { 24599 item = mPendingProcessChanges.get(i); 24600 if (item.pid == app.pid) { 24601 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG_PROCESS_OBSERVERS, 24602 "Re-using existing item: " + item); 24603 break; 24604 } 24605 i--; 24606 } 24607 if (i < 0) { 24608 // No existing item in pending changes; need a new one. 24609 final int NA = mAvailProcessChanges.size(); 24610 if (NA > 0) { 24611 item = mAvailProcessChanges.remove(NA-1); 24612 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG_PROCESS_OBSERVERS, 24613 "Retrieving available item: " + item); 24614 } else { 24615 item = new ProcessChangeItem(); 24616 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG_PROCESS_OBSERVERS, 24617 "Allocating new item: " + item); 24618 } 24619 item.changes = 0; 24620 item.pid = app.pid; 24621 item.uid = app.info.uid; 24622 if (mPendingProcessChanges.size() == 0) { 24623 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG_PROCESS_OBSERVERS, 24624 "*** Enqueueing dispatch processes changed!"); 24625 mUiHandler.obtainMessage(DISPATCH_PROCESSES_CHANGED_UI_MSG).sendToTarget(); 24626 } 24627 mPendingProcessChanges.add(item); 24628 } 24629 item.changes |= changes; 24630 item.foregroundActivities = app.repForegroundActivities; 24631 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG_PROCESS_OBSERVERS, 24632 "Item " + Integer.toHexString(System.identityHashCode(item)) 24633 + " " + app.toShortString() + ": changes=" + item.changes 24634 + " foreground=" + item.foregroundActivities 24635 + " type=" + app.adjType + " source=" + app.adjSource 24636 + " target=" + app.adjTarget); 24637 } 24638 24639 return success; 24640 } 24641 24642 private boolean isEphemeralLocked(int uid) { 24643 String packages[] = mContext.getPackageManager().getPackagesForUid(uid); 24644 if (packages == null || packages.length != 1) { // Ephemeral apps cannot share uid 24645 return false; 24646 } 24647 return getPackageManagerInternalLocked().isPackageEphemeral(UserHandle.getUserId(uid), 24648 packages[0]); 24649 } 24650 24651 @VisibleForTesting 24652 final void enqueueUidChangeLocked(UidRecord uidRec, int uid, int change) { 24653 final UidRecord.ChangeItem pendingChange; 24654 if (uidRec == null || uidRec.pendingChange == null) { 24655 if (mPendingUidChanges.size() == 0) { 24656 if (DEBUG_UID_OBSERVERS) Slog.i(TAG_UID_OBSERVERS, 24657 "*** Enqueueing dispatch uid changed!"); 24658 mUiHandler.obtainMessage(DISPATCH_UIDS_CHANGED_UI_MSG).sendToTarget(); 24659 } 24660 final int NA = mAvailUidChanges.size(); 24661 if (NA > 0) { 24662 pendingChange = mAvailUidChanges.remove(NA-1); 24663 if (DEBUG_UID_OBSERVERS) Slog.i(TAG_UID_OBSERVERS, 24664 "Retrieving available item: " + pendingChange); 24665 } else { 24666 pendingChange = new UidRecord.ChangeItem(); 24667 if (DEBUG_UID_OBSERVERS) Slog.i(TAG_UID_OBSERVERS, 24668 "Allocating new item: " + pendingChange); 24669 } 24670 if (uidRec != null) { 24671 uidRec.pendingChange = pendingChange; 24672 if ((change & UidRecord.CHANGE_GONE) != 0 && !uidRec.idle) { 24673 // If this uid is going away, and we haven't yet reported it is gone, 24674 // then do so now. 24675 change |= UidRecord.CHANGE_IDLE; 24676 } 24677 } else if (uid < 0) { 24678 throw new IllegalArgumentException("No UidRecord or uid"); 24679 } 24680 pendingChange.uidRecord = uidRec; 24681 pendingChange.uid = uidRec != null ? uidRec.uid : uid; 24682 mPendingUidChanges.add(pendingChange); 24683 } else { 24684 pendingChange = uidRec.pendingChange; 24685 // If there is no change in idle or active state, then keep whatever was pending. 24686 if ((change & (UidRecord.CHANGE_IDLE | UidRecord.CHANGE_ACTIVE)) == 0) { 24687 change |= (pendingChange.change & (UidRecord.CHANGE_IDLE 24688 | UidRecord.CHANGE_ACTIVE)); 24689 } 24690 // If there is no change in cached or uncached state, then keep whatever was pending. 24691 if ((change & (UidRecord.CHANGE_CACHED | UidRecord.CHANGE_UNCACHED)) == 0) { 24692 change |= (pendingChange.change & (UidRecord.CHANGE_CACHED 24693 | UidRecord.CHANGE_UNCACHED)); 24694 } 24695 // If this is a report of the UID being gone, then we shouldn't keep any previous 24696 // report of it being active or cached. (That is, a gone uid is never active, 24697 // and never cached.) 24698 if ((change & UidRecord.CHANGE_GONE) != 0) { 24699 change &= ~(UidRecord.CHANGE_ACTIVE | UidRecord.CHANGE_CACHED); 24700 if (!uidRec.idle) { 24701 // If this uid is going away, and we haven't yet reported it is gone, 24702 // then do so now. 24703 change |= UidRecord.CHANGE_IDLE; 24704 } 24705 } 24706 } 24707 pendingChange.change = change; 24708 pendingChange.processState = uidRec != null 24709 ? uidRec.setProcState : ActivityManager.PROCESS_STATE_NONEXISTENT; 24710 pendingChange.ephemeral = uidRec != null ? uidRec.ephemeral : isEphemeralLocked(uid); 24711 pendingChange.procStateSeq = uidRec != null ? uidRec.curProcStateSeq : 0; 24712 if (uidRec != null) { 24713 uidRec.lastReportedChange = change; 24714 uidRec.updateLastDispatchedProcStateSeq(change); 24715 } 24716 24717 // Directly update the power manager, since we sit on top of it and it is critical 24718 // it be kept in sync (so wake locks will be held as soon as appropriate). 24719 if (mLocalPowerManager != null) { 24720 // TO DO: dispatch cached/uncached changes here, so we don't need to report 24721 // all proc state changes. 24722 if ((change & UidRecord.CHANGE_ACTIVE) != 0) { 24723 mLocalPowerManager.uidActive(pendingChange.uid); 24724 } 24725 if ((change & UidRecord.CHANGE_IDLE) != 0) { 24726 mLocalPowerManager.uidIdle(pendingChange.uid); 24727 } 24728 if ((change & UidRecord.CHANGE_GONE) != 0) { 24729 mLocalPowerManager.uidGone(pendingChange.uid); 24730 } else { 24731 mLocalPowerManager.updateUidProcState(pendingChange.uid, 24732 pendingChange.processState); 24733 } 24734 } 24735 } 24736 24737 private void maybeUpdateProviderUsageStatsLocked(ProcessRecord app, String providerPkgName, 24738 String authority) { 24739 if (app == null) return; 24740 if (app.curProcState <= ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND) { 24741 UserState userState = mUserController.getStartedUserState(app.userId); 24742 if (userState == null) return; 24743 final long now = SystemClock.elapsedRealtime(); 24744 Long lastReported = userState.mProviderLastReportedFg.get(authority); 24745 if (lastReported == null || lastReported < now - 60 * 1000L) { 24746 if (mSystemReady) { 24747 // Cannot touch the user stats if not system ready 24748 mUsageStatsService.reportContentProviderUsage( 24749 authority, providerPkgName, app.userId); 24750 } 24751 userState.mProviderLastReportedFg.put(authority, now); 24752 } 24753 } 24754 } 24755 24756 private void maybeUpdateUsageStatsLocked(ProcessRecord app, long nowElapsed) { 24757 if (DEBUG_USAGE_STATS) { 24758 Slog.d(TAG, "Checking proc [" + Arrays.toString(app.getPackageList()) 24759 + "] state changes: old = " + app.setProcState + ", new = " 24760 + app.curProcState); 24761 } 24762 if (mUsageStatsService == null) { 24763 return; 24764 } 24765 boolean isInteraction; 24766 // To avoid some abuse patterns, we are going to be careful about what we consider 24767 // to be an app interaction. Being the top activity doesn't count while the display 24768 // is sleeping, nor do short foreground services. 24769 if (app.curProcState <= ActivityManager.PROCESS_STATE_TOP) { 24770 isInteraction = true; 24771 app.fgInteractionTime = 0; 24772 } else if (app.curProcState <= ActivityManager.PROCESS_STATE_FOREGROUND_SERVICE) { 24773 if (app.fgInteractionTime == 0) { 24774 app.fgInteractionTime = nowElapsed; 24775 isInteraction = false; 24776 } else { 24777 isInteraction = nowElapsed > app.fgInteractionTime 24778 + mConstants.SERVICE_USAGE_INTERACTION_TIME; 24779 } 24780 } else { 24781 isInteraction = app.curProcState <= ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 24782 app.fgInteractionTime = 0; 24783 } 24784 if (isInteraction && (!app.reportedInteraction || (nowElapsed-app.interactionEventTime) 24785 > mConstants.USAGE_STATS_INTERACTION_INTERVAL)) { 24786 app.interactionEventTime = nowElapsed; 24787 String[] packages = app.getPackageList(); 24788 if (packages != null) { 24789 for (int i = 0; i < packages.length; i++) { 24790 mUsageStatsService.reportEvent(packages[i], app.userId, 24791 UsageEvents.Event.SYSTEM_INTERACTION); 24792 } 24793 } 24794 } 24795 app.reportedInteraction = isInteraction; 24796 if (!isInteraction) { 24797 app.interactionEventTime = 0; 24798 } 24799 } 24800 24801 private final void setProcessTrackerStateLocked(ProcessRecord proc, int memFactor, long now) { 24802 if (proc.thread != null) { 24803 if (proc.baseProcessTracker != null) { 24804 proc.baseProcessTracker.setState(proc.repProcState, memFactor, now, proc.pkgList); 24805 } 24806 } 24807 } 24808 24809 private final boolean updateOomAdjLocked(ProcessRecord app, int cachedAdj, 24810 ProcessRecord TOP_APP, boolean doingAll, long now) { 24811 if (app.thread == null) { 24812 return false; 24813 } 24814 24815 computeOomAdjLocked(app, cachedAdj, TOP_APP, doingAll, now); 24816 24817 return applyOomAdjLocked(app, doingAll, now, SystemClock.elapsedRealtime()); 24818 } 24819 24820 @GuardedBy("this") 24821 final void updateProcessForegroundLocked(ProcessRecord proc, boolean isForeground, 24822 boolean oomAdj) { 24823 if (isForeground != proc.foregroundServices) { 24824 proc.foregroundServices = isForeground; 24825 ArrayList<ProcessRecord> curProcs = mForegroundPackages.get(proc.info.packageName, 24826 proc.info.uid); 24827 if (isForeground) { 24828 if (curProcs == null) { 24829 curProcs = new ArrayList<ProcessRecord>(); 24830 mForegroundPackages.put(proc.info.packageName, proc.info.uid, curProcs); 24831 } 24832 if (!curProcs.contains(proc)) { 24833 curProcs.add(proc); 24834 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_FOREGROUND_START, 24835 proc.info.packageName, proc.info.uid); 24836 } 24837 } else { 24838 if (curProcs != null) { 24839 if (curProcs.remove(proc)) { 24840 mBatteryStatsService.noteEvent( 24841 BatteryStats.HistoryItem.EVENT_FOREGROUND_FINISH, 24842 proc.info.packageName, proc.info.uid); 24843 if (curProcs.size() <= 0) { 24844 mForegroundPackages.remove(proc.info.packageName, proc.info.uid); 24845 } 24846 } 24847 } 24848 } 24849 if (oomAdj) { 24850 updateOomAdjLocked(); 24851 } 24852 } 24853 } 24854 24855 private final ActivityRecord resumedAppLocked() { 24856 ActivityRecord act = mStackSupervisor.getResumedActivityLocked(); 24857 String pkg; 24858 int uid; 24859 if (act != null) { 24860 pkg = act.packageName; 24861 uid = act.info.applicationInfo.uid; 24862 } else { 24863 pkg = null; 24864 uid = -1; 24865 } 24866 // Has the UID or resumed package name changed? 24867 if (uid != mCurResumedUid || (pkg != mCurResumedPackage 24868 && (pkg == null || !pkg.equals(mCurResumedPackage)))) { 24869 if (mCurResumedPackage != null) { 24870 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_TOP_FINISH, 24871 mCurResumedPackage, mCurResumedUid); 24872 } 24873 mCurResumedPackage = pkg; 24874 mCurResumedUid = uid; 24875 if (mCurResumedPackage != null) { 24876 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_TOP_START, 24877 mCurResumedPackage, mCurResumedUid); 24878 } 24879 } 24880 return act; 24881 } 24882 24883 /** 24884 * Update OomAdj for a specific process. 24885 * @param app The process to update 24886 * @param oomAdjAll If it's ok to call updateOomAdjLocked() for all running apps 24887 * if necessary, or skip. 24888 * @return whether updateOomAdjLocked(app) was successful. 24889 */ 24890 @GuardedBy("this") 24891 final boolean updateOomAdjLocked(ProcessRecord app, boolean oomAdjAll) { 24892 final ActivityRecord TOP_ACT = resumedAppLocked(); 24893 final ProcessRecord TOP_APP = TOP_ACT != null ? TOP_ACT.app : null; 24894 final boolean wasCached = app.cached; 24895 24896 mAdjSeq++; 24897 24898 // This is the desired cached adjusment we want to tell it to use. 24899 // If our app is currently cached, we know it, and that is it. Otherwise, 24900 // we don't know it yet, and it needs to now be cached we will then 24901 // need to do a complete oom adj. 24902 final int cachedAdj = app.curRawAdj >= ProcessList.CACHED_APP_MIN_ADJ 24903 ? app.curRawAdj : ProcessList.UNKNOWN_ADJ; 24904 boolean success = updateOomAdjLocked(app, cachedAdj, TOP_APP, false, 24905 SystemClock.uptimeMillis()); 24906 if (oomAdjAll 24907 && (wasCached != app.cached || app.curRawAdj == ProcessList.UNKNOWN_ADJ)) { 24908 // Changed to/from cached state, so apps after it in the LRU 24909 // list may also be changed. 24910 updateOomAdjLocked(); 24911 } 24912 return success; 24913 } 24914 24915 @GuardedBy("this") 24916 final void updateOomAdjLocked() { 24917 final ActivityRecord TOP_ACT = resumedAppLocked(); 24918 final ProcessRecord TOP_APP = TOP_ACT != null ? TOP_ACT.app : null; 24919 final long now = SystemClock.uptimeMillis(); 24920 final long nowElapsed = SystemClock.elapsedRealtime(); 24921 final long oldTime = now - ProcessList.MAX_EMPTY_TIME; 24922 final int N = mLruProcesses.size(); 24923 24924 if (false) { 24925 RuntimeException e = new RuntimeException(); 24926 e.fillInStackTrace(); 24927 Slog.i(TAG, "updateOomAdj: top=" + TOP_ACT, e); 24928 } 24929 24930 // Reset state in all uid records. 24931 for (int i=mActiveUids.size()-1; i>=0; i--) { 24932 final UidRecord uidRec = mActiveUids.valueAt(i); 24933 if (false && DEBUG_UID_OBSERVERS) Slog.i(TAG_UID_OBSERVERS, 24934 "Starting update of " + uidRec); 24935 uidRec.reset(); 24936 } 24937 24938 mStackSupervisor.rankTaskLayersIfNeeded(); 24939 24940 mAdjSeq++; 24941 mNewNumServiceProcs = 0; 24942 mNewNumAServiceProcs = 0; 24943 24944 final int emptyProcessLimit = mConstants.CUR_MAX_EMPTY_PROCESSES; 24945 final int cachedProcessLimit = mConstants.CUR_MAX_CACHED_PROCESSES - emptyProcessLimit; 24946 24947 // Let's determine how many processes we have running vs. 24948 // how many slots we have for background processes; we may want 24949 // to put multiple processes in a slot of there are enough of 24950 // them. 24951 int numSlots = (ProcessList.CACHED_APP_MAX_ADJ 24952 - ProcessList.CACHED_APP_MIN_ADJ + 1) / 2; 24953 int numEmptyProcs = N - mNumNonCachedProcs - mNumCachedHiddenProcs; 24954 if (numEmptyProcs > cachedProcessLimit) { 24955 // If there are more empty processes than our limit on cached 24956 // processes, then use the cached process limit for the factor. 24957 // This ensures that the really old empty processes get pushed 24958 // down to the bottom, so if we are running low on memory we will 24959 // have a better chance at keeping around more cached processes 24960 // instead of a gazillion empty processes. 24961 numEmptyProcs = cachedProcessLimit; 24962 } 24963 int emptyFactor = numEmptyProcs/numSlots; 24964 if (emptyFactor < 1) emptyFactor = 1; 24965 int cachedFactor = (mNumCachedHiddenProcs > 0 ? mNumCachedHiddenProcs : 1)/numSlots; 24966 if (cachedFactor < 1) cachedFactor = 1; 24967 int stepCached = 0; 24968 int stepEmpty = 0; 24969 int numCached = 0; 24970 int numEmpty = 0; 24971 int numTrimming = 0; 24972 24973 mNumNonCachedProcs = 0; 24974 mNumCachedHiddenProcs = 0; 24975 24976 // First update the OOM adjustment for each of the 24977 // application processes based on their current state. 24978 int curCachedAdj = ProcessList.CACHED_APP_MIN_ADJ; 24979 int nextCachedAdj = curCachedAdj+1; 24980 int curEmptyAdj = ProcessList.CACHED_APP_MIN_ADJ; 24981 int nextEmptyAdj = curEmptyAdj+2; 24982 24983 boolean retryCycles = false; 24984 24985 // need to reset cycle state before calling computeOomAdjLocked because of service connections 24986 for (int i=N-1; i>=0; i--) { 24987 ProcessRecord app = mLruProcesses.get(i); 24988 app.containsCycle = false; 24989 } 24990 for (int i=N-1; i>=0; i--) { 24991 ProcessRecord app = mLruProcesses.get(i); 24992 if (!app.killedByAm && app.thread != null) { 24993 app.procStateChanged = false; 24994 computeOomAdjLocked(app, ProcessList.UNKNOWN_ADJ, TOP_APP, true, now); 24995 24996 // if any app encountered a cycle, we need to perform an additional loop later 24997 retryCycles |= app.containsCycle; 24998 24999 // If we haven't yet assigned the final cached adj 25000 // to the process, do that now. 25001 if (app.curAdj >= ProcessList.UNKNOWN_ADJ) { 25002 switch (app.curProcState) { 25003 case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY: 25004 case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY_CLIENT: 25005 case ActivityManager.PROCESS_STATE_CACHED_RECENT: 25006 // This process is a cached process holding activities... 25007 // assign it the next cached value for that type, and then 25008 // step that cached level. 25009 app.curRawAdj = curCachedAdj; 25010 app.curAdj = app.modifyRawOomAdj(curCachedAdj); 25011 if (DEBUG_LRU && false) Slog.d(TAG_LRU, "Assigning activity LRU #" + i 25012 + " adj: " + app.curAdj + " (curCachedAdj=" + curCachedAdj 25013 + ")"); 25014 if (curCachedAdj != nextCachedAdj) { 25015 stepCached++; 25016 if (stepCached >= cachedFactor) { 25017 stepCached = 0; 25018 curCachedAdj = nextCachedAdj; 25019 nextCachedAdj += 2; 25020 if (nextCachedAdj > ProcessList.CACHED_APP_MAX_ADJ) { 25021 nextCachedAdj = ProcessList.CACHED_APP_MAX_ADJ; 25022 } 25023 } 25024 } 25025 break; 25026 default: 25027 // For everything else, assign next empty cached process 25028 // level and bump that up. Note that this means that 25029 // long-running services that have dropped down to the 25030 // cached level will be treated as empty (since their process 25031 // state is still as a service), which is what we want. 25032 app.curRawAdj = curEmptyAdj; 25033 app.curAdj = app.modifyRawOomAdj(curEmptyAdj); 25034 if (DEBUG_LRU && false) Slog.d(TAG_LRU, "Assigning empty LRU #" + i 25035 + " adj: " + app.curAdj + " (curEmptyAdj=" + curEmptyAdj 25036 + ")"); 25037 if (curEmptyAdj != nextEmptyAdj) { 25038 stepEmpty++; 25039 if (stepEmpty >= emptyFactor) { 25040 stepEmpty = 0; 25041 curEmptyAdj = nextEmptyAdj; 25042 nextEmptyAdj += 2; 25043 if (nextEmptyAdj > ProcessList.CACHED_APP_MAX_ADJ) { 25044 nextEmptyAdj = ProcessList.CACHED_APP_MAX_ADJ; 25045 } 25046 } 25047 } 25048 break; 25049 } 25050 } 25051 25052 25053 } 25054 } 25055 25056 // Cycle strategy: 25057 // - Retry computing any process that has encountered a cycle. 25058 // - Continue retrying until no process was promoted. 25059 // - Iterate from least important to most important. 25060 int cycleCount = 0; 25061 while (retryCycles) { 25062 cycleCount++; 25063 retryCycles = false; 25064 25065 for (int i=0; i<N; i++) { 25066 ProcessRecord app = mLruProcesses.get(i); 25067 if (!app.killedByAm && app.thread != null && app.containsCycle == true) { 25068 app.adjSeq--; 25069 app.completedAdjSeq--; 25070 } 25071 } 25072 25073 for (int i=0; i<N; i++) { 25074 ProcessRecord app = mLruProcesses.get(i); 25075 if (!app.killedByAm && app.thread != null && app.containsCycle == true) { 25076 if (computeOomAdjLocked(app, ProcessList.UNKNOWN_ADJ, TOP_APP, true, now)) { 25077 retryCycles = true; 25078 } 25079 } 25080 } 25081 } 25082 for (int i=N-1; i>=0; i--) { 25083 ProcessRecord app = mLruProcesses.get(i); 25084 if (!app.killedByAm && app.thread != null) { 25085 applyOomAdjLocked(app, true, now, nowElapsed); 25086 25087 // Count the number of process types. 25088 switch (app.curProcState) { 25089 case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY: 25090 case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY_CLIENT: 25091 mNumCachedHiddenProcs++; 25092 numCached++; 25093 if (numCached > cachedProcessLimit) { 25094 app.kill("cached #" + numCached, true); 25095 } 25096 break; 25097 case ActivityManager.PROCESS_STATE_CACHED_EMPTY: 25098 if (numEmpty > mConstants.CUR_TRIM_EMPTY_PROCESSES 25099 && app.lastActivityTime < oldTime) { 25100 app.kill("empty for " 25101 + ((oldTime + ProcessList.MAX_EMPTY_TIME - app.lastActivityTime) 25102 / 1000) + "s", true); 25103 } else { 25104 numEmpty++; 25105 if (numEmpty > emptyProcessLimit) { 25106 app.kill("empty #" + numEmpty, true); 25107 } 25108 } 25109 break; 25110 default: 25111 mNumNonCachedProcs++; 25112 break; 25113 } 25114 25115 if (app.isolated && app.services.size() <= 0 && app.isolatedEntryPoint == null) { 25116 // If this is an isolated process, there are no services 25117 // running in it, and it's not a special process with a 25118 // custom entry point, then the process is no longer 25119 // needed. We agressively kill these because we can by 25120 // definition not re-use the same process again, and it is 25121 // good to avoid having whatever code was running in them 25122 // left sitting around after no longer needed. 25123 app.kill("isolated not needed", true); 25124 } else { 25125 // Keeping this process, update its uid. 25126 final UidRecord uidRec = app.uidRecord; 25127 if (uidRec != null) { 25128 uidRec.ephemeral = app.info.isInstantApp(); 25129 if (uidRec.curProcState > app.curProcState) { 25130 uidRec.curProcState = app.curProcState; 25131 } 25132 if (app.foregroundServices) { 25133 uidRec.foregroundServices = true; 25134 } 25135 } 25136 } 25137 25138 if (app.curProcState >= ActivityManager.PROCESS_STATE_HOME 25139 && !app.killedByAm) { 25140 numTrimming++; 25141 } 25142 } 25143 } 25144 25145 incrementProcStateSeqAndNotifyAppsLocked(); 25146 25147 mNumServiceProcs = mNewNumServiceProcs; 25148 25149 // Now determine the memory trimming level of background processes. 25150 // Unfortunately we need to start at the back of the list to do this 25151 // properly. We only do this if the number of background apps we 25152 // are managing to keep around is less than half the maximum we desire; 25153 // if we are keeping a good number around, we'll let them use whatever 25154 // memory they want. 25155 final int numCachedAndEmpty = numCached + numEmpty; 25156 int memFactor; 25157 if (numCached <= mConstants.CUR_TRIM_CACHED_PROCESSES 25158 && numEmpty <= mConstants.CUR_TRIM_EMPTY_PROCESSES) { 25159 if (numCachedAndEmpty <= ProcessList.TRIM_CRITICAL_THRESHOLD) { 25160 memFactor = ProcessStats.ADJ_MEM_FACTOR_CRITICAL; 25161 } else if (numCachedAndEmpty <= ProcessList.TRIM_LOW_THRESHOLD) { 25162 memFactor = ProcessStats.ADJ_MEM_FACTOR_LOW; 25163 } else { 25164 memFactor = ProcessStats.ADJ_MEM_FACTOR_MODERATE; 25165 } 25166 } else { 25167 memFactor = ProcessStats.ADJ_MEM_FACTOR_NORMAL; 25168 } 25169 // We always allow the memory level to go up (better). We only allow it to go 25170 // down if we are in a state where that is allowed, *and* the total number of processes 25171 // has gone down since last time. 25172 if (DEBUG_OOM_ADJ) Slog.d(TAG_OOM_ADJ, "oom: memFactor=" + memFactor 25173 + " last=" + mLastMemoryLevel + " allowLow=" + mAllowLowerMemLevel 25174 + " numProcs=" + mLruProcesses.size() + " last=" + mLastNumProcesses); 25175 if (memFactor > mLastMemoryLevel) { 25176 if (!mAllowLowerMemLevel || mLruProcesses.size() >= mLastNumProcesses) { 25177 memFactor = mLastMemoryLevel; 25178 if (DEBUG_OOM_ADJ) Slog.d(TAG_OOM_ADJ, "Keeping last mem factor!"); 25179 } 25180 } 25181 if (memFactor != mLastMemoryLevel) { 25182 EventLogTags.writeAmMemFactor(memFactor, mLastMemoryLevel); 25183 } 25184 mLastMemoryLevel = memFactor; 25185 mLastNumProcesses = mLruProcesses.size(); 25186 boolean allChanged = mProcessStats.setMemFactorLocked(memFactor, !isSleepingLocked(), now); 25187 final int trackerMemFactor = mProcessStats.getMemFactorLocked(); 25188 if (memFactor != ProcessStats.ADJ_MEM_FACTOR_NORMAL) { 25189 if (mLowRamStartTime == 0) { 25190 mLowRamStartTime = now; 25191 } 25192 int step = 0; 25193 int fgTrimLevel; 25194 switch (memFactor) { 25195 case ProcessStats.ADJ_MEM_FACTOR_CRITICAL: 25196 fgTrimLevel = ComponentCallbacks2.TRIM_MEMORY_RUNNING_CRITICAL; 25197 break; 25198 case ProcessStats.ADJ_MEM_FACTOR_LOW: 25199 fgTrimLevel = ComponentCallbacks2.TRIM_MEMORY_RUNNING_LOW; 25200 break; 25201 default: 25202 fgTrimLevel = ComponentCallbacks2.TRIM_MEMORY_RUNNING_MODERATE; 25203 break; 25204 } 25205 int factor = numTrimming/3; 25206 int minFactor = 2; 25207 if (mHomeProcess != null) minFactor++; 25208 if (mPreviousProcess != null) minFactor++; 25209 if (factor < minFactor) factor = minFactor; 25210 int curLevel = ComponentCallbacks2.TRIM_MEMORY_COMPLETE; 25211 for (int i=N-1; i>=0; i--) { 25212 ProcessRecord app = mLruProcesses.get(i); 25213 if (allChanged || app.procStateChanged) { 25214 setProcessTrackerStateLocked(app, trackerMemFactor, now); 25215 app.procStateChanged = false; 25216 } 25217 if (app.curProcState >= ActivityManager.PROCESS_STATE_HOME 25218 && !app.killedByAm) { 25219 if (app.trimMemoryLevel < curLevel && app.thread != null) { 25220 try { 25221 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG_OOM_ADJ, 25222 "Trimming memory of " + app.processName + " to " + curLevel); 25223 app.thread.scheduleTrimMemory(curLevel); 25224 } catch (RemoteException e) { 25225 } 25226 if (false) { 25227 // For now we won't do this; our memory trimming seems 25228 // to be good enough at this point that destroying 25229 // activities causes more harm than good. 25230 if (curLevel >= ComponentCallbacks2.TRIM_MEMORY_COMPLETE 25231 && app != mHomeProcess && app != mPreviousProcess) { 25232 // Need to do this on its own message because the stack may not 25233 // be in a consistent state at this point. 25234 // For these apps we will also finish their activities 25235 // to help them free memory. 25236 mStackSupervisor.scheduleDestroyAllActivities(app, "trim"); 25237 } 25238 } 25239 } 25240 app.trimMemoryLevel = curLevel; 25241 step++; 25242 if (step >= factor) { 25243 step = 0; 25244 switch (curLevel) { 25245 case ComponentCallbacks2.TRIM_MEMORY_COMPLETE: 25246 curLevel = ComponentCallbacks2.TRIM_MEMORY_MODERATE; 25247 break; 25248 case ComponentCallbacks2.TRIM_MEMORY_MODERATE: 25249 curLevel = ComponentCallbacks2.TRIM_MEMORY_BACKGROUND; 25250 break; 25251 } 25252 } 25253 } else if (app.curProcState == ActivityManager.PROCESS_STATE_HEAVY_WEIGHT 25254 && !app.killedByAm) { 25255 if (app.trimMemoryLevel < ComponentCallbacks2.TRIM_MEMORY_BACKGROUND 25256 && app.thread != null) { 25257 try { 25258 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG_OOM_ADJ, 25259 "Trimming memory of heavy-weight " + app.processName 25260 + " to " + ComponentCallbacks2.TRIM_MEMORY_BACKGROUND); 25261 app.thread.scheduleTrimMemory( 25262 ComponentCallbacks2.TRIM_MEMORY_BACKGROUND); 25263 } catch (RemoteException e) { 25264 } 25265 } 25266 app.trimMemoryLevel = ComponentCallbacks2.TRIM_MEMORY_BACKGROUND; 25267 } else { 25268 if ((app.curProcState >= ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND 25269 || app.systemNoUi) && app.pendingUiClean) { 25270 // If this application is now in the background and it 25271 // had done UI, then give it the special trim level to 25272 // have it free UI resources. 25273 final int level = ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN; 25274 if (app.trimMemoryLevel < level && app.thread != null) { 25275 try { 25276 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG_OOM_ADJ, 25277 "Trimming memory of bg-ui " + app.processName 25278 + " to " + level); 25279 app.thread.scheduleTrimMemory(level); 25280 } catch (RemoteException e) { 25281 } 25282 } 25283 app.pendingUiClean = false; 25284 } 25285 if (app.trimMemoryLevel < fgTrimLevel && app.thread != null) { 25286 try { 25287 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG_OOM_ADJ, 25288 "Trimming memory of fg " + app.processName 25289 + " to " + fgTrimLevel); 25290 app.thread.scheduleTrimMemory(fgTrimLevel); 25291 } catch (RemoteException e) { 25292 } 25293 } 25294 app.trimMemoryLevel = fgTrimLevel; 25295 } 25296 } 25297 } else { 25298 if (mLowRamStartTime != 0) { 25299 mLowRamTimeSinceLastIdle += now - mLowRamStartTime; 25300 mLowRamStartTime = 0; 25301 } 25302 for (int i=N-1; i>=0; i--) { 25303 ProcessRecord app = mLruProcesses.get(i); 25304 if (allChanged || app.procStateChanged) { 25305 setProcessTrackerStateLocked(app, trackerMemFactor, now); 25306 app.procStateChanged = false; 25307 } 25308 if ((app.curProcState >= ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND 25309 || app.systemNoUi) && app.pendingUiClean) { 25310 if (app.trimMemoryLevel < ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN 25311 && app.thread != null) { 25312 try { 25313 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG_OOM_ADJ, 25314 "Trimming memory of ui hidden " + app.processName 25315 + " to " + ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN); 25316 app.thread.scheduleTrimMemory( 25317 ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN); 25318 } catch (RemoteException e) { 25319 } 25320 } 25321 app.pendingUiClean = false; 25322 } 25323 app.trimMemoryLevel = 0; 25324 } 25325 } 25326 25327 if (mAlwaysFinishActivities) { 25328 // Need to do this on its own message because the stack may not 25329 // be in a consistent state at this point. 25330 mStackSupervisor.scheduleDestroyAllActivities(null, "always-finish"); 25331 } 25332 25333 if (allChanged) { 25334 requestPssAllProcsLocked(now, false, mProcessStats.isMemFactorLowered()); 25335 } 25336 25337 ArrayList<UidRecord> becameIdle = null; 25338 25339 // Update from any uid changes. 25340 if (mLocalPowerManager != null) { 25341 mLocalPowerManager.startUidChanges(); 25342 } 25343 for (int i=mActiveUids.size()-1; i>=0; i--) { 25344 final UidRecord uidRec = mActiveUids.valueAt(i); 25345 int uidChange = UidRecord.CHANGE_PROCSTATE; 25346 if (uidRec.curProcState != ActivityManager.PROCESS_STATE_NONEXISTENT 25347 && (uidRec.setProcState != uidRec.curProcState 25348 || uidRec.setWhitelist != uidRec.curWhitelist)) { 25349 if (DEBUG_UID_OBSERVERS) Slog.i(TAG_UID_OBSERVERS, 25350 "Changes in " + uidRec + ": proc state from " + uidRec.setProcState 25351 + " to " + uidRec.curProcState + ", whitelist from " + uidRec.setWhitelist 25352 + " to " + uidRec.curWhitelist); 25353 if (ActivityManager.isProcStateBackground(uidRec.curProcState) 25354 && !uidRec.curWhitelist) { 25355 // UID is now in the background (and not on the temp whitelist). Was it 25356 // previously in the foreground (or on the temp whitelist)? 25357 if (!ActivityManager.isProcStateBackground(uidRec.setProcState) 25358 || uidRec.setWhitelist) { 25359 uidRec.lastBackgroundTime = nowElapsed; 25360 if (!mHandler.hasMessages(IDLE_UIDS_MSG)) { 25361 // Note: the background settle time is in elapsed realtime, while 25362 // the handler time base is uptime. All this means is that we may 25363 // stop background uids later than we had intended, but that only 25364 // happens because the device was sleeping so we are okay anyway. 25365 mHandler.sendEmptyMessageDelayed(IDLE_UIDS_MSG, 25366 mConstants.BACKGROUND_SETTLE_TIME); 25367 } 25368 } 25369 if (uidRec.idle && !uidRec.setIdle) { 25370 uidChange = UidRecord.CHANGE_IDLE; 25371 if (becameIdle == null) { 25372 becameIdle = new ArrayList<>(); 25373 } 25374 becameIdle.add(uidRec); 25375 } 25376 } else { 25377 if (uidRec.idle) { 25378 uidChange = UidRecord.CHANGE_ACTIVE; 25379 EventLogTags.writeAmUidActive(uidRec.uid); 25380 uidRec.idle = false; 25381 } 25382 uidRec.lastBackgroundTime = 0; 25383 } 25384 final boolean wasCached = uidRec.setProcState 25385 > ActivityManager.PROCESS_STATE_RECEIVER; 25386 final boolean isCached = uidRec.curProcState 25387 > ActivityManager.PROCESS_STATE_RECEIVER; 25388 if (wasCached != isCached || 25389 uidRec.setProcState == ActivityManager.PROCESS_STATE_NONEXISTENT) { 25390 uidChange |= isCached ? UidRecord.CHANGE_CACHED : UidRecord.CHANGE_UNCACHED; 25391 } 25392 uidRec.setProcState = uidRec.curProcState; 25393 uidRec.setWhitelist = uidRec.curWhitelist; 25394 uidRec.setIdle = uidRec.idle; 25395 enqueueUidChangeLocked(uidRec, -1, uidChange); 25396 noteUidProcessState(uidRec.uid, uidRec.curProcState); 25397 if (uidRec.foregroundServices) { 25398 mServices.foregroundServiceProcStateChangedLocked(uidRec); 25399 } 25400 } 25401 } 25402 if (mLocalPowerManager != null) { 25403 mLocalPowerManager.finishUidChanges(); 25404 } 25405 25406 if (becameIdle != null) { 25407 // If we have any new uids that became idle this time, we need to make sure 25408 // they aren't left with running services. 25409 for (int i = becameIdle.size() - 1; i >= 0; i--) { 25410 mServices.stopInBackgroundLocked(becameIdle.get(i).uid); 25411 } 25412 } 25413 25414 if (mProcessStats.shouldWriteNowLocked(now)) { 25415 mHandler.post(new Runnable() { 25416 @Override public void run() { 25417 synchronized (ActivityManagerService.this) { 25418 mProcessStats.writeStateAsyncLocked(); 25419 } 25420 } 25421 }); 25422 } 25423 25424 if (DEBUG_OOM_ADJ) { 25425 final long duration = SystemClock.uptimeMillis() - now; 25426 if (false) { 25427 Slog.d(TAG_OOM_ADJ, "Did OOM ADJ in " + duration + "ms", 25428 new RuntimeException("here").fillInStackTrace()); 25429 } else { 25430 Slog.d(TAG_OOM_ADJ, "Did OOM ADJ in " + duration + "ms"); 25431 } 25432 } 25433 } 25434 25435 @Override 25436 public void makePackageIdle(String packageName, int userId) { 25437 if (checkCallingPermission(android.Manifest.permission.FORCE_STOP_PACKAGES) 25438 != PackageManager.PERMISSION_GRANTED) { 25439 String msg = "Permission Denial: makePackageIdle() from pid=" 25440 + Binder.getCallingPid() 25441 + ", uid=" + Binder.getCallingUid() 25442 + " requires " + android.Manifest.permission.FORCE_STOP_PACKAGES; 25443 Slog.w(TAG, msg); 25444 throw new SecurityException(msg); 25445 } 25446 final int callingPid = Binder.getCallingPid(); 25447 userId = mUserController.handleIncomingUser(callingPid, Binder.getCallingUid(), 25448 userId, true, ALLOW_FULL_ONLY, "makePackageIdle", null); 25449 long callingId = Binder.clearCallingIdentity(); 25450 synchronized(this) { 25451 try { 25452 IPackageManager pm = AppGlobals.getPackageManager(); 25453 int pkgUid = -1; 25454 try { 25455 pkgUid = pm.getPackageUid(packageName, MATCH_UNINSTALLED_PACKAGES 25456 | MATCH_DEBUG_TRIAGED_MISSING, UserHandle.USER_SYSTEM); 25457 } catch (RemoteException e) { 25458 } 25459 if (pkgUid == -1) { 25460 throw new IllegalArgumentException("Unknown package name " + packageName); 25461 } 25462 25463 if (mLocalPowerManager != null) { 25464 mLocalPowerManager.startUidChanges(); 25465 } 25466 final int appId = UserHandle.getAppId(pkgUid); 25467 final int N = mActiveUids.size(); 25468 for (int i=N-1; i>=0; i--) { 25469 final UidRecord uidRec = mActiveUids.valueAt(i); 25470 final long bgTime = uidRec.lastBackgroundTime; 25471 if (bgTime > 0 && !uidRec.idle) { 25472 if (UserHandle.getAppId(uidRec.uid) == appId) { 25473 if (userId == UserHandle.USER_ALL || 25474 userId == UserHandle.getUserId(uidRec.uid)) { 25475 EventLogTags.writeAmUidIdle(uidRec.uid); 25476 uidRec.idle = true; 25477 uidRec.setIdle = true; 25478 Slog.w(TAG, "Idling uid " + UserHandle.formatUid(uidRec.uid) 25479 + " from package " + packageName + " user " + userId); 25480 doStopUidLocked(uidRec.uid, uidRec); 25481 } 25482 } 25483 } 25484 } 25485 } finally { 25486 if (mLocalPowerManager != null) { 25487 mLocalPowerManager.finishUidChanges(); 25488 } 25489 Binder.restoreCallingIdentity(callingId); 25490 } 25491 } 25492 } 25493 25494 final void idleUids() { 25495 synchronized (this) { 25496 final int N = mActiveUids.size(); 25497 if (N <= 0) { 25498 return; 25499 } 25500 final long nowElapsed = SystemClock.elapsedRealtime(); 25501 final long maxBgTime = nowElapsed - mConstants.BACKGROUND_SETTLE_TIME; 25502 long nextTime = 0; 25503 if (mLocalPowerManager != null) { 25504 mLocalPowerManager.startUidChanges(); 25505 } 25506 for (int i=N-1; i>=0; i--) { 25507 final UidRecord uidRec = mActiveUids.valueAt(i); 25508 final long bgTime = uidRec.lastBackgroundTime; 25509 if (bgTime > 0 && !uidRec.idle) { 25510 if (bgTime <= maxBgTime) { 25511 EventLogTags.writeAmUidIdle(uidRec.uid); 25512 uidRec.idle = true; 25513 uidRec.setIdle = true; 25514 doStopUidLocked(uidRec.uid, uidRec); 25515 } else { 25516 if (nextTime == 0 || nextTime > bgTime) { 25517 nextTime = bgTime; 25518 } 25519 } 25520 } 25521 } 25522 if (mLocalPowerManager != null) { 25523 mLocalPowerManager.finishUidChanges(); 25524 } 25525 if (nextTime > 0) { 25526 mHandler.removeMessages(IDLE_UIDS_MSG); 25527 mHandler.sendEmptyMessageDelayed(IDLE_UIDS_MSG, 25528 nextTime + mConstants.BACKGROUND_SETTLE_TIME - nowElapsed); 25529 } 25530 } 25531 } 25532 25533 /** 25534 * Checks if any uid is coming from background to foreground or vice versa and if so, increments 25535 * the {@link UidRecord#curProcStateSeq} corresponding to that uid using global seq counter 25536 * {@link #mProcStateSeqCounter} and notifies the app if it needs to block. 25537 */ 25538 @VisibleForTesting 25539 @GuardedBy("this") 25540 void incrementProcStateSeqAndNotifyAppsLocked() { 25541 if (mWaitForNetworkTimeoutMs <= 0) { 25542 return; 25543 } 25544 // Used for identifying which uids need to block for network. 25545 ArrayList<Integer> blockingUids = null; 25546 for (int i = mActiveUids.size() - 1; i >= 0; --i) { 25547 final UidRecord uidRec = mActiveUids.valueAt(i); 25548 // If the network is not restricted for uid, then nothing to do here. 25549 if (!mInjector.isNetworkRestrictedForUid(uidRec.uid)) { 25550 continue; 25551 } 25552 if (!UserHandle.isApp(uidRec.uid) || !uidRec.hasInternetPermission) { 25553 continue; 25554 } 25555 // If process state is not changed, then there's nothing to do. 25556 if (uidRec.setProcState == uidRec.curProcState) { 25557 continue; 25558 } 25559 final int blockState = getBlockStateForUid(uidRec); 25560 // No need to inform the app when the blockState is NETWORK_STATE_NO_CHANGE as 25561 // there's nothing the app needs to do in this scenario. 25562 if (blockState == NETWORK_STATE_NO_CHANGE) { 25563 continue; 25564 } 25565 synchronized (uidRec.networkStateLock) { 25566 uidRec.curProcStateSeq = ++mProcStateSeqCounter; 25567 if (blockState == NETWORK_STATE_BLOCK) { 25568 if (blockingUids == null) { 25569 blockingUids = new ArrayList<>(); 25570 } 25571 blockingUids.add(uidRec.uid); 25572 } else { 25573 if (DEBUG_NETWORK) { 25574 Slog.d(TAG_NETWORK, "uid going to background, notifying all blocking" 25575 + " threads for uid: " + uidRec); 25576 } 25577 if (uidRec.waitingForNetwork) { 25578 uidRec.networkStateLock.notifyAll(); 25579 } 25580 } 25581 } 25582 } 25583 25584 // There are no uids that need to block, so nothing more to do. 25585 if (blockingUids == null) { 25586 return; 25587 } 25588 25589 for (int i = mLruProcesses.size() - 1; i >= 0; --i) { 25590 final ProcessRecord app = mLruProcesses.get(i); 25591 if (!blockingUids.contains(app.uid)) { 25592 continue; 25593 } 25594 if (!app.killedByAm && app.thread != null) { 25595 final UidRecord uidRec = mActiveUids.get(app.uid); 25596 try { 25597 if (DEBUG_NETWORK) { 25598 Slog.d(TAG_NETWORK, "Informing app thread that it needs to block: " 25599 + uidRec); 25600 } 25601 app.thread.setNetworkBlockSeq(uidRec.curProcStateSeq); 25602 } catch (RemoteException ignored) { 25603 } 25604 } 25605 } 25606 } 25607 25608 /** 25609 * Checks if the uid is coming from background to foreground or vice versa and returns 25610 * appropriate block state based on this. 25611 * 25612 * @return blockState based on whether the uid is coming from background to foreground or 25613 * vice versa. If bg->fg or fg->bg, then {@link #NETWORK_STATE_BLOCK} or 25614 * {@link #NETWORK_STATE_UNBLOCK} respectively, otherwise 25615 * {@link #NETWORK_STATE_NO_CHANGE}. 25616 */ 25617 @VisibleForTesting 25618 int getBlockStateForUid(UidRecord uidRec) { 25619 // Denotes whether uid's process state is currently allowed network access. 25620 final boolean isAllowed = isProcStateAllowedWhileIdleOrPowerSaveMode(uidRec.curProcState) 25621 || isProcStateAllowedWhileOnRestrictBackground(uidRec.curProcState); 25622 // Denotes whether uid's process state was previously allowed network access. 25623 final boolean wasAllowed = isProcStateAllowedWhileIdleOrPowerSaveMode(uidRec.setProcState) 25624 || isProcStateAllowedWhileOnRestrictBackground(uidRec.setProcState); 25625 25626 // When the uid is coming to foreground, AMS should inform the app thread that it should 25627 // block for the network rules to get updated before launching an activity. 25628 if (!wasAllowed && isAllowed) { 25629 return NETWORK_STATE_BLOCK; 25630 } 25631 // When the uid is going to background, AMS should inform the app thread that if an 25632 // activity launch is blocked for the network rules to get updated, it should be unblocked. 25633 if (wasAllowed && !isAllowed) { 25634 return NETWORK_STATE_UNBLOCK; 25635 } 25636 return NETWORK_STATE_NO_CHANGE; 25637 } 25638 25639 final void runInBackgroundDisabled(int uid) { 25640 synchronized (this) { 25641 UidRecord uidRec = mActiveUids.get(uid); 25642 if (uidRec != null) { 25643 // This uid is actually running... should it be considered background now? 25644 if (uidRec.idle) { 25645 doStopUidLocked(uidRec.uid, uidRec); 25646 } 25647 } else { 25648 // This uid isn't actually running... still send a report about it being "stopped". 25649 doStopUidLocked(uid, null); 25650 } 25651 } 25652 } 25653 25654 /** 25655 * Call {@link #doStopUidLocked} (which will also stop background services) for all idle UIDs. 25656 */ 25657 void doStopUidForIdleUidsLocked() { 25658 final int size = mActiveUids.size(); 25659 for (int i = 0; i < size; i++) { 25660 final int uid = mActiveUids.keyAt(i); 25661 if (UserHandle.isCore(uid)) { 25662 continue; 25663 } 25664 final UidRecord uidRec = mActiveUids.valueAt(i); 25665 if (!uidRec.idle) { 25666 continue; 25667 } 25668 doStopUidLocked(uidRec.uid, uidRec); 25669 } 25670 } 25671 25672 final void doStopUidLocked(int uid, final UidRecord uidRec) { 25673 mServices.stopInBackgroundLocked(uid); 25674 enqueueUidChangeLocked(uidRec, uid, UidRecord.CHANGE_IDLE); 25675 } 25676 25677 /** 25678 * Whitelists {@code targetUid} to temporarily bypass Power Save mode. 25679 */ 25680 @GuardedBy("this") 25681 void tempWhitelistForPendingIntentLocked(int callerPid, int callerUid, int targetUid, 25682 long duration, String tag) { 25683 if (DEBUG_WHITELISTS) { 25684 Slog.d(TAG, "tempWhitelistForPendingIntentLocked(" + callerPid + ", " + callerUid + ", " 25685 + targetUid + ", " + duration + ")"); 25686 } 25687 25688 synchronized (mPidsSelfLocked) { 25689 final ProcessRecord pr = mPidsSelfLocked.get(callerPid); 25690 if (pr == null) { 25691 Slog.w(TAG, "tempWhitelistForPendingIntentLocked() no ProcessRecord for pid " 25692 + callerPid); 25693 return; 25694 } 25695 if (!pr.whitelistManager) { 25696 if (checkPermission(CHANGE_DEVICE_IDLE_TEMP_WHITELIST, callerPid, callerUid) 25697 != PackageManager.PERMISSION_GRANTED) { 25698 if (DEBUG_WHITELISTS) { 25699 Slog.d(TAG, "tempWhitelistForPendingIntentLocked() for target " + targetUid 25700 + ": pid " + callerPid + " is not allowed"); 25701 } 25702 return; 25703 } 25704 } 25705 } 25706 25707 tempWhitelistUidLocked(targetUid, duration, tag); 25708 } 25709 25710 /** 25711 * Whitelists {@code targetUid} to temporarily bypass Power Save mode. 25712 */ 25713 @GuardedBy("this") 25714 void tempWhitelistUidLocked(int targetUid, long duration, String tag) { 25715 mPendingTempWhitelist.put(targetUid, new PendingTempWhitelist(targetUid, duration, tag)); 25716 setUidTempWhitelistStateLocked(targetUid, true); 25717 mUiHandler.obtainMessage(PUSH_TEMP_WHITELIST_UI_MSG).sendToTarget(); 25718 } 25719 25720 void pushTempWhitelist() { 25721 final int N; 25722 final PendingTempWhitelist[] list; 25723 25724 // First copy out the pending changes... we need to leave them in the map for now, 25725 // in case someone needs to check what is coming up while we don't have the lock held. 25726 synchronized(this) { 25727 N = mPendingTempWhitelist.size(); 25728 list = new PendingTempWhitelist[N]; 25729 for (int i = 0; i < N; i++) { 25730 list[i] = mPendingTempWhitelist.valueAt(i); 25731 } 25732 } 25733 25734 // Now safely dispatch changes to device idle controller. 25735 for (int i = 0; i < N; i++) { 25736 PendingTempWhitelist ptw = list[i]; 25737 mLocalDeviceIdleController.addPowerSaveTempWhitelistAppDirect(ptw.targetUid, 25738 ptw.duration, true, ptw.tag); 25739 } 25740 25741 // And now we can safely remove them from the map. 25742 synchronized(this) { 25743 for (int i = 0; i < N; i++) { 25744 PendingTempWhitelist ptw = list[i]; 25745 int index = mPendingTempWhitelist.indexOfKey(ptw.targetUid); 25746 if (index >= 0 && mPendingTempWhitelist.valueAt(index) == ptw) { 25747 mPendingTempWhitelist.removeAt(index); 25748 } 25749 } 25750 } 25751 } 25752 25753 @GuardedBy("this") 25754 final void setAppIdTempWhitelistStateLocked(int appId, boolean onWhitelist) { 25755 boolean changed = false; 25756 for (int i=mActiveUids.size()-1; i>=0; i--) { 25757 final UidRecord uidRec = mActiveUids.valueAt(i); 25758 if (UserHandle.getAppId(uidRec.uid) == appId && uidRec.curWhitelist != onWhitelist) { 25759 uidRec.curWhitelist = onWhitelist; 25760 changed = true; 25761 } 25762 } 25763 if (changed) { 25764 updateOomAdjLocked(); 25765 } 25766 } 25767 25768 @GuardedBy("this") 25769 final void setUidTempWhitelistStateLocked(int uid, boolean onWhitelist) { 25770 boolean changed = false; 25771 final UidRecord uidRec = mActiveUids.get(uid); 25772 if (uidRec != null && uidRec.curWhitelist != onWhitelist) { 25773 uidRec.curWhitelist = onWhitelist; 25774 updateOomAdjLocked(); 25775 } 25776 } 25777 25778 final void trimApplications() { 25779 synchronized (this) { 25780 trimApplicationsLocked(); 25781 } 25782 } 25783 25784 final void trimApplicationsLocked() { 25785 // First remove any unused application processes whose package 25786 // has been removed. 25787 for (int i=mRemovedProcesses.size()-1; i>=0; i--) { 25788 final ProcessRecord app = mRemovedProcesses.get(i); 25789 if (app.activities.size() == 0 && app.recentTasks.size() == 0 25790 && app.curReceivers.isEmpty() && app.services.size() == 0) { 25791 Slog.i( 25792 TAG, "Exiting empty application process " 25793 + app.toShortString() + " (" 25794 + (app.thread != null ? app.thread.asBinder() : null) 25795 + ")\n"); 25796 if (app.pid > 0 && app.pid != MY_PID) { 25797 app.kill("empty", false); 25798 } else if (app.thread != null) { 25799 try { 25800 app.thread.scheduleExit(); 25801 } catch (Exception e) { 25802 // Ignore exceptions. 25803 } 25804 } 25805 cleanUpApplicationRecordLocked(app, false, true, -1, false /*replacingPid*/); 25806 mRemovedProcesses.remove(i); 25807 25808 if (app.persistent) { 25809 addAppLocked(app.info, null, false, null /* ABI override */); 25810 } 25811 } 25812 } 25813 25814 // Now update the oom adj for all processes. Don't skip this, since other callers 25815 // might be depending on it. 25816 updateOomAdjLocked(); 25817 } 25818 25819 /** This method sends the specified signal to each of the persistent apps */ 25820 public void signalPersistentProcesses(int sig) throws RemoteException { 25821 if (sig != SIGNAL_USR1) { 25822 throw new SecurityException("Only SIGNAL_USR1 is allowed"); 25823 } 25824 25825 synchronized (this) { 25826 if (checkCallingPermission(android.Manifest.permission.SIGNAL_PERSISTENT_PROCESSES) 25827 != PackageManager.PERMISSION_GRANTED) { 25828 throw new SecurityException("Requires permission " 25829 + android.Manifest.permission.SIGNAL_PERSISTENT_PROCESSES); 25830 } 25831 25832 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 25833 ProcessRecord r = mLruProcesses.get(i); 25834 if (r.thread != null && r.persistent) { 25835 sendSignal(r.pid, sig); 25836 } 25837 } 25838 } 25839 } 25840 25841 private void stopProfilerLocked(ProcessRecord proc, int profileType) { 25842 if (proc == null || proc == mProfileProc) { 25843 proc = mProfileProc; 25844 profileType = mProfileType; 25845 clearProfilerLocked(); 25846 } 25847 if (proc == null) { 25848 return; 25849 } 25850 try { 25851 proc.thread.profilerControl(false, null, profileType); 25852 } catch (RemoteException e) { 25853 throw new IllegalStateException("Process disappeared"); 25854 } 25855 } 25856 25857 private void clearProfilerLocked() { 25858 if (mProfilerInfo !=null && mProfilerInfo.profileFd != null) { 25859 try { 25860 mProfilerInfo.profileFd.close(); 25861 } catch (IOException e) { 25862 } 25863 } 25864 mProfileApp = null; 25865 mProfileProc = null; 25866 mProfilerInfo = null; 25867 } 25868 25869 public boolean profileControl(String process, int userId, boolean start, 25870 ProfilerInfo profilerInfo, int profileType) throws RemoteException { 25871 25872 try { 25873 synchronized (this) { 25874 // note: hijacking SET_ACTIVITY_WATCHER, but should be changed to 25875 // its own permission. 25876 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 25877 != PackageManager.PERMISSION_GRANTED) { 25878 throw new SecurityException("Requires permission " 25879 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 25880 } 25881 25882 if (start && (profilerInfo == null || profilerInfo.profileFd == null)) { 25883 throw new IllegalArgumentException("null profile info or fd"); 25884 } 25885 25886 ProcessRecord proc = null; 25887 if (process != null) { 25888 proc = findProcessLocked(process, userId, "profileControl"); 25889 } 25890 25891 if (start && (proc == null || proc.thread == null)) { 25892 throw new IllegalArgumentException("Unknown process: " + process); 25893 } 25894 25895 if (start) { 25896 stopProfilerLocked(null, 0); 25897 setProfileApp(proc.info, proc.processName, profilerInfo); 25898 mProfileProc = proc; 25899 mProfileType = profileType; 25900 ParcelFileDescriptor fd = profilerInfo.profileFd; 25901 try { 25902 fd = fd.dup(); 25903 } catch (IOException e) { 25904 fd = null; 25905 } 25906 profilerInfo.profileFd = fd; 25907 proc.thread.profilerControl(start, profilerInfo, profileType); 25908 fd = null; 25909 try { 25910 mProfilerInfo.profileFd.close(); 25911 } catch (IOException e) { 25912 } 25913 mProfilerInfo.profileFd = null; 25914 25915 if (proc.pid == MY_PID) { 25916 // When profiling the system server itself, avoid closing the file 25917 // descriptor, as profilerControl will not create a copy. 25918 // Note: it is also not correct to just set profileFd to null, as the 25919 // whole ProfilerInfo instance is passed down! 25920 profilerInfo = null; 25921 } 25922 } else { 25923 stopProfilerLocked(proc, profileType); 25924 if (profilerInfo != null && profilerInfo.profileFd != null) { 25925 try { 25926 profilerInfo.profileFd.close(); 25927 } catch (IOException e) { 25928 } 25929 } 25930 } 25931 25932 return true; 25933 } 25934 } catch (RemoteException e) { 25935 throw new IllegalStateException("Process disappeared"); 25936 } finally { 25937 if (profilerInfo != null && profilerInfo.profileFd != null) { 25938 try { 25939 profilerInfo.profileFd.close(); 25940 } catch (IOException e) { 25941 } 25942 } 25943 } 25944 } 25945 25946 private ProcessRecord findProcessLocked(String process, int userId, String callName) { 25947 userId = mUserController.handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 25948 userId, true, ALLOW_FULL_ONLY, callName, null); 25949 ProcessRecord proc = null; 25950 try { 25951 int pid = Integer.parseInt(process); 25952 synchronized (mPidsSelfLocked) { 25953 proc = mPidsSelfLocked.get(pid); 25954 } 25955 } catch (NumberFormatException e) { 25956 } 25957 25958 if (proc == null) { 25959 ArrayMap<String, SparseArray<ProcessRecord>> all 25960 = mProcessNames.getMap(); 25961 SparseArray<ProcessRecord> procs = all.get(process); 25962 if (procs != null && procs.size() > 0) { 25963 proc = procs.valueAt(0); 25964 if (userId != UserHandle.USER_ALL && proc.userId != userId) { 25965 for (int i=1; i<procs.size(); i++) { 25966 ProcessRecord thisProc = procs.valueAt(i); 25967 if (thisProc.userId == userId) { 25968 proc = thisProc; 25969 break; 25970 } 25971 } 25972 } 25973 } 25974 } 25975 25976 return proc; 25977 } 25978 25979 public boolean dumpHeap(String process, int userId, boolean managed, boolean mallocInfo, 25980 boolean runGc, String path, ParcelFileDescriptor fd) throws RemoteException { 25981 25982 try { 25983 synchronized (this) { 25984 // note: hijacking SET_ACTIVITY_WATCHER, but should be changed to 25985 // its own permission (same as profileControl). 25986 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 25987 != PackageManager.PERMISSION_GRANTED) { 25988 throw new SecurityException("Requires permission " 25989 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 25990 } 25991 25992 if (fd == null) { 25993 throw new IllegalArgumentException("null fd"); 25994 } 25995 25996 ProcessRecord proc = findProcessLocked(process, userId, "dumpHeap"); 25997 if (proc == null || proc.thread == null) { 25998 throw new IllegalArgumentException("Unknown process: " + process); 25999 } 26000 26001 boolean isDebuggable = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 26002 if (!isDebuggable) { 26003 if ((proc.info.flags&ApplicationInfo.FLAG_DEBUGGABLE) == 0) { 26004 throw new SecurityException("Process not debuggable: " + proc); 26005 } 26006 } 26007 26008 proc.thread.dumpHeap(managed, mallocInfo, runGc, path, fd); 26009 fd = null; 26010 return true; 26011 } 26012 } catch (RemoteException e) { 26013 throw new IllegalStateException("Process disappeared"); 26014 } finally { 26015 if (fd != null) { 26016 try { 26017 fd.close(); 26018 } catch (IOException e) { 26019 } 26020 } 26021 } 26022 } 26023 26024 @Override 26025 public void setDumpHeapDebugLimit(String processName, int uid, long maxMemSize, 26026 String reportPackage) { 26027 if (processName != null) { 26028 enforceCallingPermission(android.Manifest.permission.SET_DEBUG_APP, 26029 "setDumpHeapDebugLimit()"); 26030 } else { 26031 synchronized (mPidsSelfLocked) { 26032 ProcessRecord proc = mPidsSelfLocked.get(Binder.getCallingPid()); 26033 if (proc == null) { 26034 throw new SecurityException("No process found for calling pid " 26035 + Binder.getCallingPid()); 26036 } 26037 if (!Build.IS_DEBUGGABLE 26038 && (proc.info.flags&ApplicationInfo.FLAG_DEBUGGABLE) == 0) { 26039 throw new SecurityException("Not running a debuggable build"); 26040 } 26041 processName = proc.processName; 26042 uid = proc.uid; 26043 if (reportPackage != null && !proc.pkgList.containsKey(reportPackage)) { 26044 throw new SecurityException("Package " + reportPackage + " is not running in " 26045 + proc); 26046 } 26047 } 26048 } 26049 synchronized (this) { 26050 if (maxMemSize > 0) { 26051 mMemWatchProcesses.put(processName, uid, new Pair(maxMemSize, reportPackage)); 26052 } else { 26053 if (uid != 0) { 26054 mMemWatchProcesses.remove(processName, uid); 26055 } else { 26056 mMemWatchProcesses.getMap().remove(processName); 26057 } 26058 } 26059 } 26060 } 26061 26062 @Override 26063 public void dumpHeapFinished(String path) { 26064 synchronized (this) { 26065 if (Binder.getCallingPid() != mMemWatchDumpPid) { 26066 Slog.w(TAG, "dumpHeapFinished: Calling pid " + Binder.getCallingPid() 26067 + " does not match last pid " + mMemWatchDumpPid); 26068 return; 26069 } 26070 if (mMemWatchDumpFile == null || !mMemWatchDumpFile.equals(path)) { 26071 Slog.w(TAG, "dumpHeapFinished: Calling path " + path 26072 + " does not match last path " + mMemWatchDumpFile); 26073 return; 26074 } 26075 if (DEBUG_PSS) Slog.d(TAG_PSS, "Dump heap finished for " + path); 26076 mHandler.sendEmptyMessage(POST_DUMP_HEAP_NOTIFICATION_MSG); 26077 26078 // Forced gc to clean up the remnant hprof fd. 26079 Runtime.getRuntime().gc(); 26080 } 26081 } 26082 26083 /** In this method we try to acquire our lock to make sure that we have not deadlocked */ 26084 public void monitor() { 26085 synchronized (this) { } 26086 } 26087 26088 void onCoreSettingsChange(Bundle settings) { 26089 for (int i = mLruProcesses.size() - 1; i >= 0; i--) { 26090 ProcessRecord processRecord = mLruProcesses.get(i); 26091 try { 26092 if (processRecord.thread != null) { 26093 processRecord.thread.setCoreSettings(settings); 26094 } 26095 } catch (RemoteException re) { 26096 /* ignore */ 26097 } 26098 } 26099 } 26100 26101 // Multi-user methods 26102 26103 /** 26104 * Start user, if its not already running, but don't bring it to foreground. 26105 */ 26106 @Override 26107 public boolean startUserInBackground(final int userId) { 26108 return startUserInBackgroundWithListener(userId, null); 26109 } 26110 26111 @Override 26112 public boolean startUserInBackgroundWithListener(final int userId, 26113 @Nullable IProgressListener unlockListener) { 26114 return mUserController.startUser(userId, /* foreground */ false, unlockListener); 26115 } 26116 26117 @Override 26118 public boolean unlockUser(int userId, byte[] token, byte[] secret, IProgressListener listener) { 26119 return mUserController.unlockUser(userId, token, secret, listener); 26120 } 26121 26122 @Override 26123 public boolean switchUser(final int targetUserId) { 26124 return mUserController.switchUser(targetUserId); 26125 } 26126 26127 @Override 26128 public int stopUser(final int userId, boolean force, final IStopUserCallback callback) { 26129 return mUserController.stopUser(userId, force, callback); 26130 } 26131 26132 @Override 26133 public UserInfo getCurrentUser() { 26134 return mUserController.getCurrentUser(); 26135 } 26136 26137 String getStartedUserState(int userId) { 26138 final UserState userState = mUserController.getStartedUserState(userId); 26139 return UserState.stateToString(userState.state); 26140 } 26141 26142 @Override 26143 public boolean isUserRunning(int userId, int flags) { 26144 if (!mUserController.isSameProfileGroup(userId, UserHandle.getCallingUserId()) 26145 && checkCallingPermission(INTERACT_ACROSS_USERS) 26146 != PackageManager.PERMISSION_GRANTED) { 26147 String msg = "Permission Denial: isUserRunning() from pid=" 26148 + Binder.getCallingPid() 26149 + ", uid=" + Binder.getCallingUid() 26150 + " requires " + INTERACT_ACROSS_USERS; 26151 Slog.w(TAG, msg); 26152 throw new SecurityException(msg); 26153 } 26154 return mUserController.isUserRunning(userId, flags); 26155 } 26156 26157 @Override 26158 public int[] getRunningUserIds() { 26159 if (checkCallingPermission(INTERACT_ACROSS_USERS) 26160 != PackageManager.PERMISSION_GRANTED) { 26161 String msg = "Permission Denial: isUserRunning() from pid=" 26162 + Binder.getCallingPid() 26163 + ", uid=" + Binder.getCallingUid() 26164 + " requires " + INTERACT_ACROSS_USERS; 26165 Slog.w(TAG, msg); 26166 throw new SecurityException(msg); 26167 } 26168 return mUserController.getStartedUserArray(); 26169 } 26170 26171 @Override 26172 public void registerUserSwitchObserver(IUserSwitchObserver observer, String name) { 26173 mUserController.registerUserSwitchObserver(observer, name); 26174 } 26175 26176 @Override 26177 public void unregisterUserSwitchObserver(IUserSwitchObserver observer) { 26178 mUserController.unregisterUserSwitchObserver(observer); 26179 } 26180 26181 ApplicationInfo getAppInfoForUser(ApplicationInfo info, int userId) { 26182 if (info == null) return null; 26183 ApplicationInfo newInfo = new ApplicationInfo(info); 26184 newInfo.initForUser(userId); 26185 return newInfo; 26186 } 26187 26188 public boolean isUserStopped(int userId) { 26189 return mUserController.getStartedUserState(userId) == null; 26190 } 26191 26192 ActivityInfo getActivityInfoForUser(ActivityInfo aInfo, int userId) { 26193 if (aInfo == null 26194 || (userId < 1 && aInfo.applicationInfo.uid < UserHandle.PER_USER_RANGE)) { 26195 return aInfo; 26196 } 26197 26198 ActivityInfo info = new ActivityInfo(aInfo); 26199 info.applicationInfo = getAppInfoForUser(info.applicationInfo, userId); 26200 return info; 26201 } 26202 26203 private boolean processSanityChecksLocked(ProcessRecord process) { 26204 if (process == null || process.thread == null) { 26205 return false; 26206 } 26207 26208 boolean isDebuggable = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 26209 if (!isDebuggable) { 26210 if ((process.info.flags&ApplicationInfo.FLAG_DEBUGGABLE) == 0) { 26211 return false; 26212 } 26213 } 26214 26215 return true; 26216 } 26217 26218 public boolean startBinderTracking() throws RemoteException { 26219 synchronized (this) { 26220 mBinderTransactionTrackingEnabled = true; 26221 // TODO: hijacking SET_ACTIVITY_WATCHER, but should be changed to its own 26222 // permission (same as profileControl). 26223 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 26224 != PackageManager.PERMISSION_GRANTED) { 26225 throw new SecurityException("Requires permission " 26226 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 26227 } 26228 26229 for (int i = 0; i < mLruProcesses.size(); i++) { 26230 ProcessRecord process = mLruProcesses.get(i); 26231 if (!processSanityChecksLocked(process)) { 26232 continue; 26233 } 26234 try { 26235 process.thread.startBinderTracking(); 26236 } catch (RemoteException e) { 26237 Log.v(TAG, "Process disappared"); 26238 } 26239 } 26240 return true; 26241 } 26242 } 26243 26244 public boolean stopBinderTrackingAndDump(ParcelFileDescriptor fd) throws RemoteException { 26245 try { 26246 synchronized (this) { 26247 mBinderTransactionTrackingEnabled = false; 26248 // TODO: hijacking SET_ACTIVITY_WATCHER, but should be changed to its own 26249 // permission (same as profileControl). 26250 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 26251 != PackageManager.PERMISSION_GRANTED) { 26252 throw new SecurityException("Requires permission " 26253 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 26254 } 26255 26256 if (fd == null) { 26257 throw new IllegalArgumentException("null fd"); 26258 } 26259 26260 PrintWriter pw = new FastPrintWriter(new FileOutputStream(fd.getFileDescriptor())); 26261 pw.println("Binder transaction traces for all processes.\n"); 26262 for (ProcessRecord process : mLruProcesses) { 26263 if (!processSanityChecksLocked(process)) { 26264 continue; 26265 } 26266 26267 pw.println("Traces for process: " + process.processName); 26268 pw.flush(); 26269 try { 26270 TransferPipe tp = new TransferPipe(); 26271 try { 26272 process.thread.stopBinderTrackingAndDump(tp.getWriteFd()); 26273 tp.go(fd.getFileDescriptor()); 26274 } finally { 26275 tp.kill(); 26276 } 26277 } catch (IOException e) { 26278 pw.println("Failure while dumping IPC traces from " + process + 26279 ". Exception: " + e); 26280 pw.flush(); 26281 } catch (RemoteException e) { 26282 pw.println("Got a RemoteException while dumping IPC traces from " + 26283 process + ". Exception: " + e); 26284 pw.flush(); 26285 } 26286 } 26287 fd = null; 26288 return true; 26289 } 26290 } finally { 26291 if (fd != null) { 26292 try { 26293 fd.close(); 26294 } catch (IOException e) { 26295 } 26296 } 26297 } 26298 } 26299 26300 @VisibleForTesting 26301 final class LocalService extends ActivityManagerInternal { 26302 @Override 26303 public void grantUriPermissionFromIntent(int callingUid, String targetPkg, Intent intent, 26304 int targetUserId) { 26305 synchronized (ActivityManagerService.this) { 26306 ActivityManagerService.this.grantUriPermissionFromIntentLocked(callingUid, 26307 targetPkg, intent, null, targetUserId); 26308 } 26309 } 26310 26311 @Override 26312 public String checkContentProviderAccess(String authority, int userId) { 26313 return ActivityManagerService.this.checkContentProviderAccess(authority, userId); 26314 } 26315 26316 @Override 26317 public void onWakefulnessChanged(int wakefulness) { 26318 ActivityManagerService.this.onWakefulnessChanged(wakefulness); 26319 } 26320 26321 @Override 26322 public boolean startIsolatedProcess(String entryPoint, String[] entryPointArgs, 26323 String processName, String abiOverride, int uid, Runnable crashHandler) { 26324 return ActivityManagerService.this.startIsolatedProcess(entryPoint, entryPointArgs, 26325 processName, abiOverride, uid, crashHandler); 26326 } 26327 26328 @Override 26329 public SleepToken acquireSleepToken(String tag, int displayId) { 26330 Preconditions.checkNotNull(tag); 26331 return ActivityManagerService.this.acquireSleepToken(tag, displayId); 26332 } 26333 26334 @Override 26335 public ComponentName getHomeActivityForUser(int userId) { 26336 synchronized (ActivityManagerService.this) { 26337 ActivityRecord homeActivity = mStackSupervisor.getHomeActivityForUser(userId); 26338 return homeActivity == null ? null : homeActivity.realActivity; 26339 } 26340 } 26341 26342 @Override 26343 public void onUserRemoved(int userId) { 26344 synchronized (ActivityManagerService.this) { 26345 ActivityManagerService.this.onUserStoppedLocked(userId); 26346 } 26347 mBatteryStatsService.onUserRemoved(userId); 26348 mUserController.onUserRemoved(userId); 26349 } 26350 26351 @Override 26352 public void onLocalVoiceInteractionStarted(IBinder activity, 26353 IVoiceInteractionSession voiceSession, IVoiceInteractor voiceInteractor) { 26354 synchronized (ActivityManagerService.this) { 26355 ActivityManagerService.this.onLocalVoiceInteractionStartedLocked(activity, 26356 voiceSession, voiceInteractor); 26357 } 26358 } 26359 26360 @Override 26361 public void notifyAppTransitionStarting(SparseIntArray reasons, long timestamp) { 26362 synchronized (ActivityManagerService.this) { 26363 mStackSupervisor.getActivityMetricsLogger().notifyTransitionStarting( 26364 reasons, timestamp); 26365 } 26366 } 26367 26368 @Override 26369 public void notifyAppTransitionFinished() { 26370 synchronized (ActivityManagerService.this) { 26371 mStackSupervisor.notifyAppTransitionDone(); 26372 } 26373 } 26374 26375 @Override 26376 public void notifyAppTransitionCancelled() { 26377 synchronized (ActivityManagerService.this) { 26378 mStackSupervisor.notifyAppTransitionDone(); 26379 } 26380 } 26381 26382 @Override 26383 public List<IBinder> getTopVisibleActivities() { 26384 synchronized (ActivityManagerService.this) { 26385 return mStackSupervisor.getTopVisibleActivities(); 26386 } 26387 } 26388 26389 @Override 26390 public void notifyDockedStackMinimizedChanged(boolean minimized) { 26391 synchronized (ActivityManagerService.this) { 26392 mStackSupervisor.setDockedStackMinimized(minimized); 26393 } 26394 } 26395 26396 @Override 26397 public void killForegroundAppsForUser(int userHandle) { 26398 synchronized (ActivityManagerService.this) { 26399 final ArrayList<ProcessRecord> procs = new ArrayList<>(); 26400 final int NP = mProcessNames.getMap().size(); 26401 for (int ip = 0; ip < NP; ip++) { 26402 final SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 26403 final int NA = apps.size(); 26404 for (int ia = 0; ia < NA; ia++) { 26405 final ProcessRecord app = apps.valueAt(ia); 26406 if (app.persistent) { 26407 // We don't kill persistent processes. 26408 continue; 26409 } 26410 if (app.removed) { 26411 procs.add(app); 26412 } else if (app.userId == userHandle && app.foregroundActivities) { 26413 app.removed = true; 26414 procs.add(app); 26415 } 26416 } 26417 } 26418 26419 final int N = procs.size(); 26420 for (int i = 0; i < N; i++) { 26421 removeProcessLocked(procs.get(i), false, true, "kill all fg"); 26422 } 26423 } 26424 } 26425 26426 @Override 26427 public void setPendingIntentWhitelistDuration(IIntentSender target, IBinder whitelistToken, 26428 long duration) { 26429 if (!(target instanceof PendingIntentRecord)) { 26430 Slog.w(TAG, "markAsSentFromNotification(): not a PendingIntentRecord: " + target); 26431 return; 26432 } 26433 synchronized (ActivityManagerService.this) { 26434 ((PendingIntentRecord) target).setWhitelistDurationLocked(whitelistToken, duration); 26435 } 26436 } 26437 26438 @Override 26439 public void setDeviceIdleWhitelist(int[] allAppids, int[] exceptIdleAppids) { 26440 synchronized (ActivityManagerService.this) { 26441 mDeviceIdleWhitelist = allAppids; 26442 mDeviceIdleExceptIdleWhitelist = exceptIdleAppids; 26443 } 26444 } 26445 26446 @Override 26447 public void updateDeviceIdleTempWhitelist(int[] appids, int changingAppId, boolean adding) { 26448 synchronized (ActivityManagerService.this) { 26449 mDeviceIdleTempWhitelist = appids; 26450 setAppIdTempWhitelistStateLocked(changingAppId, adding); 26451 } 26452 } 26453 26454 @Override 26455 public void updatePersistentConfigurationForUser(@NonNull Configuration values, 26456 int userId) { 26457 Preconditions.checkNotNull(values, "Configuration must not be null"); 26458 Preconditions.checkArgumentNonnegative(userId, "userId " + userId + " not supported"); 26459 synchronized (ActivityManagerService.this) { 26460 updateConfigurationLocked(values, null, false, true, userId, 26461 false /* deferResume */); 26462 } 26463 } 26464 26465 @Override 26466 public int startActivitiesAsPackage(String packageName, int userId, Intent[] intents, 26467 Bundle bOptions) { 26468 Preconditions.checkNotNull(intents, "intents"); 26469 final String[] resolvedTypes = new String[intents.length]; 26470 26471 // UID of the package on user userId. 26472 // "= 0" is needed because otherwise catch(RemoteException) would make it look like 26473 // packageUid may not be initialized. 26474 int packageUid = 0; 26475 final long ident = Binder.clearCallingIdentity(); 26476 26477 try { 26478 for (int i = 0; i < intents.length; i++) { 26479 resolvedTypes[i] = 26480 intents[i].resolveTypeIfNeeded(mContext.getContentResolver()); 26481 } 26482 26483 packageUid = AppGlobals.getPackageManager().getPackageUid( 26484 packageName, PackageManager.MATCH_DEBUG_TRIAGED_MISSING, userId); 26485 } catch (RemoteException e) { 26486 // Shouldn't happen. 26487 } finally { 26488 Binder.restoreCallingIdentity(ident); 26489 } 26490 26491 synchronized (ActivityManagerService.this) { 26492 return mActivityStartController.startActivitiesInPackage( 26493 packageUid, packageName, 26494 intents, resolvedTypes, null /* resultTo */, 26495 SafeActivityOptions.fromBundle(bOptions), userId, 26496 false /* validateIncomingUser */); 26497 } 26498 } 26499 26500 @Override 26501 public int startActivityAsUser(IApplicationThread caller, String callerPacakge, 26502 Intent intent, Bundle options, int userId) { 26503 return ActivityManagerService.this.startActivityAsUser( 26504 caller, callerPacakge, intent, 26505 intent.resolveTypeIfNeeded(mContext.getContentResolver()), 26506 null, null, 0, Intent.FLAG_ACTIVITY_NEW_TASK, null, options, userId, 26507 false /*validateIncomingUser*/); 26508 } 26509 26510 @Override 26511 public int getUidProcessState(int uid) { 26512 return getUidState(uid); 26513 } 26514 26515 @Override 26516 public void notifyKeyguardFlagsChanged(@Nullable Runnable callback) { 26517 synchronized (ActivityManagerService.this) { 26518 26519 // We might change the visibilities here, so prepare an empty app transition which 26520 // might be overridden later if we actually change visibilities. 26521 final boolean wasTransitionSet = 26522 mWindowManager.getPendingAppTransition() != TRANSIT_NONE; 26523 if (!wasTransitionSet) { 26524 mWindowManager.prepareAppTransition(TRANSIT_NONE, 26525 false /* alwaysKeepCurrent */); 26526 } 26527 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0, !PRESERVE_WINDOWS); 26528 26529 // If there was a transition set already we don't want to interfere with it as we 26530 // might be starting it too early. 26531 if (!wasTransitionSet) { 26532 mWindowManager.executeAppTransition(); 26533 } 26534 } 26535 if (callback != null) { 26536 callback.run(); 26537 } 26538 } 26539 26540 @Override 26541 public boolean isSystemReady() { 26542 // no need to synchronize(this) just to read & return the value 26543 return mSystemReady; 26544 } 26545 26546 @Override 26547 public void notifyKeyguardTrustedChanged() { 26548 synchronized (ActivityManagerService.this) { 26549 if (mKeyguardController.isKeyguardShowing(DEFAULT_DISPLAY)) { 26550 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0, !PRESERVE_WINDOWS); 26551 } 26552 } 26553 } 26554 26555 /** 26556 * Sets if the given pid has an overlay UI or not. 26557 * 26558 * @param pid The pid we are setting overlay UI for. 26559 * @param hasOverlayUi True if the process has overlay UI. 26560 * @see android.view.WindowManager.LayoutParams#TYPE_APPLICATION_OVERLAY 26561 */ 26562 @Override 26563 public void setHasOverlayUi(int pid, boolean hasOverlayUi) { 26564 synchronized (ActivityManagerService.this) { 26565 final ProcessRecord pr; 26566 synchronized (mPidsSelfLocked) { 26567 pr = mPidsSelfLocked.get(pid); 26568 if (pr == null) { 26569 Slog.w(TAG, "setHasOverlayUi called on unknown pid: " + pid); 26570 return; 26571 } 26572 } 26573 if (pr.hasOverlayUi == hasOverlayUi) { 26574 return; 26575 } 26576 pr.hasOverlayUi = hasOverlayUi; 26577 //Slog.i(TAG, "Setting hasOverlayUi=" + pr.hasOverlayUi + " for pid=" + pid); 26578 updateOomAdjLocked(pr, true); 26579 } 26580 } 26581 26582 @Override 26583 public void setRunningRemoteAnimation(int pid, boolean runningRemoteAnimation) { 26584 ActivityManagerService.this.setRunningRemoteAnimation(pid, runningRemoteAnimation); 26585 } 26586 26587 /** 26588 * Called after the network policy rules are updated by 26589 * {@link com.android.server.net.NetworkPolicyManagerService} for a specific {@param uid} 26590 * and {@param procStateSeq}. 26591 */ 26592 @Override 26593 public void notifyNetworkPolicyRulesUpdated(int uid, long procStateSeq) { 26594 if (DEBUG_NETWORK) { 26595 Slog.d(TAG_NETWORK, "Got update from NPMS for uid: " 26596 + uid + " seq: " + procStateSeq); 26597 } 26598 UidRecord record; 26599 synchronized (ActivityManagerService.this) { 26600 record = mActiveUids.get(uid); 26601 if (record == null) { 26602 if (DEBUG_NETWORK) { 26603 Slog.d(TAG_NETWORK, "No active uidRecord for uid: " + uid 26604 + " procStateSeq: " + procStateSeq); 26605 } 26606 return; 26607 } 26608 } 26609 synchronized (record.networkStateLock) { 26610 if (record.lastNetworkUpdatedProcStateSeq >= procStateSeq) { 26611 if (DEBUG_NETWORK) { 26612 Slog.d(TAG_NETWORK, "procStateSeq: " + procStateSeq + " has already" 26613 + " been handled for uid: " + uid); 26614 } 26615 return; 26616 } 26617 record.lastNetworkUpdatedProcStateSeq = procStateSeq; 26618 if (record.curProcStateSeq > procStateSeq) { 26619 if (DEBUG_NETWORK) { 26620 Slog.d(TAG_NETWORK, "No need to handle older seq no., Uid: " + uid 26621 + ", curProcstateSeq: " + record.curProcStateSeq 26622 + ", procStateSeq: " + procStateSeq); 26623 } 26624 return; 26625 } 26626 if (record.waitingForNetwork) { 26627 if (DEBUG_NETWORK) { 26628 Slog.d(TAG_NETWORK, "Notifying all blocking threads for uid: " + uid 26629 + ", procStateSeq: " + procStateSeq); 26630 } 26631 record.networkStateLock.notifyAll(); 26632 } 26633 } 26634 } 26635 26636 @Override 26637 public void notifyActiveVoiceInteractionServiceChanged(ComponentName component) { 26638 synchronized (ActivityManagerService.this) { 26639 mActiveVoiceInteractionServiceComponent = component; 26640 } 26641 } 26642 26643 /** 26644 * Called after virtual display Id is updated by 26645 * {@link com.android.server.vr.Vr2dDisplay} with a specific 26646 * {@param vrVr2dDisplayId}. 26647 */ 26648 @Override 26649 public void setVr2dDisplayId(int vr2dDisplayId) { 26650 if (DEBUG_STACK) { 26651 Slog.d(TAG, "setVr2dDisplayId called for: " + 26652 vr2dDisplayId); 26653 } 26654 synchronized (ActivityManagerService.this) { 26655 mVr2dDisplayId = vr2dDisplayId; 26656 } 26657 } 26658 26659 @Override 26660 public void saveANRState(String reason) { 26661 synchronized (ActivityManagerService.this) { 26662 final StringWriter sw = new StringWriter(); 26663 final PrintWriter pw = new FastPrintWriter(sw, false, 1024); 26664 pw.println(" ANR time: " + DateFormat.getDateTimeInstance().format(new Date())); 26665 if (reason != null) { 26666 pw.println(" Reason: " + reason); 26667 } 26668 pw.println(); 26669 mActivityStartController.dump(pw, " ", null); 26670 pw.println(); 26671 pw.println("-------------------------------------------------------------------------------"); 26672 dumpActivitiesLocked(null /* fd */, pw, null /* args */, 0 /* opti */, 26673 true /* dumpAll */, false /* dumpClient */, null /* dumpPackage */, 26674 "" /* header */); 26675 pw.println(); 26676 pw.close(); 26677 26678 mLastANRState = sw.toString(); 26679 } 26680 } 26681 26682 @Override 26683 public void clearSavedANRState() { 26684 synchronized (ActivityManagerService.this) { 26685 mLastANRState = null; 26686 } 26687 } 26688 26689 @Override 26690 public void setFocusedActivity(IBinder token) { 26691 synchronized (ActivityManagerService.this) { 26692 final ActivityRecord r = ActivityRecord.forTokenLocked(token); 26693 if (r == null) { 26694 throw new IllegalArgumentException( 26695 "setFocusedActivity: No activity record matching token=" + token); 26696 } 26697 if (mStackSupervisor.moveFocusableActivityStackToFrontLocked( 26698 r, "setFocusedActivity")) { 26699 mStackSupervisor.resumeFocusedStackTopActivityLocked(); 26700 } 26701 } 26702 } 26703 26704 @Override 26705 public void setAllowAppSwitches(@NonNull String type, int uid, int userId) { 26706 synchronized (ActivityManagerService.this) { 26707 if (mUserController.isUserRunning(userId, ActivityManager.FLAG_OR_STOPPED)) { 26708 ArrayMap<String, Integer> types = mAllowAppSwitchUids.get(userId); 26709 if (types == null) { 26710 if (uid < 0) { 26711 return; 26712 } 26713 types = new ArrayMap<>(); 26714 mAllowAppSwitchUids.put(userId, types); 26715 } 26716 if (uid < 0) { 26717 types.remove(type); 26718 } else { 26719 types.put(type, uid); 26720 } 26721 } 26722 } 26723 } 26724 26725 @Override 26726 public boolean isRuntimeRestarted() { 26727 return mSystemServiceManager.isRuntimeRestarted(); 26728 } 26729 26730 @Override 26731 public boolean hasRunningActivity(int uid, @Nullable String packageName) { 26732 if (packageName == null) return false; 26733 26734 synchronized (ActivityManagerService.this) { 26735 for (int i = 0; i < mLruProcesses.size(); i++) { 26736 final ProcessRecord processRecord = mLruProcesses.get(i); 26737 if (processRecord.uid == uid) { 26738 for (int j = 0; j < processRecord.activities.size(); j++) { 26739 final ActivityRecord activityRecord = processRecord.activities.get(j); 26740 if (packageName.equals(activityRecord.packageName)) { 26741 return true; 26742 } 26743 } 26744 } 26745 } 26746 } 26747 return false; 26748 } 26749 26750 @Override 26751 public void registerScreenObserver(ScreenObserver observer) { 26752 mScreenObservers.add(observer); 26753 } 26754 26755 @Override 26756 public boolean canStartMoreUsers() { 26757 return mUserController.canStartMoreUsers(); 26758 } 26759 26760 @Override 26761 public void setSwitchingFromSystemUserMessage(String switchingFromSystemUserMessage) { 26762 mUserController.setSwitchingFromSystemUserMessage(switchingFromSystemUserMessage); 26763 } 26764 26765 @Override 26766 public void setSwitchingToSystemUserMessage(String switchingToSystemUserMessage) { 26767 mUserController.setSwitchingToSystemUserMessage(switchingToSystemUserMessage); 26768 } 26769 26770 @Override 26771 public int getMaxRunningUsers() { 26772 return mUserController.mMaxRunningUsers; 26773 } 26774 26775 @Override 26776 public boolean isCallerRecents(int callingUid) { 26777 return getRecentTasks().isCallerRecents(callingUid); 26778 } 26779 26780 @Override 26781 public boolean isRecentsComponentHomeActivity(int userId) { 26782 return getRecentTasks().isRecentsComponentHomeActivity(userId); 26783 } 26784 26785 @Override 26786 public void cancelRecentsAnimation(boolean restoreHomeStackPosition) { 26787 ActivityManagerService.this.cancelRecentsAnimation(restoreHomeStackPosition); 26788 } 26789 26790 @Override 26791 public boolean isUidActive(int uid) { 26792 synchronized (ActivityManagerService.this) { 26793 return isUidActiveLocked(uid); 26794 } 26795 } 26796 26797 @Override 26798 public List<ProcessMemoryState> getMemoryStateForProcesses() { 26799 List<ProcessMemoryState> processMemoryStates = new ArrayList<>(); 26800 synchronized (mPidsSelfLocked) { 26801 for (int i = 0, size = mPidsSelfLocked.size(); i < size; i++) { 26802 final ProcessRecord r = mPidsSelfLocked.valueAt(i); 26803 final int pid = r.pid; 26804 final int uid = r.uid; 26805 final MemoryStat memoryStat = readMemoryStatFromFilesystem(uid, pid); 26806 if (memoryStat == null) { 26807 continue; 26808 } 26809 ProcessMemoryState processMemoryState = 26810 new ProcessMemoryState(uid, 26811 r.processName, 26812 r.maxAdj, 26813 memoryStat.pgfault, 26814 memoryStat.pgmajfault, 26815 memoryStat.rssInBytes, 26816 memoryStat.cacheInBytes, 26817 memoryStat.swapInBytes); 26818 processMemoryStates.add(processMemoryState); 26819 } 26820 } 26821 return processMemoryStates; 26822 } 26823 26824 @Override 26825 public void enforceCallerIsRecentsOrHasPermission(String permission, String func) { 26826 ActivityManagerService.this.enforceCallerIsRecentsOrHasPermission(permission, func); 26827 } 26828 } 26829 26830 /** 26831 * Called by app main thread to wait for the network policy rules to get updated. 26832 * 26833 * @param procStateSeq The sequence number indicating the process state change that the main 26834 * thread is interested in. 26835 */ 26836 @Override 26837 public void waitForNetworkStateUpdate(long procStateSeq) { 26838 final int callingUid = Binder.getCallingUid(); 26839 if (DEBUG_NETWORK) { 26840 Slog.d(TAG_NETWORK, "Called from " + callingUid + " to wait for seq: " + procStateSeq); 26841 } 26842 UidRecord record; 26843 synchronized (this) { 26844 record = mActiveUids.get(callingUid); 26845 if (record == null) { 26846 return; 26847 } 26848 } 26849 synchronized (record.networkStateLock) { 26850 if (record.lastDispatchedProcStateSeq < procStateSeq) { 26851 if (DEBUG_NETWORK) { 26852 Slog.d(TAG_NETWORK, "Uid state change for seq no. " + procStateSeq + " is not " 26853 + "dispatched to NPMS yet, so don't wait. Uid: " + callingUid 26854 + " lastProcStateSeqDispatchedToObservers: " 26855 + record.lastDispatchedProcStateSeq); 26856 } 26857 return; 26858 } 26859 if (record.curProcStateSeq > procStateSeq) { 26860 if (DEBUG_NETWORK) { 26861 Slog.d(TAG_NETWORK, "Ignore the wait requests for older seq numbers. Uid: " 26862 + callingUid + ", curProcStateSeq: " + record.curProcStateSeq 26863 + ", procStateSeq: " + procStateSeq); 26864 } 26865 return; 26866 } 26867 if (record.lastNetworkUpdatedProcStateSeq >= procStateSeq) { 26868 if (DEBUG_NETWORK) { 26869 Slog.d(TAG_NETWORK, "Network rules have been already updated for seq no. " 26870 + procStateSeq + ", so no need to wait. Uid: " 26871 + callingUid + ", lastProcStateSeqWithUpdatedNetworkState: " 26872 + record.lastNetworkUpdatedProcStateSeq); 26873 } 26874 return; 26875 } 26876 try { 26877 if (DEBUG_NETWORK) { 26878 Slog.d(TAG_NETWORK, "Starting to wait for the network rules update." 26879 + " Uid: " + callingUid + " procStateSeq: " + procStateSeq); 26880 } 26881 final long startTime = SystemClock.uptimeMillis(); 26882 record.waitingForNetwork = true; 26883 record.networkStateLock.wait(mWaitForNetworkTimeoutMs); 26884 record.waitingForNetwork = false; 26885 final long totalTime = SystemClock.uptimeMillis() - startTime; 26886 if (totalTime >= mWaitForNetworkTimeoutMs || DEBUG_NETWORK) { 26887 Slog.w(TAG_NETWORK, "Total time waited for network rules to get updated: " 26888 + totalTime + ". Uid: " + callingUid + " procStateSeq: " 26889 + procStateSeq + " UidRec: " + record 26890 + " validateUidRec: " + mValidateUids.get(callingUid)); 26891 } 26892 } catch (InterruptedException e) { 26893 Thread.currentThread().interrupt(); 26894 } 26895 } 26896 } 26897 26898 public void waitForBroadcastIdle(PrintWriter pw) { 26899 enforceCallingPermission(permission.DUMP, "waitForBroadcastIdle()"); 26900 while (true) { 26901 boolean idle = true; 26902 synchronized (this) { 26903 for (BroadcastQueue queue : mBroadcastQueues) { 26904 if (!queue.isIdle()) { 26905 final String msg = "Waiting for queue " + queue + " to become idle..."; 26906 pw.println(msg); 26907 pw.flush(); 26908 Slog.v(TAG, msg); 26909 idle = false; 26910 } 26911 } 26912 } 26913 26914 if (idle) { 26915 final String msg = "All broadcast queues are idle!"; 26916 pw.println(msg); 26917 pw.flush(); 26918 Slog.v(TAG, msg); 26919 return; 26920 } else { 26921 SystemClock.sleep(1000); 26922 } 26923 } 26924 } 26925 26926 /** 26927 * Return the user id of the last resumed activity. 26928 */ 26929 @Override 26930 public @UserIdInt int getLastResumedActivityUserId() { 26931 enforceCallingPermission( 26932 permission.INTERACT_ACROSS_USERS_FULL, "getLastResumedActivityUserId()"); 26933 synchronized (this) { 26934 if (mLastResumedActivity == null) { 26935 return mUserController.getCurrentUserId(); 26936 } 26937 return mLastResumedActivity.userId; 26938 } 26939 } 26940 26941 /** 26942 * Kill processes for the user with id userId and that depend on the package named packageName 26943 */ 26944 @Override 26945 public void killPackageDependents(String packageName, int userId) { 26946 enforceCallingPermission(android.Manifest.permission.KILL_UID, "killPackageDependents()"); 26947 if (packageName == null) { 26948 throw new NullPointerException( 26949 "Cannot kill the dependents of a package without its name."); 26950 } 26951 26952 long callingId = Binder.clearCallingIdentity(); 26953 IPackageManager pm = AppGlobals.getPackageManager(); 26954 int pkgUid = -1; 26955 try { 26956 pkgUid = pm.getPackageUid(packageName, MATCH_DEBUG_TRIAGED_MISSING, userId); 26957 } catch (RemoteException e) { 26958 } 26959 if (userId != UserHandle.USER_ALL && pkgUid == -1) { 26960 throw new IllegalArgumentException( 26961 "Cannot kill dependents of non-existing package " + packageName); 26962 } 26963 try { 26964 synchronized(this) { 26965 killPackageProcessesLocked(packageName, UserHandle.getAppId(pkgUid), userId, 26966 ProcessList.FOREGROUND_APP_ADJ, false, true, true, false, 26967 "dep: " + packageName); 26968 } 26969 } finally { 26970 Binder.restoreCallingIdentity(callingId); 26971 } 26972 } 26973 26974 @Override 26975 public void dismissKeyguard(IBinder token, IKeyguardDismissCallback callback, 26976 CharSequence message) throws RemoteException { 26977 if (message != null) { 26978 enforceCallingPermission(permission.SHOW_KEYGUARD_MESSAGE, 26979 "dismissKeyguard()"); 26980 } 26981 final long callingId = Binder.clearCallingIdentity(); 26982 try { 26983 mKeyguardController.dismissKeyguard(token, callback, message); 26984 } finally { 26985 Binder.restoreCallingIdentity(callingId); 26986 } 26987 } 26988 26989 @Override 26990 public int restartUserInBackground(final int userId) { 26991 return mUserController.restartUser(userId, /* foreground */ false); 26992 } 26993 26994 @Override 26995 public void scheduleApplicationInfoChanged(List<String> packageNames, int userId) { 26996 enforceCallingPermission(android.Manifest.permission.CHANGE_CONFIGURATION, 26997 "scheduleApplicationInfoChanged()"); 26998 26999 synchronized (this) { 27000 final long origId = Binder.clearCallingIdentity(); 27001 try { 27002 updateApplicationInfoLocked(packageNames, userId); 27003 } finally { 27004 Binder.restoreCallingIdentity(origId); 27005 } 27006 } 27007 } 27008 27009 void updateApplicationInfoLocked(@NonNull List<String> packagesToUpdate, int userId) { 27010 final boolean updateFrameworkRes = packagesToUpdate.contains("android"); 27011 for (int i = mLruProcesses.size() - 1; i >= 0; i--) { 27012 final ProcessRecord app = mLruProcesses.get(i); 27013 if (app.thread == null) { 27014 continue; 27015 } 27016 27017 if (userId != UserHandle.USER_ALL && app.userId != userId) { 27018 continue; 27019 } 27020 27021 final int packageCount = app.pkgList.size(); 27022 for (int j = 0; j < packageCount; j++) { 27023 final String packageName = app.pkgList.keyAt(j); 27024 if (updateFrameworkRes || packagesToUpdate.contains(packageName)) { 27025 try { 27026 final ApplicationInfo ai = AppGlobals.getPackageManager() 27027 .getApplicationInfo(packageName, STOCK_PM_FLAGS, app.userId); 27028 if (ai != null) { 27029 app.thread.scheduleApplicationInfoChanged(ai); 27030 } 27031 } catch (RemoteException e) { 27032 Slog.w(TAG, String.format("Failed to update %s ApplicationInfo for %s", 27033 packageName, app)); 27034 } 27035 } 27036 } 27037 } 27038 if (updateFrameworkRes) { 27039 // Update system server components that need to know about changed overlays. Because the 27040 // overlay is applied in ActivityThread, we need to serialize through its thread too. 27041 final Executor executor = ActivityThread.currentActivityThread().getExecutor(); 27042 final DisplayManagerInternal display = 27043 LocalServices.getService(DisplayManagerInternal.class); 27044 if (display != null) { 27045 executor.execute(display::onOverlayChanged); 27046 } 27047 if (mWindowManager != null) { 27048 executor.execute(mWindowManager::onOverlayChanged); 27049 } 27050 } 27051 } 27052 27053 /** 27054 * Attach an agent to the specified process (proces name or PID) 27055 */ 27056 public void attachAgent(String process, String path) { 27057 try { 27058 synchronized (this) { 27059 ProcessRecord proc = findProcessLocked(process, UserHandle.USER_SYSTEM, "attachAgent"); 27060 if (proc == null || proc.thread == null) { 27061 throw new IllegalArgumentException("Unknown process: " + process); 27062 } 27063 27064 boolean isDebuggable = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 27065 if (!isDebuggable) { 27066 if ((proc.info.flags & ApplicationInfo.FLAG_DEBUGGABLE) == 0) { 27067 throw new SecurityException("Process not debuggable: " + proc); 27068 } 27069 } 27070 27071 proc.thread.attachAgent(path); 27072 } 27073 } catch (RemoteException e) { 27074 throw new IllegalStateException("Process disappeared"); 27075 } 27076 } 27077 27078 @VisibleForTesting 27079 public static class Injector { 27080 private NetworkManagementInternal mNmi; 27081 27082 public Context getContext() { 27083 return null; 27084 } 27085 27086 public AppOpsService getAppOpsService(File file, Handler handler) { 27087 return new AppOpsService(file, handler); 27088 } 27089 27090 public Handler getUiHandler(ActivityManagerService service) { 27091 return service.new UiHandler(); 27092 } 27093 27094 public boolean isNetworkRestrictedForUid(int uid) { 27095 if (ensureHasNetworkManagementInternal()) { 27096 return mNmi.isNetworkRestrictedForUid(uid); 27097 } 27098 return false; 27099 } 27100 27101 private boolean ensureHasNetworkManagementInternal() { 27102 if (mNmi == null) { 27103 mNmi = LocalServices.getService(NetworkManagementInternal.class); 27104 } 27105 return mNmi != null; 27106 } 27107 } 27108 27109 @Override 27110 public void setShowWhenLocked(IBinder token, boolean showWhenLocked) 27111 throws RemoteException { 27112 synchronized (this) { 27113 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 27114 if (r == null) { 27115 return; 27116 } 27117 final long origId = Binder.clearCallingIdentity(); 27118 try { 27119 r.setShowWhenLocked(showWhenLocked); 27120 } finally { 27121 Binder.restoreCallingIdentity(origId); 27122 } 27123 } 27124 } 27125 27126 @Override 27127 public void setTurnScreenOn(IBinder token, boolean turnScreenOn) throws RemoteException { 27128 synchronized (this) { 27129 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 27130 if (r == null) { 27131 return; 27132 } 27133 final long origId = Binder.clearCallingIdentity(); 27134 try { 27135 r.setTurnScreenOn(turnScreenOn); 27136 } finally { 27137 Binder.restoreCallingIdentity(origId); 27138 } 27139 } 27140 } 27141 27142 @Override 27143 public void registerRemoteAnimations(IBinder token, RemoteAnimationDefinition definition) 27144 throws RemoteException { 27145 enforceCallingPermission(CONTROL_REMOTE_APP_TRANSITION_ANIMATIONS, 27146 "registerRemoteAnimations"); 27147 definition.setCallingPid(Binder.getCallingPid()); 27148 synchronized (this) { 27149 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 27150 if (r == null) { 27151 return; 27152 } 27153 final long origId = Binder.clearCallingIdentity(); 27154 try { 27155 r.registerRemoteAnimations(definition); 27156 } finally { 27157 Binder.restoreCallingIdentity(origId); 27158 } 27159 } 27160 } 27161 27162 @Override 27163 public void registerRemoteAnimationForNextActivityStart(String packageName, 27164 RemoteAnimationAdapter adapter) throws RemoteException { 27165 enforceCallingPermission(CONTROL_REMOTE_APP_TRANSITION_ANIMATIONS, 27166 "registerRemoteAnimationForNextActivityStart"); 27167 adapter.setCallingPid(Binder.getCallingPid()); 27168 synchronized (this) { 27169 final long origId = Binder.clearCallingIdentity(); 27170 try { 27171 mActivityStartController.registerRemoteAnimationForNextActivityStart(packageName, 27172 adapter); 27173 } finally { 27174 Binder.restoreCallingIdentity(origId); 27175 } 27176 } 27177 } 27178 27179 /** @see android.app.ActivityManager#alwaysShowUnsupportedCompileSdkWarning */ 27180 @Override 27181 public void alwaysShowUnsupportedCompileSdkWarning(ComponentName activity) { 27182 synchronized (this) { 27183 final long origId = Binder.clearCallingIdentity(); 27184 try { 27185 mAppWarnings.alwaysShowUnsupportedCompileSdkWarning(activity); 27186 } finally { 27187 Binder.restoreCallingIdentity(origId); 27188 } 27189 } 27190 } 27191 } 27192