1 /* 2 * Copyright (C) 2016 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.wm; 18 19 import static android.Manifest.permission.START_ACTIVITIES_FROM_BACKGROUND; 20 import static android.app.Activity.RESULT_CANCELED; 21 import static android.app.ActivityManager.START_ABORTED; 22 import static android.app.ActivityManager.START_CANCELED; 23 import static android.app.ActivityManager.START_CLASS_NOT_FOUND; 24 import static android.app.ActivityManager.START_DELIVERED_TO_TOP; 25 import static android.app.ActivityManager.START_FLAG_ONLY_IF_NEEDED; 26 import static android.app.ActivityManager.START_RETURN_INTENT_TO_CALLER; 27 import static android.app.ActivityManager.START_RETURN_LOCK_TASK_MODE_VIOLATION; 28 import static android.app.ActivityManager.START_SUCCESS; 29 import static android.app.ActivityManager.START_TASK_TO_FRONT; 30 import static android.app.ActivityTaskManager.INVALID_TASK_ID; 31 import static android.app.WindowConfiguration.WINDOWING_MODE_SPLIT_SCREEN_PRIMARY; 32 import static android.app.WindowConfiguration.WINDOWING_MODE_SPLIT_SCREEN_SECONDARY; 33 import static android.app.WindowConfiguration.WINDOWING_MODE_UNDEFINED; 34 import static android.content.Intent.FLAG_ACTIVITY_CLEAR_TASK; 35 import static android.content.Intent.FLAG_ACTIVITY_CLEAR_TOP; 36 import static android.content.Intent.FLAG_ACTIVITY_LAUNCH_ADJACENT; 37 import static android.content.Intent.FLAG_ACTIVITY_MULTIPLE_TASK; 38 import static android.content.Intent.FLAG_ACTIVITY_NEW_DOCUMENT; 39 import static android.content.Intent.FLAG_ACTIVITY_NEW_TASK; 40 import static android.content.Intent.FLAG_ACTIVITY_NO_ANIMATION; 41 import static android.content.Intent.FLAG_ACTIVITY_NO_USER_ACTION; 42 import static android.content.Intent.FLAG_ACTIVITY_PREVIOUS_IS_TOP; 43 import static android.content.Intent.FLAG_ACTIVITY_REORDER_TO_FRONT; 44 import static android.content.Intent.FLAG_ACTIVITY_RESET_TASK_IF_NEEDED; 45 import static android.content.Intent.FLAG_ACTIVITY_RETAIN_IN_RECENTS; 46 import static android.content.Intent.FLAG_ACTIVITY_SINGLE_TOP; 47 import static android.content.Intent.FLAG_ACTIVITY_TASK_ON_HOME; 48 import static android.content.pm.ActivityInfo.DOCUMENT_LAUNCH_ALWAYS; 49 import static android.content.pm.ActivityInfo.FLAG_SHOW_FOR_ALL_USERS; 50 import static android.content.pm.ActivityInfo.LAUNCH_SINGLE_INSTANCE; 51 import static android.content.pm.ActivityInfo.LAUNCH_SINGLE_INSTANCE_PER_TASK; 52 import static android.content.pm.ActivityInfo.LAUNCH_SINGLE_TASK; 53 import static android.content.pm.ActivityInfo.LAUNCH_SINGLE_TOP; 54 import static android.content.pm.PackageManager.PERMISSION_GRANTED; 55 import static android.os.Process.INVALID_UID; 56 import static android.view.Display.DEFAULT_DISPLAY; 57 import static android.view.WindowManager.TRANSIT_OPEN; 58 59 import static com.android.internal.protolog.ProtoLogGroup.WM_DEBUG_CONFIGURATION; 60 import static com.android.internal.protolog.ProtoLogGroup.WM_DEBUG_TASKS; 61 import static com.android.server.wm.ActivityTaskManagerDebugConfig.DEBUG_ACTIVITY_STARTS; 62 import static com.android.server.wm.ActivityTaskManagerDebugConfig.DEBUG_PERMISSIONS_REVIEW; 63 import static com.android.server.wm.ActivityTaskManagerDebugConfig.DEBUG_RESULTS; 64 import static com.android.server.wm.ActivityTaskManagerDebugConfig.DEBUG_USER_LEAVING; 65 import static com.android.server.wm.ActivityTaskManagerDebugConfig.POSTFIX_CONFIGURATION; 66 import static com.android.server.wm.ActivityTaskManagerDebugConfig.POSTFIX_FOCUS; 67 import static com.android.server.wm.ActivityTaskManagerDebugConfig.POSTFIX_RESULTS; 68 import static com.android.server.wm.ActivityTaskManagerDebugConfig.POSTFIX_USER_LEAVING; 69 import static com.android.server.wm.ActivityTaskManagerDebugConfig.TAG_ATM; 70 import static com.android.server.wm.ActivityTaskManagerDebugConfig.TAG_WITH_CLASS_NAME; 71 import static com.android.server.wm.ActivityTaskManagerService.ANIMATE; 72 import static com.android.server.wm.ActivityTaskSupervisor.DEFER_RESUME; 73 import static com.android.server.wm.ActivityTaskSupervisor.ON_TOP; 74 import static com.android.server.wm.ActivityTaskSupervisor.PRESERVE_WINDOWS; 75 import static com.android.server.wm.LaunchParamsController.LaunchParamsModifier.PHASE_BOUNDS; 76 import static com.android.server.wm.LaunchParamsController.LaunchParamsModifier.PHASE_DISPLAY; 77 import static com.android.server.wm.Task.ActivityState.RESUMED; 78 import static com.android.server.wm.Task.REPARENT_MOVE_ROOT_TASK_TO_FRONT; 79 import static com.android.server.wm.WindowContainer.POSITION_TOP; 80 81 import android.annotation.NonNull; 82 import android.annotation.Nullable; 83 import android.app.ActivityManager; 84 import android.app.ActivityOptions; 85 import android.app.IApplicationThread; 86 import android.app.PendingIntent; 87 import android.app.ProfilerInfo; 88 import android.app.WaitResult; 89 import android.content.ComponentName; 90 import android.content.IIntentSender; 91 import android.content.Intent; 92 import android.content.IntentSender; 93 import android.content.pm.ActivityInfo; 94 import android.content.pm.ApplicationInfo; 95 import android.content.pm.AuxiliaryResolveInfo; 96 import android.content.pm.PackageManager; 97 import android.content.pm.PackageManagerInternal; 98 import android.content.pm.ResolveInfo; 99 import android.content.pm.UserInfo; 100 import android.content.res.Configuration; 101 import android.os.Binder; 102 import android.os.Bundle; 103 import android.os.IBinder; 104 import android.os.Process; 105 import android.os.RemoteException; 106 import android.os.Trace; 107 import android.os.UserHandle; 108 import android.os.UserManager; 109 import android.service.voice.IVoiceInteractionSession; 110 import android.text.TextUtils; 111 import android.util.ArraySet; 112 import android.util.DebugUtils; 113 import android.util.Pools.SynchronizedPool; 114 import android.util.Slog; 115 import android.window.IRemoteTransition; 116 117 import com.android.internal.annotations.VisibleForTesting; 118 import com.android.internal.app.HeavyWeightSwitcherActivity; 119 import com.android.internal.app.IVoiceInteractor; 120 import com.android.internal.protolog.common.ProtoLog; 121 import com.android.server.am.PendingIntentRecord; 122 import com.android.server.pm.InstantAppResolver; 123 import com.android.server.power.ShutdownCheckPoints; 124 import com.android.server.statusbar.StatusBarManagerInternal; 125 import com.android.server.uri.NeededUriGrants; 126 import com.android.server.wm.ActivityMetricsLogger.LaunchingState; 127 import com.android.server.wm.LaunchParamsController.LaunchParams; 128 129 import java.io.PrintWriter; 130 import java.text.DateFormat; 131 import java.util.Date; 132 133 /** 134 * Controller for interpreting how and then launching an activity. 135 * 136 * This class collects all the logic for determining how an intent and flags should be turned into 137 * an activity and associated task and root task. 138 */ 139 class ActivityStarter { 140 private static final String TAG = TAG_WITH_CLASS_NAME ? "ActivityStarter" : TAG_ATM; 141 private static final String TAG_RESULTS = TAG + POSTFIX_RESULTS; 142 private static final String TAG_FOCUS = TAG + POSTFIX_FOCUS; 143 private static final String TAG_CONFIGURATION = TAG + POSTFIX_CONFIGURATION; 144 private static final String TAG_USER_LEAVING = TAG + POSTFIX_USER_LEAVING; 145 private static final int INVALID_LAUNCH_MODE = -1; 146 147 private final ActivityTaskManagerService mService; 148 private final RootWindowContainer mRootWindowContainer; 149 private final ActivityTaskSupervisor mSupervisor; 150 private final ActivityStartInterceptor mInterceptor; 151 private final ActivityStartController mController; 152 153 // Share state variable among methods when starting an activity. 154 @VisibleForTesting 155 ActivityRecord mStartActivity; 156 private Intent mIntent; 157 private int mCallingUid; 158 private ActivityOptions mOptions; 159 160 // If it is true, background activity can only be started in an existing task that contains 161 // an activity with same uid, or if activity starts are enabled in developer options. 162 private boolean mRestrictedBgActivity; 163 164 private int mLaunchMode; 165 private boolean mLaunchTaskBehind; 166 private int mLaunchFlags; 167 168 private LaunchParams mLaunchParams = new LaunchParams(); 169 170 private ActivityRecord mNotTop; 171 private boolean mDoResume; 172 private int mStartFlags; 173 private ActivityRecord mSourceRecord; 174 175 // The task display area to launch the activity onto, barring any strong reason to do otherwise. 176 private TaskDisplayArea mPreferredTaskDisplayArea; 177 private int mPreferredWindowingMode; 178 179 private Task mInTask; 180 @VisibleForTesting 181 boolean mAddingToTask; 182 private Task mReuseTask; 183 184 private ActivityInfo mNewTaskInfo; 185 private Intent mNewTaskIntent; 186 private Task mSourceRootTask; 187 private Task mTargetRootTask; 188 // The task that the last activity was started into. We currently reset the actual start 189 // activity's task and as a result may not have a reference to the task in all cases 190 private Task mTargetTask; 191 private boolean mMovedToFront; 192 private boolean mNoAnimation; 193 private boolean mKeepCurTransition; 194 private boolean mAvoidMoveToFront; 195 private boolean mFrozeTaskList; 196 private boolean mTransientLaunch; 197 198 // We must track when we deliver the new intent since multiple code paths invoke 199 // {@link #deliverNewIntent}. This is due to early returns in the code path. This flag is used 200 // inside {@link #deliverNewIntent} to suppress duplicate requests and ensure the intent is 201 // delivered at most once. 202 private boolean mIntentDelivered; 203 204 private IVoiceInteractionSession mVoiceSession; 205 private IVoiceInteractor mVoiceInteractor; 206 207 // Last activity record we attempted to start 208 private ActivityRecord mLastStartActivityRecord; 209 // The result of the last activity we attempted to start. 210 private int mLastStartActivityResult; 211 // Time in milli seconds we attempted to start the last activity. 212 private long mLastStartActivityTimeMs; 213 // The reason we were trying to start the last activity 214 private String mLastStartReason; 215 216 /* 217 * Request details provided through setter methods. Should be reset after {@link #execute()} 218 * to avoid unnecessarily retaining parameters. Note that the request is ignored when 219 * {@link #startResolvedActivity} is invoked directly. 220 */ 221 @VisibleForTesting 222 Request mRequest = new Request(); 223 224 /** 225 * An interface that to provide {@link ActivityStarter} instances to the controller. This is 226 * used by tests to inject their own starter implementations for verification purposes. 227 */ 228 @VisibleForTesting 229 interface Factory { 230 /** 231 * Sets the {@link ActivityStartController} to be passed to {@link ActivityStarter}. 232 */ setController(ActivityStartController controller)233 void setController(ActivityStartController controller); 234 235 /** 236 * Generates an {@link ActivityStarter} that is ready to handle a new start request. 237 * @param controller The {@link ActivityStartController} which the starter who will own 238 * this instance. 239 * @return an {@link ActivityStarter} 240 */ obtain()241 ActivityStarter obtain(); 242 243 /** 244 * Recycles a starter for reuse. 245 */ recycle(ActivityStarter starter)246 void recycle(ActivityStarter starter); 247 } 248 249 /** 250 * Default implementation of {@link StarterFactory}. 251 */ 252 static class DefaultFactory implements Factory { 253 /** 254 * The maximum count of starters that should be active at one time: 255 * 1. last ran starter (for logging and post activity processing) 256 * 2. current running starter 257 * 3. starter from re-entry in (2) 258 */ 259 private final int MAX_STARTER_COUNT = 3; 260 261 private ActivityStartController mController; 262 private ActivityTaskManagerService mService; 263 private ActivityTaskSupervisor mSupervisor; 264 private ActivityStartInterceptor mInterceptor; 265 266 private SynchronizedPool<ActivityStarter> mStarterPool = 267 new SynchronizedPool<>(MAX_STARTER_COUNT); 268 DefaultFactory(ActivityTaskManagerService service, ActivityTaskSupervisor supervisor, ActivityStartInterceptor interceptor)269 DefaultFactory(ActivityTaskManagerService service, 270 ActivityTaskSupervisor supervisor, ActivityStartInterceptor interceptor) { 271 mService = service; 272 mSupervisor = supervisor; 273 mInterceptor = interceptor; 274 } 275 276 @Override setController(ActivityStartController controller)277 public void setController(ActivityStartController controller) { 278 mController = controller; 279 } 280 281 @Override obtain()282 public ActivityStarter obtain() { 283 ActivityStarter starter = mStarterPool.acquire(); 284 285 if (starter == null) { 286 if (mService.mRootWindowContainer == null) { 287 throw new IllegalStateException("Too early to start activity."); 288 } 289 starter = new ActivityStarter(mController, mService, mSupervisor, mInterceptor); 290 } 291 292 return starter; 293 } 294 295 @Override recycle(ActivityStarter starter)296 public void recycle(ActivityStarter starter) { 297 starter.reset(true /* clearRequest*/); 298 mStarterPool.release(starter); 299 } 300 } 301 302 /** 303 * Container for capturing initial start request details. This information is NOT reset until 304 * the {@link ActivityStarter} is recycled, allowing for multiple invocations with the same 305 * parameters. 306 * 307 * TODO(b/64750076): Investigate consolidating member variables of {@link ActivityStarter} with 308 * the request object. Note that some member variables are referenced in 309 * {@link #dump(PrintWriter, String)} and therefore cannot be cleared immediately after 310 * execution. 311 */ 312 @VisibleForTesting 313 static class Request { 314 private static final int DEFAULT_CALLING_UID = -1; 315 private static final int DEFAULT_CALLING_PID = 0; 316 static final int DEFAULT_REAL_CALLING_UID = -1; 317 static final int DEFAULT_REAL_CALLING_PID = 0; 318 319 IApplicationThread caller; 320 Intent intent; 321 NeededUriGrants intentGrants; 322 // A copy of the original requested intent, in case for ephemeral app launch. 323 Intent ephemeralIntent; 324 String resolvedType; 325 ActivityInfo activityInfo; 326 ResolveInfo resolveInfo; 327 IVoiceInteractionSession voiceSession; 328 IVoiceInteractor voiceInteractor; 329 IBinder resultTo; 330 String resultWho; 331 int requestCode; 332 int callingPid = DEFAULT_CALLING_PID; 333 int callingUid = DEFAULT_CALLING_UID; 334 String callingPackage; 335 @Nullable String callingFeatureId; 336 int realCallingPid = DEFAULT_REAL_CALLING_PID; 337 int realCallingUid = DEFAULT_REAL_CALLING_UID; 338 int startFlags; 339 SafeActivityOptions activityOptions; 340 boolean ignoreTargetSecurity; 341 boolean componentSpecified; 342 boolean avoidMoveToFront; 343 ActivityRecord[] outActivity; 344 Task inTask; 345 String reason; 346 ProfilerInfo profilerInfo; 347 Configuration globalConfig; 348 int userId; 349 WaitResult waitResult; 350 int filterCallingUid; 351 PendingIntentRecord originatingPendingIntent; 352 boolean allowBackgroundActivityStart; 353 354 /** 355 * If set to {@code true}, allows this activity start to look into 356 * {@link PendingRemoteAnimationRegistry} 357 */ 358 boolean allowPendingRemoteAnimationRegistryLookup; 359 360 /** 361 * Ensure constructed request matches reset instance. 362 */ Request()363 Request() { 364 reset(); 365 } 366 367 /** 368 * Sets values back to the initial state, clearing any held references. 369 */ reset()370 void reset() { 371 caller = null; 372 intent = null; 373 intentGrants = null; 374 ephemeralIntent = null; 375 resolvedType = null; 376 activityInfo = null; 377 resolveInfo = null; 378 voiceSession = null; 379 voiceInteractor = null; 380 resultTo = null; 381 resultWho = null; 382 requestCode = 0; 383 callingPid = DEFAULT_CALLING_PID; 384 callingUid = DEFAULT_CALLING_UID; 385 callingPackage = null; 386 callingFeatureId = null; 387 realCallingPid = DEFAULT_REAL_CALLING_PID; 388 realCallingUid = DEFAULT_REAL_CALLING_UID; 389 startFlags = 0; 390 activityOptions = null; 391 ignoreTargetSecurity = false; 392 componentSpecified = false; 393 outActivity = null; 394 inTask = null; 395 reason = null; 396 profilerInfo = null; 397 globalConfig = null; 398 userId = 0; 399 waitResult = null; 400 avoidMoveToFront = false; 401 allowPendingRemoteAnimationRegistryLookup = true; 402 filterCallingUid = UserHandle.USER_NULL; 403 originatingPendingIntent = null; 404 allowBackgroundActivityStart = false; 405 } 406 407 /** 408 * Adopts all values from passed in request. 409 */ set(Request request)410 void set(Request request) { 411 caller = request.caller; 412 intent = request.intent; 413 intentGrants = request.intentGrants; 414 ephemeralIntent = request.ephemeralIntent; 415 resolvedType = request.resolvedType; 416 activityInfo = request.activityInfo; 417 resolveInfo = request.resolveInfo; 418 voiceSession = request.voiceSession; 419 voiceInteractor = request.voiceInteractor; 420 resultTo = request.resultTo; 421 resultWho = request.resultWho; 422 requestCode = request.requestCode; 423 callingPid = request.callingPid; 424 callingUid = request.callingUid; 425 callingPackage = request.callingPackage; 426 callingFeatureId = request.callingFeatureId; 427 realCallingPid = request.realCallingPid; 428 realCallingUid = request.realCallingUid; 429 startFlags = request.startFlags; 430 activityOptions = request.activityOptions; 431 ignoreTargetSecurity = request.ignoreTargetSecurity; 432 componentSpecified = request.componentSpecified; 433 outActivity = request.outActivity; 434 inTask = request.inTask; 435 reason = request.reason; 436 profilerInfo = request.profilerInfo; 437 globalConfig = request.globalConfig; 438 userId = request.userId; 439 waitResult = request.waitResult; 440 avoidMoveToFront = request.avoidMoveToFront; 441 allowPendingRemoteAnimationRegistryLookup 442 = request.allowPendingRemoteAnimationRegistryLookup; 443 filterCallingUid = request.filterCallingUid; 444 originatingPendingIntent = request.originatingPendingIntent; 445 allowBackgroundActivityStart = request.allowBackgroundActivityStart; 446 } 447 448 /** 449 * Resolve activity from the given intent for this launch. 450 */ resolveActivity(ActivityTaskSupervisor supervisor)451 void resolveActivity(ActivityTaskSupervisor supervisor) { 452 if (realCallingPid == Request.DEFAULT_REAL_CALLING_PID) { 453 realCallingPid = Binder.getCallingPid(); 454 } 455 if (realCallingUid == Request.DEFAULT_REAL_CALLING_UID) { 456 realCallingUid = Binder.getCallingUid(); 457 } 458 459 if (callingUid >= 0) { 460 callingPid = -1; 461 } else if (caller == null) { 462 callingPid = realCallingPid; 463 callingUid = realCallingUid; 464 } else { 465 callingPid = callingUid = -1; 466 } 467 468 // To determine the set of needed Uri permission grants, we need the 469 // "resolved" calling UID, where we try our best to identify the 470 // actual caller that is starting this activity 471 int resolvedCallingUid = callingUid; 472 if (caller != null) { 473 synchronized (supervisor.mService.mGlobalLock) { 474 final WindowProcessController callerApp = supervisor.mService 475 .getProcessController(caller); 476 if (callerApp != null) { 477 resolvedCallingUid = callerApp.mInfo.uid; 478 } 479 } 480 } 481 482 // Save a copy in case ephemeral needs it 483 ephemeralIntent = new Intent(intent); 484 // Don't modify the client's object! 485 intent = new Intent(intent); 486 if (intent.getComponent() != null 487 && !(Intent.ACTION_VIEW.equals(intent.getAction()) && intent.getData() == null) 488 && !Intent.ACTION_INSTALL_INSTANT_APP_PACKAGE.equals(intent.getAction()) 489 && !Intent.ACTION_RESOLVE_INSTANT_APP_PACKAGE.equals(intent.getAction()) 490 && supervisor.mService.getPackageManagerInternalLocked() 491 .isInstantAppInstallerComponent(intent.getComponent())) { 492 // Intercept intents targeted directly to the ephemeral installer the ephemeral 493 // installer should never be started with a raw Intent; instead adjust the intent 494 // so it looks like a "normal" instant app launch. 495 intent.setComponent(null /* component */); 496 } 497 498 resolveInfo = supervisor.resolveIntent(intent, resolvedType, userId, 499 0 /* matchFlags */, 500 computeResolveFilterUid(callingUid, realCallingUid, filterCallingUid)); 501 if (resolveInfo == null) { 502 final UserInfo userInfo = supervisor.getUserInfo(userId); 503 if (userInfo != null && userInfo.isManagedProfile()) { 504 // Special case for managed profiles, if attempting to launch non-cryto aware 505 // app in a locked managed profile from an unlocked parent allow it to resolve 506 // as user will be sent via confirm credentials to unlock the profile. 507 final UserManager userManager = UserManager.get(supervisor.mService.mContext); 508 boolean profileLockedAndParentUnlockingOrUnlocked = false; 509 final long token = Binder.clearCallingIdentity(); 510 try { 511 final UserInfo parent = userManager.getProfileParent(userId); 512 profileLockedAndParentUnlockingOrUnlocked = (parent != null) 513 && userManager.isUserUnlockingOrUnlocked(parent.id) 514 && !userManager.isUserUnlockingOrUnlocked(userId); 515 } finally { 516 Binder.restoreCallingIdentity(token); 517 } 518 if (profileLockedAndParentUnlockingOrUnlocked) { 519 resolveInfo = supervisor.resolveIntent(intent, resolvedType, userId, 520 PackageManager.MATCH_DIRECT_BOOT_AWARE 521 | PackageManager.MATCH_DIRECT_BOOT_UNAWARE, 522 computeResolveFilterUid(callingUid, realCallingUid, 523 filterCallingUid)); 524 } 525 } 526 } 527 528 // Collect information about the target of the Intent. 529 activityInfo = supervisor.resolveActivity(intent, resolveInfo, startFlags, 530 profilerInfo); 531 532 // Carefully collect grants without holding lock 533 if (activityInfo != null) { 534 intentGrants = supervisor.mService.mUgmInternal.checkGrantUriPermissionFromIntent( 535 intent, resolvedCallingUid, activityInfo.applicationInfo.packageName, 536 UserHandle.getUserId(activityInfo.applicationInfo.uid)); 537 } 538 } 539 } 540 ActivityStarter(ActivityStartController controller, ActivityTaskManagerService service, ActivityTaskSupervisor supervisor, ActivityStartInterceptor interceptor)541 ActivityStarter(ActivityStartController controller, ActivityTaskManagerService service, 542 ActivityTaskSupervisor supervisor, ActivityStartInterceptor interceptor) { 543 mController = controller; 544 mService = service; 545 mRootWindowContainer = service.mRootWindowContainer; 546 mSupervisor = supervisor; 547 mInterceptor = interceptor; 548 reset(true); 549 } 550 551 /** 552 * Effectively duplicates the starter passed in. All state and request values will be 553 * mirrored. 554 * @param starter 555 */ set(ActivityStarter starter)556 void set(ActivityStarter starter) { 557 mStartActivity = starter.mStartActivity; 558 mIntent = starter.mIntent; 559 mCallingUid = starter.mCallingUid; 560 mOptions = starter.mOptions; 561 mRestrictedBgActivity = starter.mRestrictedBgActivity; 562 563 mLaunchTaskBehind = starter.mLaunchTaskBehind; 564 mLaunchFlags = starter.mLaunchFlags; 565 mLaunchMode = starter.mLaunchMode; 566 567 mLaunchParams.set(starter.mLaunchParams); 568 569 mNotTop = starter.mNotTop; 570 mDoResume = starter.mDoResume; 571 mStartFlags = starter.mStartFlags; 572 mSourceRecord = starter.mSourceRecord; 573 mPreferredTaskDisplayArea = starter.mPreferredTaskDisplayArea; 574 mPreferredWindowingMode = starter.mPreferredWindowingMode; 575 576 mInTask = starter.mInTask; 577 mAddingToTask = starter.mAddingToTask; 578 mReuseTask = starter.mReuseTask; 579 580 mNewTaskInfo = starter.mNewTaskInfo; 581 mNewTaskIntent = starter.mNewTaskIntent; 582 mSourceRootTask = starter.mSourceRootTask; 583 584 mTargetTask = starter.mTargetTask; 585 mTargetRootTask = starter.mTargetRootTask; 586 mMovedToFront = starter.mMovedToFront; 587 mNoAnimation = starter.mNoAnimation; 588 mKeepCurTransition = starter.mKeepCurTransition; 589 mAvoidMoveToFront = starter.mAvoidMoveToFront; 590 mFrozeTaskList = starter.mFrozeTaskList; 591 592 mVoiceSession = starter.mVoiceSession; 593 mVoiceInteractor = starter.mVoiceInteractor; 594 595 mIntentDelivered = starter.mIntentDelivered; 596 597 mRequest.set(starter.mRequest); 598 } 599 relatedToPackage(String packageName)600 boolean relatedToPackage(String packageName) { 601 return (mLastStartActivityRecord != null 602 && packageName.equals(mLastStartActivityRecord.packageName)) 603 || (mStartActivity != null && packageName.equals(mStartActivity.packageName)); 604 } 605 606 /** 607 * Resolve necessary information according the request parameters provided earlier, and execute 608 * the request which begin the journey of starting an activity. 609 * @return The starter result. 610 */ execute()611 int execute() { 612 try { 613 // Refuse possible leaked file descriptors 614 if (mRequest.intent != null && mRequest.intent.hasFileDescriptors()) { 615 throw new IllegalArgumentException("File descriptors passed in Intent"); 616 } 617 618 final LaunchingState launchingState; 619 synchronized (mService.mGlobalLock) { 620 final ActivityRecord caller = ActivityRecord.forTokenLocked(mRequest.resultTo); 621 final int callingUid = mRequest.realCallingUid == Request.DEFAULT_REAL_CALLING_UID 622 ? Binder.getCallingUid() : mRequest.realCallingUid; 623 launchingState = mSupervisor.getActivityMetricsLogger().notifyActivityLaunching( 624 mRequest.intent, caller, callingUid); 625 } 626 627 // If the caller hasn't already resolved the activity, we're willing 628 // to do so here. If the caller is already holding the WM lock here, 629 // and we need to check dynamic Uri permissions, then we're forced 630 // to assume those permissions are denied to avoid deadlocking. 631 if (mRequest.activityInfo == null) { 632 mRequest.resolveActivity(mSupervisor); 633 } 634 635 // Add checkpoint for this shutdown or reboot attempt, so we can record the original 636 // intent action and package name. 637 if (mRequest.intent != null) { 638 String intentAction = mRequest.intent.getAction(); 639 String callingPackage = mRequest.callingPackage; 640 if (intentAction != null && callingPackage != null 641 && (Intent.ACTION_REQUEST_SHUTDOWN.equals(intentAction) 642 || Intent.ACTION_SHUTDOWN.equals(intentAction) 643 || Intent.ACTION_REBOOT.equals(intentAction))) { 644 ShutdownCheckPoints.recordCheckPoint(intentAction, callingPackage, null); 645 } 646 } 647 648 int res; 649 synchronized (mService.mGlobalLock) { 650 final boolean globalConfigWillChange = mRequest.globalConfig != null 651 && mService.getGlobalConfiguration().diff(mRequest.globalConfig) != 0; 652 final Task rootTask = mRootWindowContainer.getTopDisplayFocusedRootTask(); 653 if (rootTask != null) { 654 rootTask.mConfigWillChange = globalConfigWillChange; 655 } 656 ProtoLog.v(WM_DEBUG_CONFIGURATION, "Starting activity when config " 657 + "will change = %b", globalConfigWillChange); 658 659 final long origId = Binder.clearCallingIdentity(); 660 661 res = resolveToHeavyWeightSwitcherIfNeeded(); 662 if (res != START_SUCCESS) { 663 return res; 664 } 665 res = executeRequest(mRequest); 666 667 Binder.restoreCallingIdentity(origId); 668 669 if (globalConfigWillChange) { 670 // If the caller also wants to switch to a new configuration, do so now. 671 // This allows a clean switch, as we are waiting for the current activity 672 // to pause (so we will not destroy it), and have not yet started the 673 // next activity. 674 mService.mAmInternal.enforceCallingPermission( 675 android.Manifest.permission.CHANGE_CONFIGURATION, 676 "updateConfiguration()"); 677 if (rootTask != null) { 678 rootTask.mConfigWillChange = false; 679 } 680 ProtoLog.v(WM_DEBUG_CONFIGURATION, 681 "Updating to new configuration after starting activity."); 682 683 mService.updateConfigurationLocked(mRequest.globalConfig, null, false); 684 } 685 686 // The original options may have additional info about metrics. The mOptions is not 687 // used here because it may be cleared in setTargetRootTaskIfNeeded. 688 final ActivityOptions originalOptions = mRequest.activityOptions != null 689 ? mRequest.activityOptions.getOriginalOptions() : null; 690 // If the new record is the one that started, a new activity has created. 691 final boolean newActivityCreated = mStartActivity == mLastStartActivityRecord; 692 // Notify ActivityMetricsLogger that the activity has launched. 693 // ActivityMetricsLogger will then wait for the windows to be drawn and populate 694 // WaitResult. 695 mSupervisor.getActivityMetricsLogger().notifyActivityLaunched(launchingState, res, 696 newActivityCreated, mLastStartActivityRecord, originalOptions); 697 if (mRequest.waitResult != null) { 698 mRequest.waitResult.result = res; 699 res = waitResultIfNeeded(mRequest.waitResult, mLastStartActivityRecord, 700 launchingState); 701 } 702 return getExternalResult(res); 703 } 704 } finally { 705 onExecutionComplete(); 706 } 707 } 708 709 /** 710 * Updates the request to heavy-weight switch if this is a heavy-weight process while there 711 * already have another, different heavy-weight process running. 712 */ resolveToHeavyWeightSwitcherIfNeeded()713 private int resolveToHeavyWeightSwitcherIfNeeded() { 714 if (mRequest.activityInfo == null || !mService.mHasHeavyWeightFeature 715 || (mRequest.activityInfo.applicationInfo.privateFlags 716 & ApplicationInfo.PRIVATE_FLAG_CANT_SAVE_STATE) == 0) { 717 return START_SUCCESS; 718 } 719 720 if (!mRequest.activityInfo.processName.equals( 721 mRequest.activityInfo.applicationInfo.packageName)) { 722 return START_SUCCESS; 723 } 724 725 final WindowProcessController heavy = mService.mHeavyWeightProcess; 726 if (heavy == null || (heavy.mInfo.uid == mRequest.activityInfo.applicationInfo.uid 727 && heavy.mName.equals(mRequest.activityInfo.processName))) { 728 return START_SUCCESS; 729 } 730 731 int appCallingUid = mRequest.callingUid; 732 if (mRequest.caller != null) { 733 WindowProcessController callerApp = mService.getProcessController(mRequest.caller); 734 if (callerApp != null) { 735 appCallingUid = callerApp.mInfo.uid; 736 } else { 737 Slog.w(TAG, "Unable to find app for caller " + mRequest.caller + " (pid=" 738 + mRequest.callingPid + ") when starting: " + mRequest.intent.toString()); 739 SafeActivityOptions.abort(mRequest.activityOptions); 740 return ActivityManager.START_PERMISSION_DENIED; 741 } 742 } 743 744 final IIntentSender target = mService.getIntentSenderLocked( 745 ActivityManager.INTENT_SENDER_ACTIVITY, "android" /* packageName */, 746 null /* featureId */, appCallingUid, mRequest.userId, null /* token */, 747 null /* resultWho*/, 0 /* requestCode*/, new Intent[]{mRequest.intent}, 748 new String[]{mRequest.resolvedType}, 749 PendingIntent.FLAG_CANCEL_CURRENT | PendingIntent.FLAG_ONE_SHOT, 750 null /* bOptions */); 751 752 final Intent newIntent = new Intent(); 753 if (mRequest.requestCode >= 0) { 754 // Caller is requesting a result. 755 newIntent.putExtra(HeavyWeightSwitcherActivity.KEY_HAS_RESULT, true); 756 } 757 newIntent.putExtra(HeavyWeightSwitcherActivity.KEY_INTENT, new IntentSender(target)); 758 heavy.updateIntentForHeavyWeightActivity(newIntent); 759 newIntent.putExtra(HeavyWeightSwitcherActivity.KEY_NEW_APP, 760 mRequest.activityInfo.packageName); 761 newIntent.setFlags(mRequest.intent.getFlags()); 762 newIntent.setClassName("android" /* packageName */, 763 HeavyWeightSwitcherActivity.class.getName()); 764 mRequest.intent = newIntent; 765 mRequest.resolvedType = null; 766 mRequest.caller = null; 767 mRequest.callingUid = Binder.getCallingUid(); 768 mRequest.callingPid = Binder.getCallingPid(); 769 mRequest.componentSpecified = true; 770 mRequest.resolveInfo = mSupervisor.resolveIntent(mRequest.intent, null /* resolvedType */, 771 mRequest.userId, 0 /* matchFlags */, 772 computeResolveFilterUid(mRequest.callingUid, mRequest.realCallingUid, 773 mRequest.filterCallingUid)); 774 mRequest.activityInfo = 775 mRequest.resolveInfo != null ? mRequest.resolveInfo.activityInfo : null; 776 if (mRequest.activityInfo != null) { 777 mRequest.activityInfo = mService.mAmInternal.getActivityInfoForUser( 778 mRequest.activityInfo, mRequest.userId); 779 } 780 781 return START_SUCCESS; 782 } 783 784 /** 785 * Wait for activity launch completes. 786 */ waitResultIfNeeded(WaitResult waitResult, ActivityRecord r, LaunchingState launchingState)787 private int waitResultIfNeeded(WaitResult waitResult, ActivityRecord r, 788 LaunchingState launchingState) { 789 final int res = waitResult.result; 790 if (res == START_DELIVERED_TO_TOP 791 || (res == START_TASK_TO_FRONT && r.nowVisible && r.isState(RESUMED))) { 792 // The activity should already be visible, so nothing to wait. 793 waitResult.timeout = false; 794 waitResult.who = r.mActivityComponent; 795 waitResult.totalTime = 0; 796 return res; 797 } 798 mSupervisor.waitActivityVisibleOrLaunched(waitResult, r, launchingState); 799 if (res == START_SUCCESS && waitResult.result == START_TASK_TO_FRONT) { 800 // A trampoline activity is launched and it brings another existing activity to front. 801 return START_TASK_TO_FRONT; 802 } 803 return res; 804 } 805 806 /** 807 * Executing activity start request and starts the journey of starting an activity. Here 808 * begins with performing several preliminary checks. The normally activity launch flow will 809 * go through {@link #startActivityUnchecked} to {@link #startActivityInner}. 810 */ executeRequest(Request request)811 private int executeRequest(Request request) { 812 if (TextUtils.isEmpty(request.reason)) { 813 throw new IllegalArgumentException("Need to specify a reason."); 814 } 815 mLastStartReason = request.reason; 816 mLastStartActivityTimeMs = System.currentTimeMillis(); 817 mLastStartActivityRecord = null; 818 819 final IApplicationThread caller = request.caller; 820 Intent intent = request.intent; 821 NeededUriGrants intentGrants = request.intentGrants; 822 String resolvedType = request.resolvedType; 823 ActivityInfo aInfo = request.activityInfo; 824 ResolveInfo rInfo = request.resolveInfo; 825 final IVoiceInteractionSession voiceSession = request.voiceSession; 826 final IBinder resultTo = request.resultTo; 827 String resultWho = request.resultWho; 828 int requestCode = request.requestCode; 829 int callingPid = request.callingPid; 830 int callingUid = request.callingUid; 831 String callingPackage = request.callingPackage; 832 String callingFeatureId = request.callingFeatureId; 833 final int realCallingPid = request.realCallingPid; 834 final int realCallingUid = request.realCallingUid; 835 final int startFlags = request.startFlags; 836 final SafeActivityOptions options = request.activityOptions; 837 Task inTask = request.inTask; 838 839 int err = ActivityManager.START_SUCCESS; 840 // Pull the optional Ephemeral Installer-only bundle out of the options early. 841 final Bundle verificationBundle = 842 options != null ? options.popAppVerificationBundle() : null; 843 844 WindowProcessController callerApp = null; 845 if (caller != null) { 846 callerApp = mService.getProcessController(caller); 847 if (callerApp != null) { 848 callingPid = callerApp.getPid(); 849 callingUid = callerApp.mInfo.uid; 850 } else { 851 Slog.w(TAG, "Unable to find app for caller " + caller + " (pid=" + callingPid 852 + ") when starting: " + intent.toString()); 853 err = ActivityManager.START_PERMISSION_DENIED; 854 } 855 } 856 857 final int userId = aInfo != null && aInfo.applicationInfo != null 858 ? UserHandle.getUserId(aInfo.applicationInfo.uid) : 0; 859 if (err == ActivityManager.START_SUCCESS) { 860 Slog.i(TAG, "START u" + userId + " {" + intent.toShortString(true, true, true, false) 861 + "} from uid " + callingUid); 862 } 863 864 ActivityRecord sourceRecord = null; 865 ActivityRecord resultRecord = null; 866 if (resultTo != null) { 867 sourceRecord = mRootWindowContainer.isInAnyTask(resultTo); 868 if (DEBUG_RESULTS) { 869 Slog.v(TAG_RESULTS, "Will send result to " + resultTo + " " + sourceRecord); 870 } 871 if (sourceRecord != null) { 872 if (requestCode >= 0 && !sourceRecord.finishing) { 873 resultRecord = sourceRecord; 874 } 875 } 876 } 877 878 final int launchFlags = intent.getFlags(); 879 if ((launchFlags & Intent.FLAG_ACTIVITY_FORWARD_RESULT) != 0 && sourceRecord != null) { 880 // Transfer the result target from the source activity to the new one being started, 881 // including any failures. 882 if (requestCode >= 0) { 883 SafeActivityOptions.abort(options); 884 return ActivityManager.START_FORWARD_AND_REQUEST_CONFLICT; 885 } 886 resultRecord = sourceRecord.resultTo; 887 if (resultRecord != null && !resultRecord.isInRootTaskLocked()) { 888 resultRecord = null; 889 } 890 resultWho = sourceRecord.resultWho; 891 requestCode = sourceRecord.requestCode; 892 sourceRecord.resultTo = null; 893 if (resultRecord != null) { 894 resultRecord.removeResultsLocked(sourceRecord, resultWho, requestCode); 895 } 896 if (sourceRecord.launchedFromUid == callingUid) { 897 // The new activity is being launched from the same uid as the previous activity 898 // in the flow, and asking to forward its result back to the previous. In this 899 // case the activity is serving as a trampoline between the two, so we also want 900 // to update its launchedFromPackage to be the same as the previous activity. 901 // Note that this is safe, since we know these two packages come from the same 902 // uid; the caller could just as well have supplied that same package name itself 903 // . This specifially deals with the case of an intent picker/chooser being 904 // launched in the app flow to redirect to an activity picked by the user, where 905 // we want the final activity to consider it to have been launched by the 906 // previous app activity. 907 callingPackage = sourceRecord.launchedFromPackage; 908 callingFeatureId = sourceRecord.launchedFromFeatureId; 909 } 910 } 911 912 if (err == ActivityManager.START_SUCCESS && intent.getComponent() == null) { 913 // We couldn't find a class that can handle the given Intent. 914 // That's the end of that! 915 err = ActivityManager.START_INTENT_NOT_RESOLVED; 916 } 917 918 if (err == ActivityManager.START_SUCCESS && aInfo == null) { 919 // We couldn't find the specific class specified in the Intent. 920 // Also the end of the line. 921 err = ActivityManager.START_CLASS_NOT_FOUND; 922 } 923 924 if (err == ActivityManager.START_SUCCESS && sourceRecord != null 925 && sourceRecord.getTask().voiceSession != null) { 926 // If this activity is being launched as part of a voice session, we need to ensure 927 // that it is safe to do so. If the upcoming activity will also be part of the voice 928 // session, we can only launch it if it has explicitly said it supports the VOICE 929 // category, or it is a part of the calling app. 930 if ((launchFlags & FLAG_ACTIVITY_NEW_TASK) == 0 931 && sourceRecord.info.applicationInfo.uid != aInfo.applicationInfo.uid) { 932 try { 933 intent.addCategory(Intent.CATEGORY_VOICE); 934 if (!mService.getPackageManager().activitySupportsIntent( 935 intent.getComponent(), intent, resolvedType)) { 936 Slog.w(TAG, "Activity being started in current voice task does not support " 937 + "voice: " + intent); 938 err = ActivityManager.START_NOT_VOICE_COMPATIBLE; 939 } 940 } catch (RemoteException e) { 941 Slog.w(TAG, "Failure checking voice capabilities", e); 942 err = ActivityManager.START_NOT_VOICE_COMPATIBLE; 943 } 944 } 945 } 946 947 if (err == ActivityManager.START_SUCCESS && voiceSession != null) { 948 // If the caller is starting a new voice session, just make sure the target 949 // is actually allowing it to run this way. 950 try { 951 if (!mService.getPackageManager().activitySupportsIntent(intent.getComponent(), 952 intent, resolvedType)) { 953 Slog.w(TAG, 954 "Activity being started in new voice task does not support: " + intent); 955 err = ActivityManager.START_NOT_VOICE_COMPATIBLE; 956 } 957 } catch (RemoteException e) { 958 Slog.w(TAG, "Failure checking voice capabilities", e); 959 err = ActivityManager.START_NOT_VOICE_COMPATIBLE; 960 } 961 } 962 963 final Task resultRootTask = resultRecord == null 964 ? null : resultRecord.getRootTask(); 965 966 if (err != START_SUCCESS) { 967 if (resultRecord != null) { 968 resultRecord.sendResult(INVALID_UID, resultWho, requestCode, RESULT_CANCELED, 969 null /* data */, null /* dataGrants */); 970 } 971 SafeActivityOptions.abort(options); 972 return err; 973 } 974 975 boolean abort = !mSupervisor.checkStartAnyActivityPermission(intent, aInfo, resultWho, 976 requestCode, callingPid, callingUid, callingPackage, callingFeatureId, 977 request.ignoreTargetSecurity, inTask != null, callerApp, resultRecord, 978 resultRootTask); 979 abort |= !mService.mIntentFirewall.checkStartActivity(intent, callingUid, 980 callingPid, resolvedType, aInfo.applicationInfo); 981 abort |= !mService.getPermissionPolicyInternal().checkStartActivity(intent, callingUid, 982 callingPackage); 983 984 boolean restrictedBgActivity = false; 985 if (!abort) { 986 try { 987 Trace.traceBegin(Trace.TRACE_TAG_WINDOW_MANAGER, 988 "shouldAbortBackgroundActivityStart"); 989 restrictedBgActivity = shouldAbortBackgroundActivityStart(callingUid, 990 callingPid, callingPackage, realCallingUid, realCallingPid, callerApp, 991 request.originatingPendingIntent, request.allowBackgroundActivityStart, 992 intent); 993 } finally { 994 Trace.traceEnd(Trace.TRACE_TAG_WINDOW_MANAGER); 995 } 996 } 997 998 // Merge the two options bundles, while realCallerOptions takes precedence. 999 ActivityOptions checkedOptions = options != null 1000 ? options.getOptions(intent, aInfo, callerApp, mSupervisor) : null; 1001 if (request.allowPendingRemoteAnimationRegistryLookup) { 1002 checkedOptions = mService.getActivityStartController() 1003 .getPendingRemoteAnimationRegistry() 1004 .overrideOptionsIfNeeded(callingPackage, checkedOptions); 1005 } 1006 if (mService.mController != null) { 1007 try { 1008 // The Intent we give to the watcher has the extra data stripped off, since it 1009 // can contain private information. 1010 Intent watchIntent = intent.cloneFilter(); 1011 abort |= !mService.mController.activityStarting(watchIntent, 1012 aInfo.applicationInfo.packageName); 1013 } catch (RemoteException e) { 1014 mService.mController = null; 1015 } 1016 } 1017 1018 mInterceptor.setStates(userId, realCallingPid, realCallingUid, startFlags, callingPackage, 1019 callingFeatureId); 1020 if (mInterceptor.intercept(intent, rInfo, aInfo, resolvedType, inTask, callingPid, 1021 callingUid, checkedOptions)) { 1022 // activity start was intercepted, e.g. because the target user is currently in quiet 1023 // mode (turn off work) or the target application is suspended 1024 intent = mInterceptor.mIntent; 1025 rInfo = mInterceptor.mRInfo; 1026 aInfo = mInterceptor.mAInfo; 1027 resolvedType = mInterceptor.mResolvedType; 1028 inTask = mInterceptor.mInTask; 1029 callingPid = mInterceptor.mCallingPid; 1030 callingUid = mInterceptor.mCallingUid; 1031 checkedOptions = mInterceptor.mActivityOptions; 1032 1033 // The interception target shouldn't get any permission grants 1034 // intended for the original destination 1035 intentGrants = null; 1036 } 1037 1038 if (abort) { 1039 if (resultRecord != null) { 1040 resultRecord.sendResult(INVALID_UID, resultWho, requestCode, RESULT_CANCELED, 1041 null /* data */, null /* dataGrants */); 1042 } 1043 // We pretend to the caller that it was really started, but they will just get a 1044 // cancel result. 1045 ActivityOptions.abort(checkedOptions); 1046 return START_ABORTED; 1047 } 1048 1049 // If permissions need a review before any of the app components can run, we 1050 // launch the review activity and pass a pending intent to start the activity 1051 // we are to launching now after the review is completed. 1052 if (aInfo != null) { 1053 if (mService.getPackageManagerInternalLocked().isPermissionsReviewRequired( 1054 aInfo.packageName, userId)) { 1055 final IIntentSender target = mService.getIntentSenderLocked( 1056 ActivityManager.INTENT_SENDER_ACTIVITY, callingPackage, callingFeatureId, 1057 callingUid, userId, null, null, 0, new Intent[]{intent}, 1058 new String[]{resolvedType}, PendingIntent.FLAG_CANCEL_CURRENT 1059 | PendingIntent.FLAG_ONE_SHOT, null); 1060 1061 Intent newIntent = new Intent(Intent.ACTION_REVIEW_PERMISSIONS); 1062 1063 int flags = intent.getFlags(); 1064 flags |= Intent.FLAG_ACTIVITY_EXCLUDE_FROM_RECENTS; 1065 1066 /* 1067 * Prevent reuse of review activity: Each app needs their own review activity. By 1068 * default activities launched with NEW_TASK or NEW_DOCUMENT try to reuse activities 1069 * with the same launch parameters (extras are ignored). Hence to avoid possible 1070 * reuse force a new activity via the MULTIPLE_TASK flag. 1071 * 1072 * Activities that are not launched with NEW_TASK or NEW_DOCUMENT are not re-used, 1073 * hence no need to add the flag in this case. 1074 */ 1075 if ((flags & (FLAG_ACTIVITY_NEW_TASK | FLAG_ACTIVITY_NEW_DOCUMENT)) != 0) { 1076 flags |= Intent.FLAG_ACTIVITY_MULTIPLE_TASK; 1077 } 1078 newIntent.setFlags(flags); 1079 1080 newIntent.putExtra(Intent.EXTRA_PACKAGE_NAME, aInfo.packageName); 1081 newIntent.putExtra(Intent.EXTRA_INTENT, new IntentSender(target)); 1082 if (resultRecord != null) { 1083 newIntent.putExtra(Intent.EXTRA_RESULT_NEEDED, true); 1084 } 1085 intent = newIntent; 1086 1087 // The permissions review target shouldn't get any permission 1088 // grants intended for the original destination 1089 intentGrants = null; 1090 1091 resolvedType = null; 1092 callingUid = realCallingUid; 1093 callingPid = realCallingPid; 1094 1095 rInfo = mSupervisor.resolveIntent(intent, resolvedType, userId, 0, 1096 computeResolveFilterUid( 1097 callingUid, realCallingUid, request.filterCallingUid)); 1098 aInfo = mSupervisor.resolveActivity(intent, rInfo, startFlags, 1099 null /*profilerInfo*/); 1100 1101 if (DEBUG_PERMISSIONS_REVIEW) { 1102 final Task focusedRootTask = 1103 mRootWindowContainer.getTopDisplayFocusedRootTask(); 1104 Slog.i(TAG, "START u" + userId + " {" + intent.toShortString(true, true, 1105 true, false) + "} from uid " + callingUid + " on display " 1106 + (focusedRootTask == null ? DEFAULT_DISPLAY 1107 : focusedRootTask.getDisplayId())); 1108 } 1109 } 1110 } 1111 1112 // If we have an ephemeral app, abort the process of launching the resolved intent. 1113 // Instead, launch the ephemeral installer. Once the installer is finished, it 1114 // starts either the intent we resolved here [on install error] or the ephemeral 1115 // app [on install success]. 1116 if (rInfo != null && rInfo.auxiliaryInfo != null) { 1117 intent = createLaunchIntent(rInfo.auxiliaryInfo, request.ephemeralIntent, 1118 callingPackage, callingFeatureId, verificationBundle, resolvedType, userId); 1119 resolvedType = null; 1120 callingUid = realCallingUid; 1121 callingPid = realCallingPid; 1122 1123 // The ephemeral installer shouldn't get any permission grants 1124 // intended for the original destination 1125 intentGrants = null; 1126 1127 aInfo = mSupervisor.resolveActivity(intent, rInfo, startFlags, null /*profilerInfo*/); 1128 } 1129 // TODO (b/187680964) Correcting the caller/pid/uid when start activity from shortcut 1130 // Pending intent launched from systemui also depends on caller app 1131 if (callerApp == null && realCallingPid > 0) { 1132 final WindowProcessController wpc = mService.mProcessMap.getProcess(realCallingPid); 1133 if (wpc != null) { 1134 callerApp = wpc; 1135 } 1136 } 1137 final ActivityRecord r = new ActivityRecord.Builder(mService) 1138 .setCaller(callerApp) 1139 .setLaunchedFromPid(callingPid) 1140 .setLaunchedFromUid(callingUid) 1141 .setLaunchedFromPackage(callingPackage) 1142 .setLaunchedFromFeature(callingFeatureId) 1143 .setIntent(intent) 1144 .setResolvedType(resolvedType) 1145 .setActivityInfo(aInfo) 1146 .setConfiguration(mService.getGlobalConfiguration()) 1147 .setResultTo(resultRecord) 1148 .setResultWho(resultWho) 1149 .setRequestCode(requestCode) 1150 .setComponentSpecified(request.componentSpecified) 1151 .setRootVoiceInteraction(voiceSession != null) 1152 .setActivityOptions(checkedOptions) 1153 .setSourceRecord(sourceRecord) 1154 .build(); 1155 1156 mLastStartActivityRecord = r; 1157 1158 if (r.appTimeTracker == null && sourceRecord != null) { 1159 // If the caller didn't specify an explicit time tracker, we want to continue 1160 // tracking under any it has. 1161 r.appTimeTracker = sourceRecord.appTimeTracker; 1162 } 1163 1164 // Only allow app switching to be resumed if activity is not a restricted background 1165 // activity and target app is not home process, otherwise any background activity 1166 // started in background task can stop home button protection mode. 1167 // As the targeted app is not a home process and we don't need to wait for the 2nd 1168 // activity to be started to resume app switching, we can just enable app switching 1169 // directly. 1170 WindowProcessController homeProcess = mService.mHomeProcess; 1171 boolean isHomeProcess = homeProcess != null 1172 && aInfo.applicationInfo.uid == homeProcess.mUid; 1173 if (!restrictedBgActivity && !isHomeProcess) { 1174 mService.resumeAppSwitches(); 1175 } 1176 1177 mLastStartActivityResult = startActivityUnchecked(r, sourceRecord, voiceSession, 1178 request.voiceInteractor, startFlags, true /* doResume */, checkedOptions, inTask, 1179 restrictedBgActivity, intentGrants); 1180 1181 if (request.outActivity != null) { 1182 request.outActivity[0] = mLastStartActivityRecord; 1183 } 1184 1185 return mLastStartActivityResult; 1186 } 1187 1188 /** 1189 * Return true if background activity is really aborted. 1190 * 1191 * TODO(b/131748165): Refactor the logic so we don't need to call this method everywhere. 1192 */ handleBackgroundActivityAbort(ActivityRecord r)1193 private boolean handleBackgroundActivityAbort(ActivityRecord r) { 1194 // TODO(b/131747138): Remove toast and refactor related code in R release. 1195 final boolean abort = !mService.isBackgroundActivityStartsEnabled(); 1196 if (!abort) { 1197 return false; 1198 } 1199 final ActivityRecord resultRecord = r.resultTo; 1200 final String resultWho = r.resultWho; 1201 int requestCode = r.requestCode; 1202 if (resultRecord != null) { 1203 resultRecord.sendResult(INVALID_UID, resultWho, requestCode, RESULT_CANCELED, 1204 null /* data */, null /* dataGrants */); 1205 } 1206 // We pretend to the caller that it was really started to make it backward compatible, but 1207 // they will just get a cancel result. 1208 ActivityOptions.abort(r.getOptions()); 1209 return true; 1210 } 1211 getExternalResult(int result)1212 static int getExternalResult(int result) { 1213 // Aborted results are treated as successes externally, but we must track them internally. 1214 return result != START_ABORTED ? result : START_SUCCESS; 1215 } 1216 1217 /** 1218 * Called when execution is complete. Sets state indicating completion and proceeds with 1219 * recycling if appropriate. 1220 */ onExecutionComplete()1221 private void onExecutionComplete() { 1222 mController.onExecutionComplete(this); 1223 } 1224 isHomeApp(int uid, @Nullable String packageName)1225 private boolean isHomeApp(int uid, @Nullable String packageName) { 1226 if (mService.mHomeProcess != null) { 1227 // Fast check 1228 return uid == mService.mHomeProcess.mUid; 1229 } 1230 if (packageName == null) { 1231 return false; 1232 } 1233 ComponentName activity = 1234 mService.getPackageManagerInternalLocked().getDefaultHomeActivity( 1235 UserHandle.getUserId(uid)); 1236 return activity != null && packageName.equals(activity.getPackageName()); 1237 } 1238 shouldAbortBackgroundActivityStart(int callingUid, int callingPid, final String callingPackage, int realCallingUid, int realCallingPid, WindowProcessController callerApp, PendingIntentRecord originatingPendingIntent, boolean allowBackgroundActivityStart, Intent intent)1239 boolean shouldAbortBackgroundActivityStart(int callingUid, int callingPid, 1240 final String callingPackage, int realCallingUid, int realCallingPid, 1241 WindowProcessController callerApp, PendingIntentRecord originatingPendingIntent, 1242 boolean allowBackgroundActivityStart, Intent intent) { 1243 // don't abort for the most important UIDs 1244 final int callingAppId = UserHandle.getAppId(callingUid); 1245 if (callingUid == Process.ROOT_UID || callingAppId == Process.SYSTEM_UID 1246 || callingAppId == Process.NFC_UID) { 1247 if (DEBUG_ACTIVITY_STARTS) { 1248 Slog.d(TAG, "Activity start allowed for important callingUid (" + callingUid + ")"); 1249 } 1250 return false; 1251 } 1252 1253 // Always allow home application to start activities. 1254 if (isHomeApp(callingUid, callingPackage)) { 1255 if (DEBUG_ACTIVITY_STARTS) { 1256 Slog.d(TAG, "Activity start allowed for home app callingUid (" + callingUid + ")"); 1257 } 1258 return false; 1259 } 1260 1261 // IME should always be allowed to start activity, like IME settings. 1262 final WindowState imeWindow = mRootWindowContainer.getCurrentInputMethodWindow(); 1263 if (imeWindow != null && callingAppId == imeWindow.mOwnerUid) { 1264 if (DEBUG_ACTIVITY_STARTS) { 1265 Slog.d(TAG, "Activity start allowed for active ime (" + callingUid + ")"); 1266 } 1267 return false; 1268 } 1269 1270 // This is used to block background activity launch even if the app is still 1271 // visible to user after user clicking home button. 1272 final boolean appSwitchAllowed = mService.getBalAppSwitchesAllowed(); 1273 1274 // don't abort if the callingUid has a visible window or is a persistent system process 1275 final int callingUidProcState = mService.mActiveUids.getUidState(callingUid); 1276 final boolean callingUidHasAnyVisibleWindow = mService.hasActiveVisibleWindow(callingUid); 1277 final boolean isCallingUidForeground = callingUidHasAnyVisibleWindow 1278 || callingUidProcState == ActivityManager.PROCESS_STATE_TOP 1279 || callingUidProcState == ActivityManager.PROCESS_STATE_BOUND_TOP; 1280 final boolean isCallingUidPersistentSystemProcess = 1281 callingUidProcState <= ActivityManager.PROCESS_STATE_PERSISTENT_UI; 1282 1283 // Normal apps with visible app window will be allowed to start activity if app switching 1284 // is allowed, or apps like live wallpaper with non app visible window will be allowed. 1285 if (((appSwitchAllowed || mService.mActiveUids.hasNonAppVisibleWindow(callingUid)) 1286 && callingUidHasAnyVisibleWindow) 1287 || isCallingUidPersistentSystemProcess) { 1288 if (DEBUG_ACTIVITY_STARTS) { 1289 Slog.d(TAG, "Activity start allowed: callingUidHasAnyVisibleWindow = " + callingUid 1290 + ", isCallingUidPersistentSystemProcess = " 1291 + isCallingUidPersistentSystemProcess); 1292 } 1293 return false; 1294 } 1295 // take realCallingUid into consideration 1296 final int realCallingUidProcState = (callingUid == realCallingUid) 1297 ? callingUidProcState 1298 : mService.mActiveUids.getUidState(realCallingUid); 1299 final boolean realCallingUidHasAnyVisibleWindow = (callingUid == realCallingUid) 1300 ? callingUidHasAnyVisibleWindow 1301 : mService.hasActiveVisibleWindow(realCallingUid); 1302 final boolean isRealCallingUidForeground = (callingUid == realCallingUid) 1303 ? isCallingUidForeground 1304 : realCallingUidHasAnyVisibleWindow 1305 || realCallingUidProcState == ActivityManager.PROCESS_STATE_TOP; 1306 final int realCallingAppId = UserHandle.getAppId(realCallingUid); 1307 final boolean isRealCallingUidPersistentSystemProcess = (callingUid == realCallingUid) 1308 ? isCallingUidPersistentSystemProcess 1309 : (realCallingAppId == Process.SYSTEM_UID) 1310 || realCallingUidProcState <= ActivityManager.PROCESS_STATE_PERSISTENT_UI; 1311 if (realCallingUid != callingUid) { 1312 // don't abort if the realCallingUid has a visible window 1313 // TODO(b/171459802): We should check appSwitchAllowed also 1314 if (realCallingUidHasAnyVisibleWindow) { 1315 if (DEBUG_ACTIVITY_STARTS) { 1316 Slog.d(TAG, "Activity start allowed: realCallingUid (" + realCallingUid 1317 + ") has visible (non-toast) window"); 1318 } 1319 return false; 1320 } 1321 // if the realCallingUid is a persistent system process, abort if the IntentSender 1322 // wasn't allowed to start an activity 1323 if (isRealCallingUidPersistentSystemProcess && allowBackgroundActivityStart) { 1324 if (DEBUG_ACTIVITY_STARTS) { 1325 Slog.d(TAG, "Activity start allowed: realCallingUid (" + realCallingUid 1326 + ") is persistent system process AND intent sender allowed " 1327 + "(allowBackgroundActivityStart = true)"); 1328 } 1329 return false; 1330 } 1331 // don't abort if the realCallingUid is an associated companion app 1332 if (mService.isAssociatedCompanionApp(UserHandle.getUserId(realCallingUid), 1333 realCallingUid)) { 1334 if (DEBUG_ACTIVITY_STARTS) { 1335 Slog.d(TAG, "Activity start allowed: realCallingUid (" + realCallingUid 1336 + ") is companion app"); 1337 } 1338 return false; 1339 } 1340 } 1341 // don't abort if the callingUid has START_ACTIVITIES_FROM_BACKGROUND permission 1342 if (mService.checkPermission(START_ACTIVITIES_FROM_BACKGROUND, callingPid, callingUid) 1343 == PERMISSION_GRANTED) { 1344 if (DEBUG_ACTIVITY_STARTS) { 1345 Slog.d(TAG, 1346 "Background activity start allowed: START_ACTIVITIES_FROM_BACKGROUND " 1347 + "permission granted for uid " 1348 + callingUid); 1349 } 1350 return false; 1351 } 1352 // don't abort if the caller has the same uid as the recents component 1353 if (mSupervisor.mRecentTasks.isCallerRecents(callingUid)) { 1354 if (DEBUG_ACTIVITY_STARTS) { 1355 Slog.d(TAG, "Background activity start allowed: callingUid (" + callingUid 1356 + ") is recents"); 1357 } 1358 return false; 1359 } 1360 // don't abort if the callingUid is the device owner 1361 if (mService.isDeviceOwner(callingUid)) { 1362 if (DEBUG_ACTIVITY_STARTS) { 1363 Slog.d(TAG, "Background activity start allowed: callingUid (" + callingUid 1364 + ") is device owner"); 1365 } 1366 return false; 1367 } 1368 // don't abort if the callingUid has companion device 1369 final int callingUserId = UserHandle.getUserId(callingUid); 1370 if (mService.isAssociatedCompanionApp(callingUserId, callingUid)) { 1371 if (DEBUG_ACTIVITY_STARTS) { 1372 Slog.d(TAG, "Background activity start allowed: callingUid (" + callingUid 1373 + ") is companion app"); 1374 } 1375 return false; 1376 } 1377 // don't abort if the callingUid has SYSTEM_ALERT_WINDOW permission 1378 if (mService.hasSystemAlertWindowPermission(callingUid, callingPid, callingPackage)) { 1379 Slog.w(TAG, "Background activity start for " + callingPackage 1380 + " allowed because SYSTEM_ALERT_WINDOW permission is granted."); 1381 return false; 1382 } 1383 // If we don't have callerApp at this point, no caller was provided to startActivity(). 1384 // That's the case for PendingIntent-based starts, since the creator's process might not be 1385 // up and alive. If that's the case, we retrieve the WindowProcessController for the send() 1386 // caller, so that we can make the decision based on its state. 1387 int callerAppUid = callingUid; 1388 if (callerApp == null) { 1389 callerApp = mService.getProcessController(realCallingPid, realCallingUid); 1390 callerAppUid = realCallingUid; 1391 } 1392 // don't abort if the callerApp or other processes of that uid are allowed in any way 1393 if (callerApp != null) { 1394 // first check the original calling process 1395 if (callerApp.areBackgroundActivityStartsAllowed(appSwitchAllowed)) { 1396 if (DEBUG_ACTIVITY_STARTS) { 1397 Slog.d(TAG, "Background activity start allowed: callerApp process (pid = " 1398 + callerApp.getPid() + ", uid = " + callerAppUid + ") is allowed"); 1399 } 1400 return false; 1401 } 1402 // only if that one wasn't allowed, check the other ones 1403 final ArraySet<WindowProcessController> uidProcesses = 1404 mService.mProcessMap.getProcesses(callerAppUid); 1405 if (uidProcesses != null) { 1406 for (int i = uidProcesses.size() - 1; i >= 0; i--) { 1407 final WindowProcessController proc = uidProcesses.valueAt(i); 1408 if (proc != callerApp 1409 && proc.areBackgroundActivityStartsAllowed(appSwitchAllowed)) { 1410 if (DEBUG_ACTIVITY_STARTS) { 1411 Slog.d(TAG, 1412 "Background activity start allowed: process " + proc.getPid() 1413 + " from uid " + callerAppUid + " is allowed"); 1414 } 1415 return false; 1416 } 1417 } 1418 } 1419 } 1420 // anything that has fallen through would currently be aborted 1421 Slog.w(TAG, "Background activity start [callingPackage: " + callingPackage 1422 + "; callingUid: " + callingUid 1423 + "; appSwitchAllowed: " + appSwitchAllowed 1424 + "; isCallingUidForeground: " + isCallingUidForeground 1425 + "; callingUidHasAnyVisibleWindow: " + callingUidHasAnyVisibleWindow 1426 + "; callingUidProcState: " + DebugUtils.valueToString(ActivityManager.class, 1427 "PROCESS_STATE_", callingUidProcState) 1428 + "; isCallingUidPersistentSystemProcess: " + isCallingUidPersistentSystemProcess 1429 + "; realCallingUid: " + realCallingUid 1430 + "; isRealCallingUidForeground: " + isRealCallingUidForeground 1431 + "; realCallingUidHasAnyVisibleWindow: " + realCallingUidHasAnyVisibleWindow 1432 + "; realCallingUidProcState: " + DebugUtils.valueToString(ActivityManager.class, 1433 "PROCESS_STATE_", realCallingUidProcState) 1434 + "; isRealCallingUidPersistentSystemProcess: " 1435 + isRealCallingUidPersistentSystemProcess 1436 + "; originatingPendingIntent: " + originatingPendingIntent 1437 + "; allowBackgroundActivityStart: " + allowBackgroundActivityStart 1438 + "; intent: " + intent 1439 + "; callerApp: " + callerApp 1440 + "; inVisibleTask: " + (callerApp != null && callerApp.hasActivityInVisibleTask()) 1441 + "]"); 1442 // log aborted activity start to TRON 1443 if (mService.isActivityStartsLoggingEnabled()) { 1444 mSupervisor.getActivityMetricsLogger().logAbortedBgActivityStart(intent, callerApp, 1445 callingUid, callingPackage, callingUidProcState, callingUidHasAnyVisibleWindow, 1446 realCallingUid, realCallingUidProcState, realCallingUidHasAnyVisibleWindow, 1447 (originatingPendingIntent != null)); 1448 } 1449 return true; 1450 } 1451 1452 /** 1453 * Creates a launch intent for the given auxiliary resolution data. 1454 */ createLaunchIntent(@ullable AuxiliaryResolveInfo auxiliaryResponse, Intent originalIntent, String callingPackage, @Nullable String callingFeatureId, Bundle verificationBundle, String resolvedType, int userId)1455 private @NonNull Intent createLaunchIntent(@Nullable AuxiliaryResolveInfo auxiliaryResponse, 1456 Intent originalIntent, String callingPackage, @Nullable String callingFeatureId, 1457 Bundle verificationBundle, String resolvedType, int userId) { 1458 if (auxiliaryResponse != null && auxiliaryResponse.needsPhaseTwo) { 1459 // request phase two resolution 1460 PackageManagerInternal packageManager = mService.getPackageManagerInternalLocked(); 1461 boolean isRequesterInstantApp = packageManager.isInstantApp(callingPackage, userId); 1462 packageManager.requestInstantAppResolutionPhaseTwo( 1463 auxiliaryResponse, originalIntent, resolvedType, callingPackage, 1464 callingFeatureId, isRequesterInstantApp, verificationBundle, userId); 1465 } 1466 return InstantAppResolver.buildEphemeralInstallerIntent( 1467 originalIntent, 1468 InstantAppResolver.sanitizeIntent(originalIntent), 1469 auxiliaryResponse == null ? null : auxiliaryResponse.failureIntent, 1470 callingPackage, 1471 callingFeatureId, 1472 verificationBundle, 1473 resolvedType, 1474 userId, 1475 auxiliaryResponse == null ? null : auxiliaryResponse.installFailureActivity, 1476 auxiliaryResponse == null ? null : auxiliaryResponse.token, 1477 auxiliaryResponse != null && auxiliaryResponse.needsPhaseTwo, 1478 auxiliaryResponse == null ? null : auxiliaryResponse.filters); 1479 } 1480 postStartActivityProcessing(ActivityRecord r, int result, Task startedActivityRootTask)1481 void postStartActivityProcessing(ActivityRecord r, int result, 1482 Task startedActivityRootTask) { 1483 if (!ActivityManager.isStartResultSuccessful(result)) { 1484 if (mFrozeTaskList) { 1485 // If we specifically froze the task list as part of starting an activity, then 1486 // reset the frozen list state if it failed to start. This is normally otherwise 1487 // called when the freeze-timeout has elapsed. 1488 mSupervisor.mRecentTasks.resetFreezeTaskListReorderingOnTimeout(); 1489 } 1490 } 1491 if (ActivityManager.isStartResultFatalError(result)) { 1492 return; 1493 } 1494 1495 // We're waiting for an activity launch to finish, but that activity simply 1496 // brought another activity to front. We must also handle the case where the task is already 1497 // in the front as a result of the trampoline activity being in the same task (it will be 1498 // considered focused as the trampoline will be finished). Let them know about this, so 1499 // it waits for the new activity to become visible instead, {@link #waitResultIfNeeded}. 1500 mSupervisor.reportWaitingActivityLaunchedIfNeeded(r, result); 1501 1502 final Task targetTask = r.getTask() != null 1503 ? r.getTask() 1504 : mTargetTask; 1505 if (startedActivityRootTask == null || targetTask == null) { 1506 return; 1507 } 1508 1509 final int clearTaskFlags = FLAG_ACTIVITY_NEW_TASK | FLAG_ACTIVITY_CLEAR_TASK; 1510 boolean clearedTask = (mLaunchFlags & clearTaskFlags) == clearTaskFlags 1511 && mReuseTask != null; 1512 if (result == START_TASK_TO_FRONT || result == START_DELIVERED_TO_TOP || clearedTask) { 1513 // The activity was already running so it wasn't started, but either brought to the 1514 // front or the new intent was delivered to it since it was already in front. Notify 1515 // anyone interested in this piece of information. 1516 final Task rootHomeTask = targetTask.getDisplayArea().getRootHomeTask(); 1517 final boolean homeTaskVisible = rootHomeTask != null 1518 && rootHomeTask.shouldBeVisible(null); 1519 final ActivityRecord top = targetTask.getTopNonFinishingActivity(); 1520 final boolean visible = top != null && top.isVisible(); 1521 mService.getTaskChangeNotificationController().notifyActivityRestartAttempt( 1522 targetTask.getTaskInfo(), homeTaskVisible, clearedTask, visible); 1523 } 1524 } 1525 1526 /** 1527 * Compute the logical UID based on which the package manager would filter 1528 * app components i.e. based on which the instant app policy would be applied 1529 * because it is the logical calling UID. 1530 * 1531 * @param customCallingUid The UID on whose behalf to make the call. 1532 * @param actualCallingUid The UID actually making the call. 1533 * @param filterCallingUid The UID to be used to filter for instant apps. 1534 * @return The logical UID making the call. 1535 */ computeResolveFilterUid(int customCallingUid, int actualCallingUid, int filterCallingUid)1536 static int computeResolveFilterUid(int customCallingUid, int actualCallingUid, 1537 int filterCallingUid) { 1538 return filterCallingUid != UserHandle.USER_NULL 1539 ? filterCallingUid 1540 : (customCallingUid >= 0 ? customCallingUid : actualCallingUid); 1541 } 1542 1543 /** 1544 * Start an activity while most of preliminary checks has been done and caller has been 1545 * confirmed that holds necessary permissions to do so. 1546 * Here also ensures that the starting activity is removed if the start wasn't successful. 1547 */ startActivityUnchecked(final ActivityRecord r, ActivityRecord sourceRecord, IVoiceInteractionSession voiceSession, IVoiceInteractor voiceInteractor, int startFlags, boolean doResume, ActivityOptions options, Task inTask, boolean restrictedBgActivity, NeededUriGrants intentGrants)1548 private int startActivityUnchecked(final ActivityRecord r, ActivityRecord sourceRecord, 1549 IVoiceInteractionSession voiceSession, IVoiceInteractor voiceInteractor, 1550 int startFlags, boolean doResume, ActivityOptions options, Task inTask, 1551 boolean restrictedBgActivity, NeededUriGrants intentGrants) { 1552 int result = START_CANCELED; 1553 final Task startedActivityRootTask; 1554 1555 // Create a transition now to record the original intent of actions taken within 1556 // startActivityInner. Otherwise, logic in startActivityInner could start a different 1557 // transition based on a sub-action. 1558 // Only do the create here (and defer requestStart) since startActivityInner might abort. 1559 final Transition newTransition = (!mService.getTransitionController().isCollecting() 1560 && mService.getTransitionController().getTransitionPlayer() != null) 1561 ? mService.getTransitionController().createTransition(TRANSIT_OPEN) : null; 1562 IRemoteTransition remoteTransition = r.takeRemoteTransition(); 1563 if (newTransition != null && remoteTransition != null) { 1564 newTransition.setRemoteTransition(remoteTransition); 1565 } 1566 mService.getTransitionController().collect(r); 1567 try { 1568 mService.deferWindowLayout(); 1569 Trace.traceBegin(Trace.TRACE_TAG_WINDOW_MANAGER, "startActivityInner"); 1570 result = startActivityInner(r, sourceRecord, voiceSession, voiceInteractor, 1571 startFlags, doResume, options, inTask, restrictedBgActivity, intentGrants); 1572 } finally { 1573 Trace.traceEnd(Trace.TRACE_TAG_WINDOW_MANAGER); 1574 startedActivityRootTask = handleStartResult(r, result); 1575 mService.continueWindowLayout(); 1576 mSupervisor.mUserLeaving = false; 1577 1578 // Transition housekeeping 1579 if (!ActivityManager.isStartResultSuccessful(result)) { 1580 if (newTransition != null) { 1581 newTransition.abort(); 1582 } 1583 } else { 1584 if (!mAvoidMoveToFront && mDoResume 1585 && mRootWindowContainer.hasVisibleWindowAboveButDoesNotOwnNotificationShade( 1586 r.launchedFromUid)) { 1587 // If the UID launching the activity has a visible window on top of the 1588 // notification shade and it's launching an activity that's going to be at the 1589 // front, we should move the shade out of the way so the user can see it. 1590 // We want to avoid the case where the activity is launched on top of a 1591 // background task which is not moved to the front. 1592 StatusBarManagerInternal statusBar = mService.getStatusBarManagerInternal(); 1593 if (statusBar != null) { 1594 // This results in a async call since the interface is one-way 1595 statusBar.collapsePanels(); 1596 } 1597 } 1598 if (result == START_SUCCESS || result == START_TASK_TO_FRONT) { 1599 // The activity is started new rather than just brought forward, so record 1600 // it as an existence change. 1601 mService.getTransitionController().collectExistenceChange(r); 1602 } 1603 if (newTransition != null) { 1604 mService.getTransitionController().requestStartTransition(newTransition, 1605 mTargetTask, remoteTransition); 1606 } else { 1607 // Make the collecting transition wait until this request is ready. 1608 mService.getTransitionController().setReady(false); 1609 } 1610 } 1611 } 1612 1613 postStartActivityProcessing(r, result, startedActivityRootTask); 1614 1615 return result; 1616 } 1617 1618 /** 1619 * If the start result is success, ensure that the configuration of the started activity matches 1620 * the current display. Otherwise clean up unassociated containers to avoid leakage. 1621 * 1622 * @return the root task where the successful started activity resides. 1623 */ handleStartResult(@onNull ActivityRecord started, int result)1624 private @Nullable Task handleStartResult(@NonNull ActivityRecord started, int result) { 1625 final Task currentRootTask = started.getRootTask(); 1626 Task startedActivityRootTask = currentRootTask != null ? currentRootTask : mTargetRootTask; 1627 1628 if (ActivityManager.isStartResultSuccessful(result)) { 1629 if (startedActivityRootTask != null) { 1630 // If there is no state change (e.g. a resumed activity is reparented to top of 1631 // another display) to trigger a visibility/configuration checking, we have to 1632 // update the configuration for changing to different display. 1633 final ActivityRecord currentTop = startedActivityRootTask.topRunningActivity(); 1634 if (currentTop != null && currentTop.shouldUpdateConfigForDisplayChanged()) { 1635 mRootWindowContainer.ensureVisibilityAndConfig( 1636 currentTop, currentTop.getDisplayId(), 1637 true /* markFrozenIfConfigChanged */, false /* deferResume */); 1638 } 1639 } 1640 return startedActivityRootTask; 1641 } 1642 1643 // If we are not able to proceed, disassociate the activity from the task. Leaving an 1644 // activity in an incomplete state can lead to issues, such as performing operations 1645 // without a window container. 1646 final Task rootTask = mStartActivity.getRootTask(); 1647 if (rootTask != null) { 1648 mStartActivity.finishIfPossible("startActivity", true /* oomAdj */); 1649 } 1650 1651 // Root task should also be detached from display and be removed if it's empty. 1652 if (startedActivityRootTask != null && startedActivityRootTask.isAttached() 1653 && !startedActivityRootTask.hasActivity() 1654 && !startedActivityRootTask.isActivityTypeHome()) { 1655 startedActivityRootTask.removeIfPossible("handleStartResult"); 1656 startedActivityRootTask = null; 1657 } 1658 return startedActivityRootTask; 1659 } 1660 1661 /** 1662 * Start an activity and determine if the activity should be adding to the top of an existing 1663 * task or delivered new intent to an existing activity. Also manipulating the activity task 1664 * onto requested or valid root-task/display. 1665 * 1666 * Note: This method should only be called from {@link #startActivityUnchecked}. 1667 */ 1668 1669 // TODO(b/152429287): Make it easier to exercise code paths through startActivityInner 1670 @VisibleForTesting startActivityInner(final ActivityRecord r, ActivityRecord sourceRecord, IVoiceInteractionSession voiceSession, IVoiceInteractor voiceInteractor, int startFlags, boolean doResume, ActivityOptions options, Task inTask, boolean restrictedBgActivity, NeededUriGrants intentGrants)1671 int startActivityInner(final ActivityRecord r, ActivityRecord sourceRecord, 1672 IVoiceInteractionSession voiceSession, IVoiceInteractor voiceInteractor, 1673 int startFlags, boolean doResume, ActivityOptions options, Task inTask, 1674 boolean restrictedBgActivity, NeededUriGrants intentGrants) { 1675 setInitialState(r, options, inTask, doResume, startFlags, sourceRecord, voiceSession, 1676 voiceInteractor, restrictedBgActivity); 1677 1678 computeLaunchingTaskFlags(); 1679 1680 computeSourceRootTask(); 1681 1682 mIntent.setFlags(mLaunchFlags); 1683 1684 final Task reusedTask = getReusableTask(); 1685 1686 // If requested, freeze the task list 1687 if (mOptions != null && mOptions.freezeRecentTasksReordering() 1688 && mSupervisor.mRecentTasks.isCallerRecents(r.launchedFromUid) 1689 && !mSupervisor.mRecentTasks.isFreezeTaskListReorderingSet()) { 1690 mFrozeTaskList = true; 1691 mSupervisor.mRecentTasks.setFreezeTaskListReordering(); 1692 } 1693 1694 // Compute if there is an existing task that should be used for. 1695 final Task targetTask = reusedTask != null ? reusedTask : computeTargetTask(); 1696 final boolean newTask = targetTask == null; 1697 mTargetTask = targetTask; 1698 1699 computeLaunchParams(r, sourceRecord, targetTask); 1700 1701 // Check if starting activity on given task or on a new task is allowed. 1702 int startResult = isAllowedToStart(r, newTask, targetTask); 1703 if (startResult != START_SUCCESS) { 1704 return startResult; 1705 } 1706 1707 final ActivityRecord targetTaskTop = newTask 1708 ? null : targetTask.getTopNonFinishingActivity(); 1709 if (targetTaskTop != null) { 1710 // Recycle the target task for this launch. 1711 startResult = recycleTask(targetTask, targetTaskTop, reusedTask, intentGrants); 1712 if (startResult != START_SUCCESS) { 1713 return startResult; 1714 } 1715 } else { 1716 mAddingToTask = true; 1717 } 1718 1719 // If the activity being launched is the same as the one currently at the top, then 1720 // we need to check if it should only be launched once. 1721 final Task topRootTask = mPreferredTaskDisplayArea.getFocusedRootTask(); 1722 if (topRootTask != null) { 1723 startResult = deliverToCurrentTopIfNeeded(topRootTask, intentGrants); 1724 if (startResult != START_SUCCESS) { 1725 return startResult; 1726 } 1727 } 1728 1729 if (mTargetRootTask == null) { 1730 mTargetRootTask = getLaunchRootTask(mStartActivity, mLaunchFlags, targetTask, mOptions); 1731 } 1732 if (newTask) { 1733 final Task taskToAffiliate = (mLaunchTaskBehind && mSourceRecord != null) 1734 ? mSourceRecord.getTask() : null; 1735 setNewTask(taskToAffiliate); 1736 } else if (mAddingToTask) { 1737 addOrReparentStartingActivity(targetTask, "adding to task"); 1738 } 1739 1740 if (!mAvoidMoveToFront && mDoResume) { 1741 mTargetRootTask.getRootTask().moveToFront("reuseOrNewTask", targetTask); 1742 if (mOptions != null) { 1743 if (mOptions.getTaskAlwaysOnTop()) { 1744 mTargetRootTask.setAlwaysOnTop(true); 1745 } 1746 } 1747 if (!mTargetRootTask.isTopRootTaskInDisplayArea() && mService.mInternal.isDreaming()) { 1748 // Launching underneath dream activity (fullscreen, always-on-top). Run the launch- 1749 // -behind transition so the Activity gets created and starts in visible state. 1750 mLaunchTaskBehind = true; 1751 r.mLaunchTaskBehind = true; 1752 } 1753 } 1754 1755 mService.mUgmInternal.grantUriPermissionUncheckedFromIntent(intentGrants, 1756 mStartActivity.getUriPermissionsLocked()); 1757 if (mStartActivity.resultTo != null && mStartActivity.resultTo.info != null) { 1758 // we need to resolve resultTo to a uid as grantImplicitAccess deals explicitly in UIDs 1759 final PackageManagerInternal pmInternal = 1760 mService.getPackageManagerInternalLocked(); 1761 final int resultToUid = pmInternal.getPackageUid( 1762 mStartActivity.resultTo.info.packageName, 0 /* flags */, 1763 mStartActivity.mUserId); 1764 pmInternal.grantImplicitAccess(mStartActivity.mUserId, mIntent, 1765 UserHandle.getAppId(mStartActivity.info.applicationInfo.uid) /*recipient*/, 1766 resultToUid /*visible*/, true /*direct*/); 1767 } 1768 if (newTask) { 1769 EventLogTags.writeWmCreateTask(mStartActivity.mUserId, 1770 mStartActivity.getTask().mTaskId); 1771 } 1772 mStartActivity.logStartActivity( 1773 EventLogTags.WM_CREATE_ACTIVITY, mStartActivity.getTask()); 1774 1775 mTargetRootTask.mLastPausedActivity = null; 1776 1777 mRootWindowContainer.startPowerModeLaunchIfNeeded( 1778 false /* forceSend */, mStartActivity); 1779 1780 mTargetRootTask.startActivityLocked(mStartActivity, 1781 topRootTask != null ? topRootTask.getTopNonFinishingActivity() : null, newTask, 1782 mKeepCurTransition, mOptions, sourceRecord); 1783 if (mDoResume) { 1784 final ActivityRecord topTaskActivity = 1785 mStartActivity.getTask().topRunningActivityLocked(); 1786 if (!mTargetRootTask.isTopActivityFocusable() 1787 || (topTaskActivity != null && topTaskActivity.isTaskOverlay() 1788 && mStartActivity != topTaskActivity)) { 1789 // If the activity is not focusable, we can't resume it, but still would like to 1790 // make sure it becomes visible as it starts (this will also trigger entry 1791 // animation). An example of this are PIP activities. 1792 // Also, we don't want to resume activities in a task that currently has an overlay 1793 // as the starting activity just needs to be in the visible paused state until the 1794 // over is removed. 1795 // Passing {@code null} as the start parameter ensures all activities are made 1796 // visible. 1797 mTargetRootTask.ensureActivitiesVisible(null /* starting */, 1798 0 /* configChanges */, !PRESERVE_WINDOWS); 1799 // Go ahead and tell window manager to execute app transition for this activity 1800 // since the app transition will not be triggered through the resume channel. 1801 mTargetRootTask.mDisplayContent.executeAppTransition(); 1802 } else { 1803 // If the target root-task was not previously focusable (previous top running 1804 // activity on that root-task was not visible) then any prior calls to move the 1805 // root-task to the will not update the focused root-task. If starting the new 1806 // activity now allows the task root-task to be focusable, then ensure that we 1807 // now update the focused root-task accordingly. 1808 if (mTargetRootTask.isTopActivityFocusable() 1809 && !mRootWindowContainer.isTopDisplayFocusedRootTask(mTargetRootTask)) { 1810 mTargetRootTask.moveToFront("startActivityInner"); 1811 } 1812 mRootWindowContainer.resumeFocusedTasksTopActivities( 1813 mTargetRootTask, mStartActivity, mOptions, mTransientLaunch); 1814 } 1815 } 1816 mRootWindowContainer.updateUserRootTask(mStartActivity.mUserId, mTargetRootTask); 1817 1818 // Update the recent tasks list immediately when the activity starts 1819 mSupervisor.mRecentTasks.add(mStartActivity.getTask()); 1820 mSupervisor.handleNonResizableTaskIfNeeded(mStartActivity.getTask(), 1821 mPreferredWindowingMode, mPreferredTaskDisplayArea, mTargetRootTask); 1822 1823 return START_SUCCESS; 1824 } 1825 computeTargetTask()1826 private Task computeTargetTask() { 1827 if (mStartActivity.resultTo == null && mInTask == null && !mAddingToTask 1828 && (mLaunchFlags & FLAG_ACTIVITY_NEW_TASK) != 0) { 1829 // A new task should be created instead of using existing one. 1830 return null; 1831 } else if (mSourceRecord != null) { 1832 return mSourceRecord.getTask(); 1833 } else if (mInTask != null) { 1834 return mInTask; 1835 } else { 1836 final Task rootTask = getLaunchRootTask(mStartActivity, mLaunchFlags, null /* task */, 1837 mOptions); 1838 final ActivityRecord top = rootTask.getTopNonFinishingActivity(); 1839 if (top != null) { 1840 return top.getTask(); 1841 } else { 1842 // Remove the root task if no activity in the root task. 1843 rootTask.removeIfPossible("computeTargetTask"); 1844 } 1845 } 1846 return null; 1847 } 1848 computeLaunchParams(ActivityRecord r, ActivityRecord sourceRecord, Task targetTask)1849 private void computeLaunchParams(ActivityRecord r, ActivityRecord sourceRecord, 1850 Task targetTask) { 1851 final Task sourceRootTask = mSourceRootTask != null ? mSourceRootTask 1852 : mRootWindowContainer.getTopDisplayFocusedRootTask(); 1853 if (sourceRootTask != null && sourceRootTask.inSplitScreenWindowingMode() 1854 && (mOptions == null 1855 || mOptions.getLaunchWindowingMode() == WINDOWING_MODE_UNDEFINED)) { 1856 int windowingMode = 1857 targetTask != null ? targetTask.getWindowingMode() : WINDOWING_MODE_UNDEFINED; 1858 if ((mLaunchFlags & FLAG_ACTIVITY_LAUNCH_ADJACENT) != 0) { 1859 if (sourceRootTask.inSplitScreenPrimaryWindowingMode()) { 1860 windowingMode = WINDOWING_MODE_SPLIT_SCREEN_SECONDARY; 1861 } else if (sourceRootTask.inSplitScreenSecondaryWindowingMode()) { 1862 windowingMode = WINDOWING_MODE_SPLIT_SCREEN_PRIMARY; 1863 } 1864 } 1865 1866 if (mOptions == null) { 1867 mOptions = ActivityOptions.makeBasic(); 1868 } 1869 mOptions.setLaunchWindowingMode(windowingMode); 1870 } 1871 1872 mSupervisor.getLaunchParamsController().calculate(targetTask, r.info.windowLayout, r, 1873 sourceRecord, mOptions, mRequest, PHASE_BOUNDS, mLaunchParams); 1874 mPreferredTaskDisplayArea = mLaunchParams.hasPreferredTaskDisplayArea() 1875 ? mLaunchParams.mPreferredTaskDisplayArea 1876 : mRootWindowContainer.getDefaultTaskDisplayArea(); 1877 mPreferredWindowingMode = mLaunchParams.mWindowingMode; 1878 } 1879 isAllowedToStart(ActivityRecord r, boolean newTask, Task targetTask)1880 private int isAllowedToStart(ActivityRecord r, boolean newTask, Task targetTask) { 1881 if (mStartActivity.packageName == null) { 1882 if (mStartActivity.resultTo != null) { 1883 mStartActivity.resultTo.sendResult(INVALID_UID, mStartActivity.resultWho, 1884 mStartActivity.requestCode, RESULT_CANCELED, 1885 null /* data */, null /* dataGrants */); 1886 } 1887 ActivityOptions.abort(mOptions); 1888 return START_CLASS_NOT_FOUND; 1889 } 1890 1891 // Do not start home activity if it cannot be launched on preferred display. We are not 1892 // doing this in ActivityTaskSupervisor#canPlaceEntityOnDisplay because it might 1893 // fallback to launch on other displays. 1894 if (r.isActivityTypeHome()) { 1895 if (!mRootWindowContainer.canStartHomeOnDisplayArea(r.info, mPreferredTaskDisplayArea, 1896 true /* allowInstrumenting */)) { 1897 Slog.w(TAG, "Cannot launch home on display area " + mPreferredTaskDisplayArea); 1898 return START_CANCELED; 1899 } 1900 } 1901 1902 // Do not allow background activity start in new task or in a task that uid is not present. 1903 // Also do not allow pinned window to start single instance activity in background, 1904 // as it will recreate the window and makes it to foreground. 1905 boolean blockBalInTask = (newTask 1906 || !targetTask.isUidPresent(mCallingUid) 1907 || (LAUNCH_SINGLE_INSTANCE == mLaunchMode && targetTask.inPinnedWindowingMode())); 1908 1909 if (mRestrictedBgActivity && blockBalInTask 1910 && handleBackgroundActivityAbort(mStartActivity)) { 1911 Slog.e(TAG, "Abort background activity starts from " + mCallingUid); 1912 return START_ABORTED; 1913 } 1914 1915 // When the flags NEW_TASK and CLEAR_TASK are set, then the task gets reused but still 1916 // needs to be a lock task mode violation since the task gets cleared out and the device 1917 // would otherwise leave the locked task. 1918 final boolean isNewClearTask = 1919 (mLaunchFlags & (FLAG_ACTIVITY_NEW_TASK | FLAG_ACTIVITY_CLEAR_TASK)) 1920 == (FLAG_ACTIVITY_NEW_TASK | FLAG_ACTIVITY_CLEAR_TASK); 1921 if (!newTask) { 1922 if (mService.getLockTaskController().isLockTaskModeViolation(targetTask, 1923 isNewClearTask)) { 1924 Slog.e(TAG, "Attempted Lock Task Mode violation mStartActivity=" + mStartActivity); 1925 return START_RETURN_LOCK_TASK_MODE_VIOLATION; 1926 } 1927 } else { 1928 if (mService.getLockTaskController().isNewTaskLockTaskModeViolation(mStartActivity)) { 1929 Slog.e(TAG, "Attempted Lock Task Mode violation mStartActivity=" + mStartActivity); 1930 return START_RETURN_LOCK_TASK_MODE_VIOLATION; 1931 } 1932 } 1933 1934 return START_SUCCESS; 1935 } 1936 1937 /** 1938 * Prepare the target task to be reused for this launch, which including: 1939 * - Position the target task on valid root task on preferred display. 1940 * - Comply to the specified activity launch flags 1941 * - Determine whether need to add a new activity on top or just brought the task to front. 1942 */ 1943 @VisibleForTesting recycleTask(Task targetTask, ActivityRecord targetTaskTop, Task reusedTask, NeededUriGrants intentGrants)1944 int recycleTask(Task targetTask, ActivityRecord targetTaskTop, Task reusedTask, 1945 NeededUriGrants intentGrants) { 1946 // Should not recycle task which is from a different user, just adding the starting 1947 // activity to the task. 1948 if (targetTask.mUserId != mStartActivity.mUserId) { 1949 mTargetRootTask = targetTask.getRootTask(); 1950 mAddingToTask = true; 1951 return START_SUCCESS; 1952 } 1953 1954 if (reusedTask != null) { 1955 if (targetTask.intent == null) { 1956 // This task was started because of movement of the activity based on 1957 // affinity... 1958 // Now that we are actually launching it, we can assign the base intent. 1959 targetTask.setIntent(mStartActivity); 1960 } else { 1961 final boolean taskOnHome = 1962 (mStartActivity.intent.getFlags() & FLAG_ACTIVITY_TASK_ON_HOME) != 0; 1963 if (taskOnHome) { 1964 targetTask.intent.addFlags(FLAG_ACTIVITY_TASK_ON_HOME); 1965 } else { 1966 targetTask.intent.removeFlags(FLAG_ACTIVITY_TASK_ON_HOME); 1967 } 1968 } 1969 } 1970 1971 mRootWindowContainer.startPowerModeLaunchIfNeeded(false /* forceSend */, 1972 targetTaskTop); 1973 1974 setTargetRootTaskIfNeeded(targetTaskTop); 1975 1976 // When there is a reused activity and the current result is a trampoline activity, 1977 // set the reused activity as the result. 1978 if (mLastStartActivityRecord != null 1979 && (mLastStartActivityRecord.finishing || mLastStartActivityRecord.noDisplay)) { 1980 mLastStartActivityRecord = targetTaskTop; 1981 } 1982 1983 if ((mStartFlags & START_FLAG_ONLY_IF_NEEDED) != 0) { 1984 // We don't need to start a new activity, and the client said not to do anything 1985 // if that is the case, so this is it! And for paranoia, make sure we have 1986 // correctly resumed the top activity. 1987 if (!mMovedToFront && mDoResume) { 1988 ProtoLog.d(WM_DEBUG_TASKS, "Bring to front target: %s from %s", mTargetRootTask, 1989 targetTaskTop); 1990 mTargetRootTask.moveToFront("intentActivityFound"); 1991 } 1992 resumeTargetRootTaskIfNeeded(); 1993 return START_RETURN_INTENT_TO_CALLER; 1994 } 1995 1996 complyActivityFlags(targetTask, 1997 reusedTask != null ? reusedTask.getTopNonFinishingActivity() : null, intentGrants); 1998 1999 if (mAddingToTask) { 2000 return START_SUCCESS; 2001 } 2002 2003 // The reusedActivity could be finishing, for example of starting an activity with 2004 // FLAG_ACTIVITY_CLEAR_TOP flag. In that case, use the top running activity in the 2005 // task instead. 2006 targetTaskTop = targetTaskTop.finishing 2007 ? targetTask.getTopNonFinishingActivity() 2008 : targetTaskTop; 2009 2010 // At this point we are certain we want the task moved to the front. If we need to dismiss 2011 // any other always-on-top root tasks, now is the time to do it. 2012 if (targetTaskTop.canTurnScreenOn() && mService.mInternal.isDreaming()) { 2013 targetTaskTop.mTaskSupervisor.wakeUp("recycleTask#turnScreenOnFlag"); 2014 } 2015 2016 if (mMovedToFront) { 2017 // We moved the task to front, use starting window to hide initial drawn delay. 2018 targetTaskTop.showStartingWindow(true /* taskSwitch */); 2019 } else if (mDoResume) { 2020 // Make sure the root task and its belonging display are moved to topmost. 2021 mTargetRootTask.moveToFront("intentActivityFound"); 2022 } 2023 // We didn't do anything... but it was needed (a.k.a., client don't use that intent!) 2024 // And for paranoia, make sure we have correctly resumed the top activity. 2025 resumeTargetRootTaskIfNeeded(); 2026 2027 mLastStartActivityRecord = targetTaskTop; 2028 return mMovedToFront ? START_TASK_TO_FRONT : START_DELIVERED_TO_TOP; 2029 } 2030 2031 /** 2032 * Check if the activity being launched is the same as the one currently at the top and it 2033 * should only be launched once. 2034 */ deliverToCurrentTopIfNeeded(Task topRootTask, NeededUriGrants intentGrants)2035 private int deliverToCurrentTopIfNeeded(Task topRootTask, NeededUriGrants intentGrants) { 2036 final ActivityRecord top = topRootTask.topRunningNonDelayedActivityLocked(mNotTop); 2037 final boolean dontStart = top != null 2038 && top.mActivityComponent.equals(mStartActivity.mActivityComponent) 2039 && top.mUserId == mStartActivity.mUserId 2040 && top.attachedToProcess() 2041 && ((mLaunchFlags & FLAG_ACTIVITY_SINGLE_TOP) != 0 2042 || LAUNCH_SINGLE_TOP == mLaunchMode) 2043 // This allows home activity to automatically launch on secondary task display area 2044 // when it was added, if home was the top activity on default task display area, 2045 // instead of sending new intent to the home activity on default display area. 2046 && (!top.isActivityTypeHome() || top.getDisplayArea() == mPreferredTaskDisplayArea); 2047 if (!dontStart) { 2048 return START_SUCCESS; 2049 } 2050 2051 // For paranoia, make sure we have correctly resumed the top activity. 2052 topRootTask.mLastPausedActivity = null; 2053 if (mDoResume) { 2054 mRootWindowContainer.resumeFocusedTasksTopActivities(); 2055 } 2056 ActivityOptions.abort(mOptions); 2057 if ((mStartFlags & START_FLAG_ONLY_IF_NEEDED) != 0) { 2058 // We don't need to start a new activity, and the client said not to do anything if 2059 // that is the case, so this is it! 2060 return START_RETURN_INTENT_TO_CALLER; 2061 } 2062 2063 if (mStartActivity.resultTo != null) { 2064 mStartActivity.resultTo.sendResult(INVALID_UID, mStartActivity.resultWho, 2065 mStartActivity.requestCode, RESULT_CANCELED, 2066 null /* data */, null /* dataGrants */); 2067 mStartActivity.resultTo = null; 2068 } 2069 2070 deliverNewIntent(top, intentGrants); 2071 2072 // Don't use mStartActivity.task to show the toast. We're not starting a new activity but 2073 // reusing 'top'. Fields in mStartActivity may not be fully initialized. 2074 mSupervisor.handleNonResizableTaskIfNeeded(top.getTask(), 2075 mLaunchParams.mWindowingMode, mPreferredTaskDisplayArea, topRootTask); 2076 2077 return START_DELIVERED_TO_TOP; 2078 } 2079 2080 /** 2081 * Applying the launching flags to the task, which might clear few or all the activities in the 2082 * task. 2083 */ complyActivityFlags(Task targetTask, ActivityRecord reusedActivity, NeededUriGrants intentGrants)2084 private void complyActivityFlags(Task targetTask, ActivityRecord reusedActivity, 2085 NeededUriGrants intentGrants) { 2086 ActivityRecord targetTaskTop = targetTask.getTopNonFinishingActivity(); 2087 final boolean resetTask = 2088 reusedActivity != null && (mLaunchFlags & FLAG_ACTIVITY_RESET_TASK_IF_NEEDED) != 0; 2089 if (resetTask) { 2090 targetTaskTop = mTargetRootTask.resetTaskIfNeeded(targetTaskTop, mStartActivity); 2091 } 2092 2093 if ((mLaunchFlags & (FLAG_ACTIVITY_NEW_TASK | FLAG_ACTIVITY_CLEAR_TASK)) 2094 == (FLAG_ACTIVITY_NEW_TASK | FLAG_ACTIVITY_CLEAR_TASK)) { 2095 // The caller has requested to completely replace any existing task with its new 2096 // activity. Well that should not be too hard... 2097 // Note: we must persist the {@link Task} first as intentActivity could be 2098 // removed from calling performClearTaskLocked (For example, if it is being brought out 2099 // of history or if it is finished immediately), thus disassociating the task. Also note 2100 // that mReuseTask is reset as a result of {@link Task#performClearTaskLocked} 2101 // launching another activity. 2102 targetTask.performClearTaskLocked(); 2103 targetTask.setIntent(mStartActivity); 2104 mAddingToTask = true; 2105 } else if ((mLaunchFlags & FLAG_ACTIVITY_CLEAR_TOP) != 0 2106 || isDocumentLaunchesIntoExisting(mLaunchFlags) 2107 || isLaunchModeOneOf(LAUNCH_SINGLE_INSTANCE, LAUNCH_SINGLE_TASK, 2108 LAUNCH_SINGLE_INSTANCE_PER_TASK)) { 2109 // In this situation we want to remove all activities from the task up to the one 2110 // being started. In most cases this means we are resetting the task to its initial 2111 // state. 2112 final ActivityRecord top = targetTask.performClearTaskForReuseLocked(mStartActivity, 2113 mLaunchFlags); 2114 2115 if (top != null) { 2116 if (top.isRootOfTask()) { 2117 // Activity aliases may mean we use different intents for the top activity, 2118 // so make sure the task now has the identity of the new intent. 2119 top.getTask().setIntent(mStartActivity); 2120 } 2121 deliverNewIntent(top, intentGrants); 2122 } else { 2123 // A special case: we need to start the activity because it is not currently 2124 // running, and the caller has asked to clear the current task to have this 2125 // activity at the top. 2126 mAddingToTask = true; 2127 if (targetTask.getRootTask() == null) { 2128 // Target root task got cleared when we all activities were removed above. 2129 // Go ahead and reset it. 2130 mTargetRootTask = getLaunchRootTask(mStartActivity, mLaunchFlags, 2131 null /* task */, mOptions); 2132 mTargetRootTask.addChild(targetTask, !mLaunchTaskBehind /* toTop */, 2133 (mStartActivity.info.flags & FLAG_SHOW_FOR_ALL_USERS) != 0); 2134 } 2135 } 2136 } else if ((mLaunchFlags & FLAG_ACTIVITY_CLEAR_TOP) == 0 && !mAddingToTask 2137 && (mLaunchFlags & FLAG_ACTIVITY_REORDER_TO_FRONT) != 0) { 2138 // In this case, we are launching an activity in our own task that may 2139 // already be running somewhere in the history, and we want to shuffle it to 2140 // the front of the root task if so. 2141 final ActivityRecord act = 2142 targetTask.findActivityInHistory(mStartActivity.mActivityComponent); 2143 if (act != null) { 2144 final Task task = act.getTask(); 2145 task.moveActivityToFrontLocked(act); 2146 act.updateOptionsLocked(mOptions); 2147 deliverNewIntent(act, intentGrants); 2148 mTargetRootTask.mLastPausedActivity = null; 2149 } else { 2150 mAddingToTask = true; 2151 } 2152 } else if (mStartActivity.mActivityComponent.equals(targetTask.realActivity)) { 2153 if (targetTask == mInTask) { 2154 // In this case we are bringing up an existing activity from a recent task. We 2155 // don't need to add a new activity instance on top. 2156 } else if (((mLaunchFlags & FLAG_ACTIVITY_SINGLE_TOP) != 0 2157 || LAUNCH_SINGLE_TOP == mLaunchMode) 2158 && targetTaskTop.mActivityComponent.equals(mStartActivity.mActivityComponent) 2159 && mStartActivity.resultTo == null) { 2160 // In this case the top activity on the task is the same as the one being launched, 2161 // so we take that as a request to bring the task to the foreground. If the top 2162 // activity in the task is the root activity, deliver this new intent to it if it 2163 // desires. 2164 if (targetTaskTop.isRootOfTask()) { 2165 targetTaskTop.getTask().setIntent(mStartActivity); 2166 } 2167 deliverNewIntent(targetTaskTop, intentGrants); 2168 } else if (!targetTask.isSameIntentFilter(mStartActivity)) { 2169 // In this case we are launching the root activity of the task, but with a 2170 // different intent. We should start a new instance on top. 2171 mAddingToTask = true; 2172 } else if (reusedActivity == null) { 2173 mAddingToTask = true; 2174 } 2175 } else if (!resetTask) { 2176 // In this case an activity is being launched in to an existing task, without 2177 // resetting that task. This is typically the situation of launching an activity 2178 // from a notification or shortcut. We want to place the new activity on top of the 2179 // current task. 2180 mAddingToTask = true; 2181 } else if (!targetTask.rootWasReset) { 2182 // In this case we are launching into an existing task that has not yet been started 2183 // from its front door. The current task has been brought to the front. Ideally, 2184 // we'd probably like to place this new task at the bottom of its root task, but that's 2185 // a little hard to do with the current organization of the code so for now we'll 2186 // just drop it. 2187 targetTask.setIntent(mStartActivity); 2188 } 2189 } 2190 2191 /** 2192 * Resets the {@link ActivityStarter} state. 2193 * @param clearRequest whether the request should be reset to default values. 2194 */ reset(boolean clearRequest)2195 void reset(boolean clearRequest) { 2196 mStartActivity = null; 2197 mIntent = null; 2198 mCallingUid = -1; 2199 mOptions = null; 2200 mRestrictedBgActivity = false; 2201 2202 mLaunchTaskBehind = false; 2203 mLaunchFlags = 0; 2204 mLaunchMode = INVALID_LAUNCH_MODE; 2205 2206 mLaunchParams.reset(); 2207 2208 mNotTop = null; 2209 mDoResume = false; 2210 mStartFlags = 0; 2211 mSourceRecord = null; 2212 mPreferredTaskDisplayArea = null; 2213 mPreferredWindowingMode = WINDOWING_MODE_UNDEFINED; 2214 2215 mInTask = null; 2216 mAddingToTask = false; 2217 mReuseTask = null; 2218 2219 mNewTaskInfo = null; 2220 mNewTaskIntent = null; 2221 mSourceRootTask = null; 2222 2223 mTargetRootTask = null; 2224 mTargetTask = null; 2225 mMovedToFront = false; 2226 mNoAnimation = false; 2227 mKeepCurTransition = false; 2228 mAvoidMoveToFront = false; 2229 mFrozeTaskList = false; 2230 mTransientLaunch = false; 2231 2232 mVoiceSession = null; 2233 mVoiceInteractor = null; 2234 2235 mIntentDelivered = false; 2236 2237 if (clearRequest) { 2238 mRequest.reset(); 2239 } 2240 } 2241 setInitialState(ActivityRecord r, ActivityOptions options, Task inTask, boolean doResume, int startFlags, ActivityRecord sourceRecord, IVoiceInteractionSession voiceSession, IVoiceInteractor voiceInteractor, boolean restrictedBgActivity)2242 private void setInitialState(ActivityRecord r, ActivityOptions options, Task inTask, 2243 boolean doResume, int startFlags, ActivityRecord sourceRecord, 2244 IVoiceInteractionSession voiceSession, IVoiceInteractor voiceInteractor, 2245 boolean restrictedBgActivity) { 2246 reset(false /* clearRequest */); 2247 2248 mStartActivity = r; 2249 mIntent = r.intent; 2250 mOptions = options; 2251 mCallingUid = r.launchedFromUid; 2252 mSourceRecord = sourceRecord; 2253 mVoiceSession = voiceSession; 2254 mVoiceInteractor = voiceInteractor; 2255 mRestrictedBgActivity = restrictedBgActivity; 2256 2257 mLaunchParams.reset(); 2258 2259 // Preferred display id is the only state we need for now and it could be updated again 2260 // after we located a reusable task (which might be resided in another display). 2261 mSupervisor.getLaunchParamsController().calculate(inTask, r.info.windowLayout, r, 2262 sourceRecord, options, mRequest, PHASE_DISPLAY, mLaunchParams); 2263 mPreferredTaskDisplayArea = mLaunchParams.hasPreferredTaskDisplayArea() 2264 ? mLaunchParams.mPreferredTaskDisplayArea 2265 : mRootWindowContainer.getDefaultTaskDisplayArea(); 2266 mPreferredWindowingMode = mLaunchParams.mWindowingMode; 2267 2268 mLaunchMode = r.launchMode; 2269 2270 mLaunchFlags = adjustLaunchFlagsToDocumentMode( 2271 r, LAUNCH_SINGLE_INSTANCE == mLaunchMode, 2272 LAUNCH_SINGLE_TASK == mLaunchMode, mIntent.getFlags()); 2273 mLaunchTaskBehind = r.mLaunchTaskBehind 2274 && !isLaunchModeOneOf(LAUNCH_SINGLE_TASK, LAUNCH_SINGLE_INSTANCE) 2275 && (mLaunchFlags & FLAG_ACTIVITY_NEW_DOCUMENT) != 0; 2276 2277 if (mLaunchMode == LAUNCH_SINGLE_INSTANCE_PER_TASK) { 2278 // Adding NEW_TASK flag for singleInstancePerTask launch mode activity, so that the 2279 // activity won't be launched in source record's task. 2280 mLaunchFlags |= FLAG_ACTIVITY_NEW_TASK; 2281 } 2282 2283 sendNewTaskResultRequestIfNeeded(); 2284 2285 if ((mLaunchFlags & FLAG_ACTIVITY_NEW_DOCUMENT) != 0 && r.resultTo == null) { 2286 mLaunchFlags |= FLAG_ACTIVITY_NEW_TASK; 2287 } 2288 2289 // If we are actually going to launch in to a new task, there are some cases where 2290 // we further want to do multiple task. 2291 if ((mLaunchFlags & FLAG_ACTIVITY_NEW_TASK) != 0) { 2292 if (mLaunchTaskBehind 2293 || r.info.documentLaunchMode == DOCUMENT_LAUNCH_ALWAYS) { 2294 mLaunchFlags |= FLAG_ACTIVITY_MULTIPLE_TASK; 2295 } 2296 } 2297 2298 // We'll invoke onUserLeaving before onPause only if the launching 2299 // activity did not explicitly state that this is an automated launch. 2300 mSupervisor.mUserLeaving = (mLaunchFlags & FLAG_ACTIVITY_NO_USER_ACTION) == 0; 2301 if (DEBUG_USER_LEAVING) Slog.v(TAG_USER_LEAVING, 2302 "startActivity() => mUserLeaving=" + mSupervisor.mUserLeaving); 2303 2304 // If the caller has asked not to resume at this point, we make note 2305 // of this in the record so that we can skip it when trying to find 2306 // the top running activity. 2307 mDoResume = doResume; 2308 if (!doResume || !r.okToShowLocked() || mLaunchTaskBehind) { 2309 r.delayedResume = true; 2310 mDoResume = false; 2311 } 2312 2313 if (mOptions != null) { 2314 if (mOptions.getLaunchTaskId() != INVALID_TASK_ID && mOptions.getTaskOverlay()) { 2315 r.setTaskOverlay(true); 2316 if (!mOptions.canTaskOverlayResume()) { 2317 final Task task = mRootWindowContainer.anyTaskForId( 2318 mOptions.getLaunchTaskId()); 2319 final ActivityRecord top = task != null 2320 ? task.getTopNonFinishingActivity() : null; 2321 if (top != null && !top.isState(RESUMED)) { 2322 2323 // The caller specifies that we'd like to be avoided to be moved to the 2324 // front, so be it! 2325 mDoResume = false; 2326 mAvoidMoveToFront = true; 2327 } 2328 } 2329 } else if (mOptions.getAvoidMoveToFront()) { 2330 mDoResume = false; 2331 mAvoidMoveToFront = true; 2332 } 2333 mTransientLaunch = mOptions.getTransientLaunch(); 2334 mTargetRootTask = Task.fromWindowContainerToken(mOptions.getLaunchRootTask()); 2335 } 2336 2337 mNotTop = (mLaunchFlags & FLAG_ACTIVITY_PREVIOUS_IS_TOP) != 0 ? sourceRecord : null; 2338 2339 mInTask = inTask; 2340 // In some flows in to this function, we retrieve the task record and hold on to it 2341 // without a lock before calling back in to here... so the task at this point may 2342 // not actually be in recents. Check for that, and if it isn't in recents just 2343 // consider it invalid. 2344 if (inTask != null && !inTask.inRecents) { 2345 Slog.w(TAG, "Starting activity in task not in recents: " + inTask); 2346 mInTask = null; 2347 } 2348 2349 mStartFlags = startFlags; 2350 // If the onlyIfNeeded flag is set, then we can do this if the activity being launched 2351 // is the same as the one making the call... or, as a special case, if we do not know 2352 // the caller then we count the current top activity as the caller. 2353 if ((startFlags & START_FLAG_ONLY_IF_NEEDED) != 0) { 2354 ActivityRecord checkedCaller = sourceRecord; 2355 if (checkedCaller == null) { 2356 Task topFocusedRootTask = mRootWindowContainer.getTopDisplayFocusedRootTask(); 2357 if (topFocusedRootTask != null) { 2358 checkedCaller = topFocusedRootTask.topRunningNonDelayedActivityLocked(mNotTop); 2359 } 2360 } 2361 if (checkedCaller == null 2362 || !checkedCaller.mActivityComponent.equals(r.mActivityComponent)) { 2363 // Caller is not the same as launcher, so always needed. 2364 mStartFlags &= ~START_FLAG_ONLY_IF_NEEDED; 2365 } 2366 } 2367 2368 mNoAnimation = (mLaunchFlags & FLAG_ACTIVITY_NO_ANIMATION) != 0; 2369 2370 if (mRestrictedBgActivity && !mService.isBackgroundActivityStartsEnabled()) { 2371 mAvoidMoveToFront = true; 2372 mDoResume = false; 2373 } 2374 } 2375 sendNewTaskResultRequestIfNeeded()2376 private void sendNewTaskResultRequestIfNeeded() { 2377 if (mStartActivity.resultTo != null && (mLaunchFlags & FLAG_ACTIVITY_NEW_TASK) != 0) { 2378 // For whatever reason this activity is being launched into a new task... 2379 // yet the caller has requested a result back. Well, that is pretty messed up, 2380 // so instead immediately send back a cancel and let the new task continue launched 2381 // as normal without a dependency on its originator. 2382 Slog.w(TAG, "Activity is launching as a new task, so cancelling activity result."); 2383 mStartActivity.resultTo.sendResult(INVALID_UID, mStartActivity.resultWho, 2384 mStartActivity.requestCode, RESULT_CANCELED, 2385 null /* data */, null /* dataGrants */); 2386 mStartActivity.resultTo = null; 2387 } 2388 } 2389 computeLaunchingTaskFlags()2390 private void computeLaunchingTaskFlags() { 2391 // If the caller is not coming from another activity, but has given us an explicit task into 2392 // which they would like us to launch the new activity, then let's see about doing that. 2393 if (mSourceRecord == null && mInTask != null && mInTask.getRootTask() != null) { 2394 final Intent baseIntent = mInTask.getBaseIntent(); 2395 final ActivityRecord root = mInTask.getRootActivity(); 2396 if (baseIntent == null) { 2397 ActivityOptions.abort(mOptions); 2398 throw new IllegalArgumentException("Launching into task without base intent: " 2399 + mInTask); 2400 } 2401 2402 // If this task is empty, then we are adding the first activity -- it 2403 // determines the root, and must be launching as a NEW_TASK. 2404 if (isLaunchModeOneOf(LAUNCH_SINGLE_INSTANCE, LAUNCH_SINGLE_TASK)) { 2405 if (!baseIntent.getComponent().equals(mStartActivity.intent.getComponent())) { 2406 ActivityOptions.abort(mOptions); 2407 throw new IllegalArgumentException("Trying to launch singleInstance/Task " 2408 + mStartActivity + " into different task " + mInTask); 2409 } 2410 if (root != null) { 2411 ActivityOptions.abort(mOptions); 2412 throw new IllegalArgumentException("Caller with mInTask " + mInTask 2413 + " has root " + root + " but target is singleInstance/Task"); 2414 } 2415 } 2416 2417 // If task is empty, then adopt the interesting intent launch flags in to the 2418 // activity being started. 2419 if (root == null) { 2420 final int flagsOfInterest = FLAG_ACTIVITY_NEW_TASK | FLAG_ACTIVITY_MULTIPLE_TASK 2421 | FLAG_ACTIVITY_NEW_DOCUMENT | FLAG_ACTIVITY_RETAIN_IN_RECENTS; 2422 mLaunchFlags = (mLaunchFlags & ~flagsOfInterest) 2423 | (baseIntent.getFlags() & flagsOfInterest); 2424 mIntent.setFlags(mLaunchFlags); 2425 mInTask.setIntent(mStartActivity); 2426 mAddingToTask = true; 2427 2428 // If the task is not empty and the caller is asking to start it as the root of 2429 // a new task, then we don't actually want to start this on the task. We will 2430 // bring the task to the front, and possibly give it a new intent. 2431 } else if ((mLaunchFlags & FLAG_ACTIVITY_NEW_TASK) != 0) { 2432 mAddingToTask = false; 2433 2434 } else { 2435 mAddingToTask = true; 2436 } 2437 2438 mReuseTask = mInTask; 2439 } else { 2440 mInTask = null; 2441 // Launch ResolverActivity in the source task, so that it stays in the task bounds 2442 // when in freeform workspace. 2443 // Also put noDisplay activities in the source task. These by itself can be placed 2444 // in any task/root-task, however it could launch other activities like 2445 // ResolverActivity, and we want those to stay in the original task. 2446 if ((mStartActivity.isResolverOrDelegateActivity() || mStartActivity.noDisplay) 2447 && mSourceRecord != null && mSourceRecord.inFreeformWindowingMode()) { 2448 mAddingToTask = true; 2449 } 2450 } 2451 2452 if (mInTask == null) { 2453 if (mSourceRecord == null) { 2454 // This activity is not being started from another... in this 2455 // case we -always- start a new task. 2456 if ((mLaunchFlags & FLAG_ACTIVITY_NEW_TASK) == 0 && mInTask == null) { 2457 Slog.w(TAG, "startActivity called from non-Activity context; forcing " + 2458 "Intent.FLAG_ACTIVITY_NEW_TASK for: " + mIntent); 2459 mLaunchFlags |= FLAG_ACTIVITY_NEW_TASK; 2460 } 2461 } else if (mSourceRecord.launchMode == LAUNCH_SINGLE_INSTANCE) { 2462 // The original activity who is starting us is running as a single 2463 // instance... this new activity it is starting must go on its 2464 // own task. 2465 mLaunchFlags |= FLAG_ACTIVITY_NEW_TASK; 2466 } else if (isLaunchModeOneOf(LAUNCH_SINGLE_INSTANCE, LAUNCH_SINGLE_TASK)) { 2467 // The activity being started is a single instance... it always 2468 // gets launched into its own task. 2469 mLaunchFlags |= FLAG_ACTIVITY_NEW_TASK; 2470 } 2471 } 2472 } 2473 computeSourceRootTask()2474 private void computeSourceRootTask() { 2475 if (mSourceRecord == null) { 2476 mSourceRootTask = null; 2477 return; 2478 } 2479 if (!mSourceRecord.finishing) { 2480 mSourceRootTask = mSourceRecord.getRootTask(); 2481 return; 2482 } 2483 2484 // If the source is finishing, we can't further count it as our source. This is because the 2485 // task it is associated with may now be empty and on its way out, so we don't want to 2486 // blindly throw it in to that task. Instead we will take the NEW_TASK flow and try to find 2487 // a task for it. But save the task information so it can be used when creating the new task. 2488 if ((mLaunchFlags & FLAG_ACTIVITY_NEW_TASK) == 0) { 2489 Slog.w(TAG, "startActivity called from finishing " + mSourceRecord 2490 + "; forcing " + "Intent.FLAG_ACTIVITY_NEW_TASK for: " + mIntent); 2491 mLaunchFlags |= FLAG_ACTIVITY_NEW_TASK; 2492 mNewTaskInfo = mSourceRecord.info; 2493 2494 // It is not guaranteed that the source record will have a task associated with it. For, 2495 // example, if this method is being called for processing a pending activity launch, it 2496 // is possible that the activity has been removed from the task after the launch was 2497 // enqueued. 2498 final Task sourceTask = mSourceRecord.getTask(); 2499 mNewTaskIntent = sourceTask != null ? sourceTask.intent : null; 2500 } 2501 mSourceRecord = null; 2502 mSourceRootTask = null; 2503 } 2504 2505 /** 2506 * Decide whether the new activity should be inserted into an existing task. Returns null 2507 * if not or an ActivityRecord with the task into which the new activity should be added. 2508 */ getReusableTask()2509 private Task getReusableTask() { 2510 // If a target task is specified, try to reuse that one 2511 if (mOptions != null && mOptions.getLaunchTaskId() != INVALID_TASK_ID) { 2512 Task launchTask = mRootWindowContainer.anyTaskForId(mOptions.getLaunchTaskId()); 2513 if (launchTask != null) { 2514 return launchTask; 2515 } 2516 return null; 2517 } 2518 2519 // We may want to try to place the new activity in to an existing task. We always 2520 // do this if the target activity is singleTask or singleInstance; we will also do 2521 // this if NEW_TASK has been requested, and there is not an additional qualifier telling 2522 // us to still place it in a new task: multi task, always doc mode, or being asked to 2523 // launch this as a new task behind the current one. 2524 boolean putIntoExistingTask = ((mLaunchFlags & FLAG_ACTIVITY_NEW_TASK) != 0 && 2525 (mLaunchFlags & FLAG_ACTIVITY_MULTIPLE_TASK) == 0) 2526 || isLaunchModeOneOf(LAUNCH_SINGLE_INSTANCE, LAUNCH_SINGLE_TASK); 2527 // If bring to front is requested, and no result is requested and we have not been given 2528 // an explicit task to launch in to, and we can find a task that was started with this 2529 // same component, then instead of launching bring that one to the front. 2530 putIntoExistingTask &= mInTask == null && mStartActivity.resultTo == null; 2531 ActivityRecord intentActivity = null; 2532 if (putIntoExistingTask) { 2533 if (LAUNCH_SINGLE_INSTANCE == mLaunchMode) { 2534 // There can be one and only one instance of single instance activity in the 2535 // history, and it is always in its own unique task, so we do a special search. 2536 intentActivity = mRootWindowContainer.findActivity(mIntent, mStartActivity.info, 2537 mStartActivity.isActivityTypeHome()); 2538 } else if ((mLaunchFlags & FLAG_ACTIVITY_LAUNCH_ADJACENT) != 0) { 2539 // For the launch adjacent case we only want to put the activity in an existing 2540 // task if the activity already exists in the history. 2541 intentActivity = mRootWindowContainer.findActivity(mIntent, mStartActivity.info, 2542 !(LAUNCH_SINGLE_TASK == mLaunchMode)); 2543 } else { 2544 // Otherwise find the best task to put the activity in. 2545 intentActivity = 2546 mRootWindowContainer.findTask(mStartActivity, mPreferredTaskDisplayArea); 2547 } 2548 } 2549 2550 if (intentActivity != null && mLaunchMode == LAUNCH_SINGLE_INSTANCE_PER_TASK 2551 && !intentActivity.getTask().getRootActivity().mActivityComponent.equals( 2552 mStartActivity.mActivityComponent)) { 2553 // The task could be selected due to same task affinity. Do not reuse the task while 2554 // starting the singleInstancePerTask activity if it is not the task root activity. 2555 intentActivity = null; 2556 } 2557 2558 if (intentActivity != null 2559 && (mStartActivity.isActivityTypeHome() || intentActivity.isActivityTypeHome()) 2560 && intentActivity.getDisplayArea() != mPreferredTaskDisplayArea) { 2561 // Do not reuse home activity on other display areas. 2562 intentActivity = null; 2563 } 2564 2565 return intentActivity != null ? intentActivity.getTask() : null; 2566 } 2567 2568 /** 2569 * Figure out which task and activity to bring to front when we have found an existing matching 2570 * activity record in history. May also clear the task if needed. 2571 * @param intentActivity Existing matching activity. 2572 * @return {@link ActivityRecord} brought to front. 2573 */ setTargetRootTaskIfNeeded(ActivityRecord intentActivity)2574 private void setTargetRootTaskIfNeeded(ActivityRecord intentActivity) { 2575 mTargetRootTask = intentActivity.getRootTask(); 2576 mTargetRootTask.mLastPausedActivity = null; 2577 Task intentTask = intentActivity.getTask(); 2578 // If the target task is not in the front, then we need to bring it to the front... 2579 // except... well, with SINGLE_TASK_LAUNCH it's not entirely clear. We'd like to have 2580 // the same behavior as if a new instance was being started, which means not bringing it 2581 // to the front if the caller is not itself in the front. 2582 final boolean differentTopTask; 2583 if (mTargetRootTask.getDisplayArea() == mPreferredTaskDisplayArea) { 2584 final Task focusRootTask = mTargetRootTask.mDisplayContent.getFocusedRootTask(); 2585 final ActivityRecord curTop = (focusRootTask == null) 2586 ? null : focusRootTask.topRunningNonDelayedActivityLocked(mNotTop); 2587 final Task topTask = curTop != null ? curTop.getTask() : null; 2588 differentTopTask = topTask != intentTask 2589 || (focusRootTask != null && topTask != focusRootTask.getTopMostTask()); 2590 } else { 2591 // The existing task should always be different from those in other displays. 2592 differentTopTask = true; 2593 } 2594 2595 if (differentTopTask && !mAvoidMoveToFront) { 2596 mStartActivity.intent.addFlags(Intent.FLAG_ACTIVITY_BROUGHT_TO_FRONT); 2597 if (mSourceRecord == null || (mSourceRootTask.getTopNonFinishingActivity() != null 2598 && mSourceRootTask.getTopNonFinishingActivity().getTask() 2599 == mSourceRecord.getTask())) { 2600 // We really do want to push this one into the user's face, right now. 2601 if (mLaunchTaskBehind && mSourceRecord != null) { 2602 intentActivity.setTaskToAffiliateWith(mSourceRecord.getTask()); 2603 } 2604 2605 final Task launchRootTask = getLaunchRootTask(mStartActivity, mLaunchFlags, 2606 intentTask, mOptions); 2607 if (launchRootTask == null || launchRootTask == mTargetRootTask) { 2608 // TODO(b/151572268): Figure out a better way to move tasks in above 2-levels 2609 // tasks hierarchies. 2610 if (mTargetRootTask != intentTask 2611 && mTargetRootTask != intentTask.getParent().asTask()) { 2612 intentTask.getParent().positionChildAt(POSITION_TOP, intentTask, 2613 false /* includingParents */); 2614 intentTask = intentTask.getParent().asTask(); 2615 } 2616 // If the task is in multi-windowing mode, the activity may already be on 2617 // the top (visible to user but not the global top), then the result code 2618 // should be START_DELIVERED_TO_TOP instead of START_TASK_TO_FRONT. 2619 final boolean wasTopOfVisibleRootTask = intentActivity.mVisibleRequested 2620 && intentActivity == mTargetRootTask.topRunningActivity(); 2621 // We only want to move to the front, if we aren't going to launch on a 2622 // different root task. If we launch on a different root task, we will put the 2623 // task on top there. 2624 // Defer resuming the top activity while moving task to top, since the 2625 // current task-top activity may not be the activity that should be resumed. 2626 mTargetRootTask.moveTaskToFront(intentTask, mNoAnimation, mOptions, 2627 mStartActivity.appTimeTracker, DEFER_RESUME, 2628 "bringingFoundTaskToFront"); 2629 mMovedToFront = !wasTopOfVisibleRootTask; 2630 } else { 2631 intentTask.reparent(launchRootTask, ON_TOP, REPARENT_MOVE_ROOT_TASK_TO_FRONT, 2632 ANIMATE, DEFER_RESUME, "reparentToTargetRootTask"); 2633 mMovedToFront = true; 2634 } 2635 mOptions = null; 2636 } 2637 } 2638 2639 if (mPreferredWindowingMode != WINDOWING_MODE_UNDEFINED 2640 && intentTask.getWindowingMode() != mPreferredWindowingMode) { 2641 intentTask.setWindowingMode(mPreferredWindowingMode); 2642 } 2643 2644 // Update the target's launch cookie to those specified in the options if set 2645 if (mStartActivity.mLaunchCookie != null) { 2646 intentActivity.mLaunchCookie = mStartActivity.mLaunchCookie; 2647 } 2648 2649 // Need to update mTargetRootTask because if task was moved out of it, the original root 2650 // task may be destroyed. 2651 mTargetRootTask = intentActivity.getRootTask(); 2652 mSupervisor.handleNonResizableTaskIfNeeded(intentTask, WINDOWING_MODE_UNDEFINED, 2653 mRootWindowContainer.getDefaultTaskDisplayArea(), mTargetRootTask); 2654 } 2655 resumeTargetRootTaskIfNeeded()2656 private void resumeTargetRootTaskIfNeeded() { 2657 if (mDoResume) { 2658 final ActivityRecord next = mTargetRootTask.topRunningActivity( 2659 true /* focusableOnly */); 2660 if (next != null) { 2661 next.setCurrentLaunchCanTurnScreenOn(true); 2662 } 2663 if (mTargetRootTask.isFocusable()) { 2664 mRootWindowContainer.resumeFocusedTasksTopActivities(mTargetRootTask, null, 2665 mOptions, mTransientLaunch); 2666 } else { 2667 mRootWindowContainer.ensureActivitiesVisible(null, 0, !PRESERVE_WINDOWS); 2668 } 2669 } else { 2670 ActivityOptions.abort(mOptions); 2671 } 2672 mRootWindowContainer.updateUserRootTask(mStartActivity.mUserId, mTargetRootTask); 2673 } 2674 setNewTask(Task taskToAffiliate)2675 private void setNewTask(Task taskToAffiliate) { 2676 final boolean toTop = !mLaunchTaskBehind && !mAvoidMoveToFront; 2677 final Task task = mTargetRootTask.reuseOrCreateTask( 2678 mNewTaskInfo != null ? mNewTaskInfo : mStartActivity.info, 2679 mNewTaskIntent != null ? mNewTaskIntent : mIntent, mVoiceSession, 2680 mVoiceInteractor, toTop, mStartActivity, mSourceRecord, mOptions); 2681 mService.getTransitionController().collectExistenceChange(task); 2682 addOrReparentStartingActivity(task, "setTaskFromReuseOrCreateNewTask - mReuseTask"); 2683 2684 ProtoLog.v(WM_DEBUG_TASKS, "Starting new activity %s in new task %s", 2685 mStartActivity, mStartActivity.getTask()); 2686 2687 if (taskToAffiliate != null) { 2688 mStartActivity.setTaskToAffiliateWith(taskToAffiliate); 2689 } 2690 } 2691 deliverNewIntent(ActivityRecord activity, NeededUriGrants intentGrants)2692 private void deliverNewIntent(ActivityRecord activity, NeededUriGrants intentGrants) { 2693 if (mIntentDelivered) { 2694 return; 2695 } 2696 2697 activity.logStartActivity(EventLogTags.WM_NEW_INTENT, activity.getTask()); 2698 activity.deliverNewIntentLocked(mCallingUid, mStartActivity.intent, intentGrants, 2699 mStartActivity.launchedFromPackage); 2700 mIntentDelivered = true; 2701 } 2702 addOrReparentStartingActivity(Task parent, String reason)2703 private void addOrReparentStartingActivity(Task parent, String reason) { 2704 if (mStartActivity.getTask() == null || mStartActivity.getTask() == parent) { 2705 parent.addChild(mStartActivity); 2706 } else { 2707 mStartActivity.reparent(parent, parent.getChildCount() /* top */, reason); 2708 } 2709 } 2710 adjustLaunchFlagsToDocumentMode(ActivityRecord r, boolean launchSingleInstance, boolean launchSingleTask, int launchFlags)2711 private int adjustLaunchFlagsToDocumentMode(ActivityRecord r, boolean launchSingleInstance, 2712 boolean launchSingleTask, int launchFlags) { 2713 if ((launchFlags & Intent.FLAG_ACTIVITY_NEW_DOCUMENT) != 0 && 2714 (launchSingleInstance || launchSingleTask)) { 2715 // We have a conflict between the Intent and the Activity manifest, manifest wins. 2716 Slog.i(TAG, "Ignoring FLAG_ACTIVITY_NEW_DOCUMENT, launchMode is " + 2717 "\"singleInstance\" or \"singleTask\""); 2718 launchFlags &= 2719 ~(Intent.FLAG_ACTIVITY_NEW_DOCUMENT | FLAG_ACTIVITY_MULTIPLE_TASK); 2720 } else { 2721 switch (r.info.documentLaunchMode) { 2722 case ActivityInfo.DOCUMENT_LAUNCH_NONE: 2723 break; 2724 case ActivityInfo.DOCUMENT_LAUNCH_INTO_EXISTING: 2725 launchFlags |= Intent.FLAG_ACTIVITY_NEW_DOCUMENT; 2726 break; 2727 case ActivityInfo.DOCUMENT_LAUNCH_ALWAYS: 2728 launchFlags |= Intent.FLAG_ACTIVITY_NEW_DOCUMENT; 2729 break; 2730 case ActivityInfo.DOCUMENT_LAUNCH_NEVER: 2731 if (mLaunchMode == LAUNCH_SINGLE_INSTANCE_PER_TASK) { 2732 // Remove MULTIPLE_TASK flag along with NEW_DOCUMENT only if NEW_DOCUMENT 2733 // is set, otherwise we still want to keep the MULTIPLE_TASK flag (if 2734 // any) for singleInstancePerTask that the multiple tasks can be created, 2735 // or a singleInstancePerTask activity is basically the same as a 2736 // singleTask activity when documentLaunchMode set to never. 2737 if ((launchFlags & Intent.FLAG_ACTIVITY_NEW_DOCUMENT) != 0) { 2738 launchFlags &= ~(Intent.FLAG_ACTIVITY_NEW_DOCUMENT 2739 | FLAG_ACTIVITY_MULTIPLE_TASK); 2740 } 2741 } else { 2742 // TODO(b/184903976): Should FLAG_ACTIVITY_MULTIPLE_TASK always be 2743 // removed for document-never activity? 2744 launchFlags &= 2745 ~(Intent.FLAG_ACTIVITY_NEW_DOCUMENT | FLAG_ACTIVITY_MULTIPLE_TASK); 2746 } 2747 break; 2748 } 2749 } 2750 return launchFlags; 2751 } 2752 getLaunchRootTask(ActivityRecord r, int launchFlags, Task task, ActivityOptions aOptions)2753 private Task getLaunchRootTask(ActivityRecord r, int launchFlags, Task task, 2754 ActivityOptions aOptions) { 2755 // We are reusing a task, keep the root task! 2756 if (mReuseTask != null) { 2757 return mReuseTask.getRootTask(); 2758 } 2759 2760 final boolean onTop = 2761 (aOptions == null || !aOptions.getAvoidMoveToFront()) && !mLaunchTaskBehind; 2762 return mRootWindowContainer.getLaunchRootTask(r, aOptions, task, mSourceRootTask, onTop, 2763 mLaunchParams, launchFlags, mRequest.realCallingPid, mRequest.realCallingUid); 2764 } 2765 isLaunchModeOneOf(int mode1, int mode2)2766 private boolean isLaunchModeOneOf(int mode1, int mode2) { 2767 return mode1 == mLaunchMode || mode2 == mLaunchMode; 2768 } 2769 isLaunchModeOneOf(int mode1, int mode2, int mode3)2770 private boolean isLaunchModeOneOf(int mode1, int mode2, int mode3) { 2771 return mode1 == mLaunchMode || mode2 == mLaunchMode || mode3 == mLaunchMode; 2772 } 2773 isDocumentLaunchesIntoExisting(int flags)2774 static boolean isDocumentLaunchesIntoExisting(int flags) { 2775 return (flags & Intent.FLAG_ACTIVITY_NEW_DOCUMENT) != 0 && 2776 (flags & Intent.FLAG_ACTIVITY_MULTIPLE_TASK) == 0; 2777 } 2778 setIntent(Intent intent)2779 ActivityStarter setIntent(Intent intent) { 2780 mRequest.intent = intent; 2781 return this; 2782 } 2783 getIntent()2784 Intent getIntent() { 2785 return mRequest.intent; 2786 } 2787 setIntentGrants(NeededUriGrants intentGrants)2788 ActivityStarter setIntentGrants(NeededUriGrants intentGrants) { 2789 mRequest.intentGrants = intentGrants; 2790 return this; 2791 } 2792 setReason(String reason)2793 ActivityStarter setReason(String reason) { 2794 mRequest.reason = reason; 2795 return this; 2796 } 2797 setCaller(IApplicationThread caller)2798 ActivityStarter setCaller(IApplicationThread caller) { 2799 mRequest.caller = caller; 2800 return this; 2801 } 2802 setResolvedType(String type)2803 ActivityStarter setResolvedType(String type) { 2804 mRequest.resolvedType = type; 2805 return this; 2806 } 2807 setActivityInfo(ActivityInfo info)2808 ActivityStarter setActivityInfo(ActivityInfo info) { 2809 mRequest.activityInfo = info; 2810 return this; 2811 } 2812 setResolveInfo(ResolveInfo info)2813 ActivityStarter setResolveInfo(ResolveInfo info) { 2814 mRequest.resolveInfo = info; 2815 return this; 2816 } 2817 setVoiceSession(IVoiceInteractionSession voiceSession)2818 ActivityStarter setVoiceSession(IVoiceInteractionSession voiceSession) { 2819 mRequest.voiceSession = voiceSession; 2820 return this; 2821 } 2822 setVoiceInteractor(IVoiceInteractor voiceInteractor)2823 ActivityStarter setVoiceInteractor(IVoiceInteractor voiceInteractor) { 2824 mRequest.voiceInteractor = voiceInteractor; 2825 return this; 2826 } 2827 setResultTo(IBinder resultTo)2828 ActivityStarter setResultTo(IBinder resultTo) { 2829 mRequest.resultTo = resultTo; 2830 return this; 2831 } 2832 setResultWho(String resultWho)2833 ActivityStarter setResultWho(String resultWho) { 2834 mRequest.resultWho = resultWho; 2835 return this; 2836 } 2837 setRequestCode(int requestCode)2838 ActivityStarter setRequestCode(int requestCode) { 2839 mRequest.requestCode = requestCode; 2840 return this; 2841 } 2842 2843 /** 2844 * Sets the pid of the caller who originally started the activity. 2845 * 2846 * Normally, the pid/uid would be the calling pid from the binder call. 2847 * However, in case of a {@link PendingIntent}, the pid/uid pair of the caller is considered 2848 * the original entity that created the pending intent, in contrast to setRealCallingPid/Uid, 2849 * which represents the entity who invoked pending intent via {@link PendingIntent#send}. 2850 */ setCallingPid(int pid)2851 ActivityStarter setCallingPid(int pid) { 2852 mRequest.callingPid = pid; 2853 return this; 2854 } 2855 2856 /** 2857 * Sets the uid of the caller who originally started the activity. 2858 * 2859 * @see #setCallingPid 2860 */ setCallingUid(int uid)2861 ActivityStarter setCallingUid(int uid) { 2862 mRequest.callingUid = uid; 2863 return this; 2864 } 2865 setCallingPackage(String callingPackage)2866 ActivityStarter setCallingPackage(String callingPackage) { 2867 mRequest.callingPackage = callingPackage; 2868 return this; 2869 } 2870 setCallingFeatureId(String callingFeatureId)2871 ActivityStarter setCallingFeatureId(String callingFeatureId) { 2872 mRequest.callingFeatureId = callingFeatureId; 2873 return this; 2874 } 2875 2876 /** 2877 * Sets the pid of the caller who requested to launch the activity. 2878 * 2879 * The pid/uid represents the caller who launches the activity in this request. 2880 * It will almost same as setCallingPid/Uid except when processing {@link PendingIntent}: 2881 * the pid/uid will be the caller who called {@link PendingIntent#send()}. 2882 * 2883 * @see #setCallingPid 2884 */ setRealCallingPid(int pid)2885 ActivityStarter setRealCallingPid(int pid) { 2886 mRequest.realCallingPid = pid; 2887 return this; 2888 } 2889 2890 /** 2891 * Sets the uid of the caller who requested to launch the activity. 2892 * 2893 * @see #setRealCallingPid 2894 */ setRealCallingUid(int uid)2895 ActivityStarter setRealCallingUid(int uid) { 2896 mRequest.realCallingUid = uid; 2897 return this; 2898 } 2899 setStartFlags(int startFlags)2900 ActivityStarter setStartFlags(int startFlags) { 2901 mRequest.startFlags = startFlags; 2902 return this; 2903 } 2904 setActivityOptions(SafeActivityOptions options)2905 ActivityStarter setActivityOptions(SafeActivityOptions options) { 2906 mRequest.activityOptions = options; 2907 return this; 2908 } 2909 setActivityOptions(Bundle bOptions)2910 ActivityStarter setActivityOptions(Bundle bOptions) { 2911 return setActivityOptions(SafeActivityOptions.fromBundle(bOptions)); 2912 } 2913 setIgnoreTargetSecurity(boolean ignoreTargetSecurity)2914 ActivityStarter setIgnoreTargetSecurity(boolean ignoreTargetSecurity) { 2915 mRequest.ignoreTargetSecurity = ignoreTargetSecurity; 2916 return this; 2917 } 2918 setFilterCallingUid(int filterCallingUid)2919 ActivityStarter setFilterCallingUid(int filterCallingUid) { 2920 mRequest.filterCallingUid = filterCallingUid; 2921 return this; 2922 } 2923 setComponentSpecified(boolean componentSpecified)2924 ActivityStarter setComponentSpecified(boolean componentSpecified) { 2925 mRequest.componentSpecified = componentSpecified; 2926 return this; 2927 } 2928 setOutActivity(ActivityRecord[] outActivity)2929 ActivityStarter setOutActivity(ActivityRecord[] outActivity) { 2930 mRequest.outActivity = outActivity; 2931 return this; 2932 } 2933 setInTask(Task inTask)2934 ActivityStarter setInTask(Task inTask) { 2935 mRequest.inTask = inTask; 2936 return this; 2937 } 2938 setWaitResult(WaitResult result)2939 ActivityStarter setWaitResult(WaitResult result) { 2940 mRequest.waitResult = result; 2941 return this; 2942 } 2943 setProfilerInfo(ProfilerInfo info)2944 ActivityStarter setProfilerInfo(ProfilerInfo info) { 2945 mRequest.profilerInfo = info; 2946 return this; 2947 } 2948 setGlobalConfiguration(Configuration config)2949 ActivityStarter setGlobalConfiguration(Configuration config) { 2950 mRequest.globalConfig = config; 2951 return this; 2952 } 2953 setUserId(int userId)2954 ActivityStarter setUserId(int userId) { 2955 mRequest.userId = userId; 2956 return this; 2957 } 2958 setAllowPendingRemoteAnimationRegistryLookup(boolean allowLookup)2959 ActivityStarter setAllowPendingRemoteAnimationRegistryLookup(boolean allowLookup) { 2960 mRequest.allowPendingRemoteAnimationRegistryLookup = allowLookup; 2961 return this; 2962 } 2963 setOriginatingPendingIntent(PendingIntentRecord originatingPendingIntent)2964 ActivityStarter setOriginatingPendingIntent(PendingIntentRecord originatingPendingIntent) { 2965 mRequest.originatingPendingIntent = originatingPendingIntent; 2966 return this; 2967 } 2968 setAllowBackgroundActivityStart(boolean allowBackgroundActivityStart)2969 ActivityStarter setAllowBackgroundActivityStart(boolean allowBackgroundActivityStart) { 2970 mRequest.allowBackgroundActivityStart = allowBackgroundActivityStart; 2971 return this; 2972 } 2973 dump(PrintWriter pw, String prefix)2974 void dump(PrintWriter pw, String prefix) { 2975 prefix = prefix + " "; 2976 pw.print(prefix); 2977 pw.print("mCurrentUser="); 2978 pw.println(mRootWindowContainer.mCurrentUser); 2979 pw.print(prefix); 2980 pw.print("mLastStartReason="); 2981 pw.println(mLastStartReason); 2982 pw.print(prefix); 2983 pw.print("mLastStartActivityTimeMs="); 2984 pw.println(DateFormat.getDateTimeInstance().format(new Date(mLastStartActivityTimeMs))); 2985 pw.print(prefix); 2986 pw.print("mLastStartActivityResult="); 2987 pw.println(mLastStartActivityResult); 2988 if (mLastStartActivityRecord != null) { 2989 pw.print(prefix); 2990 pw.println("mLastStartActivityRecord:"); 2991 mLastStartActivityRecord.dump(pw, prefix + " ", true /* dumpAll */); 2992 } 2993 if (mStartActivity != null) { 2994 pw.print(prefix); 2995 pw.println("mStartActivity:"); 2996 mStartActivity.dump(pw, prefix + " ", true /* dumpAll */); 2997 } 2998 if (mIntent != null) { 2999 pw.print(prefix); 3000 pw.print("mIntent="); 3001 pw.println(mIntent); 3002 } 3003 if (mOptions != null) { 3004 pw.print(prefix); 3005 pw.print("mOptions="); 3006 pw.println(mOptions); 3007 } 3008 pw.print(prefix); 3009 pw.print("mLaunchSingleTop="); 3010 pw.print(LAUNCH_SINGLE_TOP == mLaunchMode); 3011 pw.print(" mLaunchSingleInstance="); 3012 pw.print(LAUNCH_SINGLE_INSTANCE == mLaunchMode); 3013 pw.print(" mLaunchSingleTask="); 3014 pw.println(LAUNCH_SINGLE_TASK == mLaunchMode); 3015 pw.print(prefix); 3016 pw.print("mLaunchFlags=0x"); 3017 pw.print(Integer.toHexString(mLaunchFlags)); 3018 pw.print(" mDoResume="); 3019 pw.print(mDoResume); 3020 pw.print(" mAddingToTask="); 3021 pw.println(mAddingToTask); 3022 } 3023 } 3024