ActivityStackSupervisor.java revision cc12f28e5dc6bd027971c995c7aab63dadcc0d35
1/* 2 * Copyright (C) 2013 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17package com.android.server.am; 18 19import static android.Manifest.permission.START_ANY_ACTIVITY; 20import static android.content.Intent.FLAG_ACTIVITY_NEW_TASK; 21import static android.content.Intent.FLAG_ACTIVITY_TASK_ON_HOME; 22import static android.content.pm.PackageManager.PERMISSION_GRANTED; 23import static com.android.server.am.ActivityManagerService.localLOGV; 24import static com.android.server.am.ActivityManagerService.DEBUG_CONFIGURATION; 25import static com.android.server.am.ActivityManagerService.DEBUG_FOCUS; 26import static com.android.server.am.ActivityManagerService.DEBUG_PAUSE; 27import static com.android.server.am.ActivityManagerService.DEBUG_RESULTS; 28import static com.android.server.am.ActivityManagerService.DEBUG_STACK; 29import static com.android.server.am.ActivityManagerService.DEBUG_SWITCH; 30import static com.android.server.am.ActivityManagerService.DEBUG_TASKS; 31import static com.android.server.am.ActivityManagerService.DEBUG_USER_LEAVING; 32import static com.android.server.am.ActivityManagerService.FIRST_SUPERVISOR_STACK_MSG; 33import static com.android.server.am.ActivityManagerService.TAG; 34 35import android.app.Activity; 36import android.app.ActivityManager; 37import android.app.ActivityManager.StackInfo; 38import android.app.ActivityOptions; 39import android.app.AppGlobals; 40import android.app.IActivityContainer; 41import android.app.IActivityContainerCallback; 42import android.app.IActivityManager; 43import android.app.IApplicationThread; 44import android.app.PendingIntent; 45import android.app.ActivityManager.RunningTaskInfo; 46import android.app.IActivityManager.WaitResult; 47import android.app.ResultInfo; 48import android.content.ComponentName; 49import android.content.Context; 50import android.content.IIntentSender; 51import android.content.Intent; 52import android.content.IntentSender; 53import android.content.pm.ActivityInfo; 54import android.content.pm.ApplicationInfo; 55import android.content.pm.PackageManager; 56import android.content.pm.ResolveInfo; 57import android.content.res.Configuration; 58import android.graphics.Point; 59import android.hardware.display.DisplayManager; 60import android.hardware.display.DisplayManager.DisplayListener; 61import android.hardware.display.DisplayManagerGlobal; 62import android.hardware.display.VirtualDisplay; 63import android.hardware.input.InputManager; 64import android.hardware.input.InputManagerInternal; 65import android.os.Binder; 66import android.os.Bundle; 67import android.os.Debug; 68import android.os.Handler; 69import android.os.IBinder; 70import android.os.Looper; 71import android.os.Message; 72import android.os.ParcelFileDescriptor; 73import android.os.PowerManager; 74import android.os.Process; 75import android.os.RemoteException; 76import android.os.SystemClock; 77import android.os.UserHandle; 78import android.service.voice.IVoiceInteractionSession; 79import android.util.EventLog; 80import android.util.Slog; 81import android.util.SparseArray; 82 83import android.util.SparseIntArray; 84import android.view.Display; 85import android.view.DisplayInfo; 86import android.view.InputEvent; 87import android.view.Surface; 88import com.android.internal.app.HeavyWeightSwitcherActivity; 89import com.android.internal.app.IVoiceInteractor; 90import com.android.internal.os.TransferPipe; 91import com.android.server.LocalServices; 92import com.android.server.am.ActivityManagerService.PendingActivityLaunch; 93import com.android.server.am.ActivityStack.ActivityState; 94import com.android.server.wm.WindowManagerService; 95 96import java.io.FileDescriptor; 97import java.io.IOException; 98import java.io.PrintWriter; 99import java.util.ArrayList; 100import java.util.List; 101 102public final class ActivityStackSupervisor implements DisplayListener { 103 static final boolean DEBUG = ActivityManagerService.DEBUG || false; 104 static final boolean DEBUG_ADD_REMOVE = DEBUG || false; 105 static final boolean DEBUG_APP = DEBUG || false; 106 static final boolean DEBUG_SAVED_STATE = DEBUG || false; 107 static final boolean DEBUG_STATES = DEBUG || false; 108 static final boolean DEBUG_IDLE = DEBUG || false; 109 static final boolean DEBUG_SCREENSHOTS = DEBUG || false; 110 111 public static final int HOME_STACK_ID = 0; 112 113 /** How long we wait until giving up on the last activity telling us it is idle. */ 114 static final int IDLE_TIMEOUT = 10*1000; 115 116 /** How long we can hold the sleep wake lock before giving up. */ 117 static final int SLEEP_TIMEOUT = 5*1000; 118 119 // How long we can hold the launch wake lock before giving up. 120 static final int LAUNCH_TIMEOUT = 10*1000; 121 122 static final int IDLE_TIMEOUT_MSG = FIRST_SUPERVISOR_STACK_MSG; 123 static final int IDLE_NOW_MSG = FIRST_SUPERVISOR_STACK_MSG + 1; 124 static final int RESUME_TOP_ACTIVITY_MSG = FIRST_SUPERVISOR_STACK_MSG + 2; 125 static final int SLEEP_TIMEOUT_MSG = FIRST_SUPERVISOR_STACK_MSG + 3; 126 static final int LAUNCH_TIMEOUT_MSG = FIRST_SUPERVISOR_STACK_MSG + 4; 127 static final int HANDLE_DISPLAY_ADDED = FIRST_SUPERVISOR_STACK_MSG + 5; 128 static final int HANDLE_DISPLAY_CHANGED = FIRST_SUPERVISOR_STACK_MSG + 6; 129 static final int HANDLE_DISPLAY_REMOVED = FIRST_SUPERVISOR_STACK_MSG + 7; 130 static final int CONTAINER_CALLBACK_VISIBILITY = FIRST_SUPERVISOR_STACK_MSG + 8; 131 132 private final static String VIRTUAL_DISPLAY_BASE_NAME = "ActivityViewVirtualDisplay"; 133 134 // For debugging to make sure the caller when acquiring/releasing our 135 // wake lock is the system process. 136 static final boolean VALIDATE_WAKE_LOCK_CALLER = false; 137 138 final ActivityManagerService mService; 139 140 final ActivityStackSupervisorHandler mHandler; 141 142 /** Short cut */ 143 WindowManagerService mWindowManager; 144 DisplayManager mDisplayManager; 145 146 /** Dismiss the keyguard after the next activity is displayed? */ 147 boolean mDismissKeyguardOnNextActivity = false; 148 149 /** Identifier counter for all ActivityStacks */ 150 private int mLastStackId = HOME_STACK_ID; 151 152 /** Task identifier that activities are currently being started in. Incremented each time a 153 * new task is created. */ 154 private int mCurTaskId = 0; 155 156 /** The current user */ 157 private int mCurrentUser; 158 159 /** The stack containing the launcher app. Assumed to always be attached to 160 * Display.DEFAULT_DISPLAY. */ 161 private ActivityStack mHomeStack; 162 163 /** The stack currently receiving input or launching the next activity. */ 164 private ActivityStack mFocusedStack; 165 166 /** If this is the same as mFocusedStack then the activity on the top of the focused stack has 167 * been resumed. If stacks are changing position this will hold the old stack until the new 168 * stack becomes resumed after which it will be set to mFocusedStack. */ 169 private ActivityStack mLastFocusedStack; 170 171 /** List of activities that are waiting for a new activity to become visible before completing 172 * whatever operation they are supposed to do. */ 173 final ArrayList<ActivityRecord> mWaitingVisibleActivities = new ArrayList<ActivityRecord>(); 174 175 /** List of processes waiting to find out about the next visible activity. */ 176 final ArrayList<IActivityManager.WaitResult> mWaitingActivityVisible = 177 new ArrayList<IActivityManager.WaitResult>(); 178 179 /** List of processes waiting to find out about the next launched activity. */ 180 final ArrayList<IActivityManager.WaitResult> mWaitingActivityLaunched = 181 new ArrayList<IActivityManager.WaitResult>(); 182 183 /** List of activities that are ready to be stopped, but waiting for the next activity to 184 * settle down before doing so. */ 185 final ArrayList<ActivityRecord> mStoppingActivities = new ArrayList<ActivityRecord>(); 186 187 /** List of activities that are ready to be finished, but waiting for the previous activity to 188 * settle down before doing so. It contains ActivityRecord objects. */ 189 final ArrayList<ActivityRecord> mFinishingActivities = new ArrayList<ActivityRecord>(); 190 191 /** List of activities that are in the process of going to sleep. */ 192 final ArrayList<ActivityRecord> mGoingToSleepActivities = new ArrayList<ActivityRecord>(); 193 194 /** Used on user changes */ 195 final ArrayList<UserStartedState> mStartingUsers = new ArrayList<UserStartedState>(); 196 197 /** Used to queue up any background users being started */ 198 final ArrayList<UserStartedState> mStartingBackgroundUsers = new ArrayList<UserStartedState>(); 199 200 /** Set to indicate whether to issue an onUserLeaving callback when a newly launched activity 201 * is being brought in front of us. */ 202 boolean mUserLeaving = false; 203 204 /** Set when we have taken too long waiting to go to sleep. */ 205 boolean mSleepTimeout = false; 206 207 /** 208 * We don't want to allow the device to go to sleep while in the process 209 * of launching an activity. This is primarily to allow alarm intent 210 * receivers to launch an activity and get that to run before the device 211 * goes back to sleep. 212 */ 213 final PowerManager.WakeLock mLaunchingActivity; 214 215 /** 216 * Set when the system is going to sleep, until we have 217 * successfully paused the current activity and released our wake lock. 218 * At that point the system is allowed to actually sleep. 219 */ 220 final PowerManager.WakeLock mGoingToSleep; 221 222 /** Stack id of the front stack when user switched, indexed by userId. */ 223 SparseIntArray mUserStackInFront = new SparseIntArray(2); 224 225 // TODO: Add listener for removal of references. 226 /** Mapping from (ActivityStack/TaskStack).mStackId to their current state */ 227 SparseArray<ActivityContainer> mActivityContainers = new SparseArray<ActivityContainer>(); 228 229 /** Mapping from displayId to display current state */ 230 private final SparseArray<ActivityDisplay> mActivityDisplays = 231 new SparseArray<ActivityDisplay>(); 232 233 InputManagerInternal mInputManagerInternal; 234 235 /** If non-null then the task specified remains in front and no other tasks may be started 236 * until the task exits or #stopLockTaskMode() is called. */ 237 private TaskRecord mLockTaskModeTask; 238 239 public ActivityStackSupervisor(ActivityManagerService service) { 240 mService = service; 241 PowerManager pm = (PowerManager)mService.mContext.getSystemService(Context.POWER_SERVICE); 242 mGoingToSleep = pm.newWakeLock(PowerManager.PARTIAL_WAKE_LOCK, "ActivityManager-Sleep"); 243 mHandler = new ActivityStackSupervisorHandler(mService.mHandler.getLooper()); 244 if (VALIDATE_WAKE_LOCK_CALLER && Binder.getCallingUid() != Process.myUid()) { 245 throw new IllegalStateException("Calling must be system uid"); 246 } 247 mLaunchingActivity = 248 pm.newWakeLock(PowerManager.PARTIAL_WAKE_LOCK, "ActivityManager-Launch"); 249 mLaunchingActivity.setReferenceCounted(false); 250 } 251 252 void setWindowManager(WindowManagerService wm) { 253 synchronized (mService) { 254 mWindowManager = wm; 255 256 mDisplayManager = 257 (DisplayManager)mService.mContext.getSystemService(Context.DISPLAY_SERVICE); 258 mDisplayManager.registerDisplayListener(this, null); 259 260 Display[] displays = mDisplayManager.getDisplays(); 261 for (int displayNdx = displays.length - 1; displayNdx >= 0; --displayNdx) { 262 final int displayId = displays[displayNdx].getDisplayId(); 263 ActivityDisplay activityDisplay = new ActivityDisplay(displayId); 264 mActivityDisplays.put(displayId, activityDisplay); 265 } 266 267 createStackOnDisplay(HOME_STACK_ID, Display.DEFAULT_DISPLAY); 268 mHomeStack = mFocusedStack = mLastFocusedStack = getStack(HOME_STACK_ID); 269 270 mInputManagerInternal = LocalServices.getService(InputManagerInternal.class); 271 } 272 } 273 274 void dismissKeyguard() { 275 if (ActivityManagerService.DEBUG_LOCKSCREEN) mService.logLockScreen(""); 276 if (mDismissKeyguardOnNextActivity) { 277 mDismissKeyguardOnNextActivity = false; 278 mWindowManager.dismissKeyguard(); 279 } 280 } 281 282 ActivityStack getFocusedStack() { 283 return mFocusedStack; 284 } 285 286 ActivityStack getLastStack() { 287 return mLastFocusedStack; 288 } 289 290 // TODO: Split into two methods isFrontStack for any visible stack and isFrontmostStack for the 291 // top of all visible stacks. 292 boolean isFrontStack(ActivityStack stack) { 293 final ActivityRecord parent = stack.mActivityContainer.mParentActivity; 294 if (parent != null) { 295 stack = parent.task.stack; 296 } 297 ArrayList<ActivityStack> stacks = stack.mStacks; 298 if (stacks != null && !stacks.isEmpty()) { 299 return stack == stacks.get(stacks.size() - 1); 300 } 301 return false; 302 } 303 304 void moveHomeStack(boolean toFront) { 305 ArrayList<ActivityStack> stacks = mHomeStack.mStacks; 306 int topNdx = stacks.size() - 1; 307 if (topNdx <= 0) { 308 return; 309 } 310 ActivityStack topStack = stacks.get(topNdx); 311 final boolean homeInFront = topStack == mHomeStack; 312 if (homeInFront != toFront) { 313 mLastFocusedStack = topStack; 314 stacks.remove(mHomeStack); 315 stacks.add(toFront ? topNdx : 0, mHomeStack); 316 mFocusedStack = stacks.get(topNdx); 317 if (DEBUG_STACK) Slog.d(TAG, "moveHomeTask: topStack old=" + topStack + " new=" 318 + mFocusedStack); 319 } 320 } 321 322 void moveHomeToTop() { 323 moveHomeStack(true); 324 mHomeStack.moveHomeTaskToTop(); 325 } 326 327 boolean resumeHomeActivity(ActivityRecord prev) { 328 moveHomeToTop(); 329 if (prev != null) { 330 prev.task.mOnTopOfHome = false; 331 } 332 ActivityRecord r = mHomeStack.topRunningActivityLocked(null); 333 if (r != null && r.isHomeActivity()) { 334 mService.setFocusedActivityLocked(r); 335 return resumeTopActivitiesLocked(mHomeStack, prev, null); 336 } 337 return mService.startHomeActivityLocked(mCurrentUser); 338 } 339 340 void setDismissKeyguard(boolean dismiss) { 341 if (ActivityManagerService.DEBUG_LOCKSCREEN) mService.logLockScreen(" dismiss=" + dismiss); 342 mDismissKeyguardOnNextActivity = dismiss; 343 } 344 345 TaskRecord anyTaskForIdLocked(int id) { 346 int numDisplays = mActivityDisplays.size(); 347 for (int displayNdx = 0; displayNdx < numDisplays; ++displayNdx) { 348 ArrayList<ActivityStack> stacks = mActivityDisplays.valueAt(displayNdx).mStacks; 349 for (int stackNdx = stacks.size() - 1; stackNdx >= 0; --stackNdx) { 350 ActivityStack stack = stacks.get(stackNdx); 351 TaskRecord task = stack.taskForIdLocked(id); 352 if (task != null) { 353 return task; 354 } 355 } 356 } 357 return null; 358 } 359 360 ActivityRecord isInAnyStackLocked(IBinder token) { 361 int numDisplays = mActivityDisplays.size(); 362 for (int displayNdx = 0; displayNdx < numDisplays; ++displayNdx) { 363 ArrayList<ActivityStack> stacks = mActivityDisplays.valueAt(displayNdx).mStacks; 364 for (int stackNdx = stacks.size() - 1; stackNdx >= 0; --stackNdx) { 365 final ActivityRecord r = stacks.get(stackNdx).isInStackLocked(token); 366 if (r != null) { 367 return r; 368 } 369 } 370 } 371 return null; 372 } 373 374 int getNextTaskId() { 375 do { 376 mCurTaskId++; 377 if (mCurTaskId <= 0) { 378 mCurTaskId = 1; 379 } 380 } while (anyTaskForIdLocked(mCurTaskId) != null); 381 return mCurTaskId; 382 } 383 384 ActivityRecord resumedAppLocked() { 385 ActivityStack stack = getFocusedStack(); 386 if (stack == null) { 387 return null; 388 } 389 ActivityRecord resumedActivity = stack.mResumedActivity; 390 if (resumedActivity == null || resumedActivity.app == null) { 391 resumedActivity = stack.mPausingActivity; 392 if (resumedActivity == null || resumedActivity.app == null) { 393 resumedActivity = stack.topRunningActivityLocked(null); 394 } 395 } 396 return resumedActivity; 397 } 398 399 boolean attachApplicationLocked(ProcessRecord app) throws Exception { 400 final String processName = app.processName; 401 boolean didSomething = false; 402 for (int displayNdx = mActivityDisplays.size() - 1; displayNdx >= 0; --displayNdx) { 403 ArrayList<ActivityStack> stacks = mActivityDisplays.valueAt(displayNdx).mStacks; 404 for (int stackNdx = stacks.size() - 1; stackNdx >= 0; --stackNdx) { 405 final ActivityStack stack = stacks.get(stackNdx); 406 if (!isFrontStack(stack)) { 407 continue; 408 } 409 ActivityRecord hr = stack.topRunningActivityLocked(null); 410 if (hr != null) { 411 if (hr.app == null && app.uid == hr.info.applicationInfo.uid 412 && processName.equals(hr.processName)) { 413 try { 414 if (realStartActivityLocked(hr, app, true, true)) { 415 didSomething = true; 416 } 417 } catch (Exception e) { 418 Slog.w(TAG, "Exception in new application when starting activity " 419 + hr.intent.getComponent().flattenToShortString(), e); 420 throw e; 421 } 422 } 423 } 424 } 425 } 426 if (!didSomething) { 427 ensureActivitiesVisibleLocked(null, 0); 428 } 429 return didSomething; 430 } 431 432 boolean allResumedActivitiesIdle() { 433 for (int displayNdx = mActivityDisplays.size() - 1; displayNdx >= 0; --displayNdx) { 434 ArrayList<ActivityStack> stacks = mActivityDisplays.valueAt(displayNdx).mStacks; 435 for (int stackNdx = stacks.size() - 1; stackNdx >= 0; --stackNdx) { 436 final ActivityStack stack = stacks.get(stackNdx); 437 if (!isFrontStack(stack) || stack.numActivities() == 0) { 438 continue; 439 } 440 final ActivityRecord resumedActivity = stack.mResumedActivity; 441 if (resumedActivity == null || !resumedActivity.idle) { 442 if (DEBUG_STATES) Slog.d(TAG, "allResumedActivitiesIdle: stack=" 443 + stack.mStackId + " " + resumedActivity + " not idle"); 444 return false; 445 } 446 } 447 } 448 return true; 449 } 450 451 boolean allResumedActivitiesComplete() { 452 for (int displayNdx = mActivityDisplays.size() - 1; displayNdx >= 0; --displayNdx) { 453 ArrayList<ActivityStack> stacks = mActivityDisplays.valueAt(displayNdx).mStacks; 454 for (int stackNdx = stacks.size() - 1; stackNdx >= 0; --stackNdx) { 455 final ActivityStack stack = stacks.get(stackNdx); 456 if (isFrontStack(stack)) { 457 final ActivityRecord r = stack.mResumedActivity; 458 if (r != null && r.state != ActivityState.RESUMED) { 459 return false; 460 } 461 } 462 } 463 } 464 // TODO: Not sure if this should check if all Paused are complete too. 465 if (DEBUG_STACK) Slog.d(TAG, 466 "allResumedActivitiesComplete: mLastFocusedStack changing from=" + 467 mLastFocusedStack + " to=" + mFocusedStack); 468 mLastFocusedStack = mFocusedStack; 469 return true; 470 } 471 472 boolean allResumedActivitiesVisible() { 473 for (int displayNdx = mActivityDisplays.size() - 1; displayNdx >= 0; --displayNdx) { 474 ArrayList<ActivityStack> stacks = mActivityDisplays.valueAt(displayNdx).mStacks; 475 for (int stackNdx = stacks.size() - 1; stackNdx >= 0; --stackNdx) { 476 final ActivityStack stack = stacks.get(stackNdx); 477 final ActivityRecord r = stack.mResumedActivity; 478 if (r != null && (!r.nowVisible || r.waitingVisible)) { 479 return false; 480 } 481 } 482 } 483 return true; 484 } 485 486 /** 487 * Pause all activities in either all of the stacks or just the back stacks. 488 * @param userLeaving Passed to pauseActivity() to indicate whether to call onUserLeaving(). 489 * @return true if any activity was paused as a result of this call. 490 */ 491 boolean pauseBackStacks(boolean userLeaving) { 492 boolean someActivityPaused = false; 493 for (int displayNdx = mActivityDisplays.size() - 1; displayNdx >= 0; --displayNdx) { 494 ArrayList<ActivityStack> stacks = mActivityDisplays.valueAt(displayNdx).mStacks; 495 for (int stackNdx = stacks.size() - 1; stackNdx >= 0; --stackNdx) { 496 final ActivityStack stack = stacks.get(stackNdx); 497 if (!isFrontStack(stack) && stack.mResumedActivity != null) { 498 if (DEBUG_STATES) Slog.d(TAG, "pauseBackStacks: stack=" + stack + 499 " mResumedActivity=" + stack.mResumedActivity); 500 stack.startPausingLocked(userLeaving, false); 501 someActivityPaused = true; 502 } 503 } 504 } 505 return someActivityPaused; 506 } 507 508 boolean allPausedActivitiesComplete() { 509 boolean pausing = true; 510 for (int displayNdx = mActivityDisplays.size() - 1; displayNdx >= 0; --displayNdx) { 511 ArrayList<ActivityStack> stacks = mActivityDisplays.valueAt(displayNdx).mStacks; 512 for (int stackNdx = stacks.size() - 1; stackNdx >= 0; --stackNdx) { 513 final ActivityStack stack = stacks.get(stackNdx); 514 final ActivityRecord r = stack.mPausingActivity; 515 if (r != null && r.state != ActivityState.PAUSED 516 && r.state != ActivityState.STOPPED 517 && r.state != ActivityState.STOPPING) { 518 if (DEBUG_STATES) { 519 Slog.d(TAG, "allPausedActivitiesComplete: r=" + r + " state=" + r.state); 520 pausing = false; 521 } else { 522 return false; 523 } 524 } 525 } 526 } 527 return pausing; 528 } 529 530 void pauseChildStacks(ActivityRecord parent, boolean userLeaving, boolean uiSleeping) { 531 // TODO: Put all stacks in supervisor and iterate through them instead. 532 for (int displayNdx = mActivityDisplays.size() - 1; displayNdx >= 0; --displayNdx) { 533 ArrayList<ActivityStack> stacks = mActivityDisplays.valueAt(displayNdx).mStacks; 534 for (int stackNdx = stacks.size() - 1; stackNdx >= 0; --stackNdx) { 535 final ActivityStack stack = stacks.get(stackNdx); 536 if (stack.mResumedActivity != null && 537 stack.mActivityContainer.mParentActivity == parent) { 538 stack.startPausingLocked(userLeaving, uiSleeping); 539 } 540 } 541 } 542 } 543 544 void reportActivityVisibleLocked(ActivityRecord r) { 545 for (int i = mWaitingActivityVisible.size()-1; i >= 0; i--) { 546 WaitResult w = mWaitingActivityVisible.get(i); 547 w.timeout = false; 548 if (r != null) { 549 w.who = new ComponentName(r.info.packageName, r.info.name); 550 } 551 w.totalTime = SystemClock.uptimeMillis() - w.thisTime; 552 w.thisTime = w.totalTime; 553 } 554 mService.notifyAll(); 555 dismissKeyguard(); 556 } 557 558 void reportActivityLaunchedLocked(boolean timeout, ActivityRecord r, 559 long thisTime, long totalTime) { 560 for (int i = mWaitingActivityLaunched.size() - 1; i >= 0; i--) { 561 WaitResult w = mWaitingActivityLaunched.remove(i); 562 w.timeout = timeout; 563 if (r != null) { 564 w.who = new ComponentName(r.info.packageName, r.info.name); 565 } 566 w.thisTime = thisTime; 567 w.totalTime = totalTime; 568 } 569 mService.notifyAll(); 570 } 571 572 ActivityRecord topRunningActivityLocked() { 573 final ActivityStack focusedStack = getFocusedStack(); 574 ActivityRecord r = focusedStack.topRunningActivityLocked(null); 575 if (r != null) { 576 return r; 577 } 578 579 // Return to the home stack. 580 final ArrayList<ActivityStack> stacks = mHomeStack.mStacks; 581 for (int stackNdx = stacks.size() - 1; stackNdx >= 0; --stackNdx) { 582 final ActivityStack stack = stacks.get(stackNdx); 583 if (stack != focusedStack && isFrontStack(stack)) { 584 r = stack.topRunningActivityLocked(null); 585 if (r != null) { 586 return r; 587 } 588 } 589 } 590 return null; 591 } 592 593 void getTasksLocked(int maxNum, List<RunningTaskInfo> list, int callingUid, boolean allowed) { 594 // Gather all of the running tasks for each stack into runningTaskLists. 595 ArrayList<ArrayList<RunningTaskInfo>> runningTaskLists = 596 new ArrayList<ArrayList<RunningTaskInfo>>(); 597 final int numDisplays = mActivityDisplays.size(); 598 for (int displayNdx = 0; displayNdx < numDisplays; ++displayNdx) { 599 ArrayList<ActivityStack> stacks = mActivityDisplays.valueAt(displayNdx).mStacks; 600 for (int stackNdx = stacks.size() - 1; stackNdx >= 0; --stackNdx) { 601 final ActivityStack stack = stacks.get(stackNdx); 602 ArrayList<RunningTaskInfo> stackTaskList = new ArrayList<RunningTaskInfo>(); 603 runningTaskLists.add(stackTaskList); 604 stack.getTasksLocked(stackTaskList, callingUid, allowed); 605 } 606 } 607 608 // The lists are already sorted from most recent to oldest. Just pull the most recent off 609 // each list and add it to list. Stop when all lists are empty or maxNum reached. 610 while (maxNum > 0) { 611 long mostRecentActiveTime = Long.MIN_VALUE; 612 ArrayList<RunningTaskInfo> selectedStackList = null; 613 final int numTaskLists = runningTaskLists.size(); 614 for (int stackNdx = 0; stackNdx < numTaskLists; ++stackNdx) { 615 ArrayList<RunningTaskInfo> stackTaskList = runningTaskLists.get(stackNdx); 616 if (!stackTaskList.isEmpty()) { 617 final long lastActiveTime = stackTaskList.get(0).lastActiveTime; 618 if (lastActiveTime > mostRecentActiveTime) { 619 mostRecentActiveTime = lastActiveTime; 620 selectedStackList = stackTaskList; 621 } 622 } 623 } 624 if (selectedStackList != null) { 625 list.add(selectedStackList.remove(0)); 626 --maxNum; 627 } else { 628 break; 629 } 630 } 631 } 632 633 ActivityInfo resolveActivity(Intent intent, String resolvedType, int startFlags, 634 String profileFile, ParcelFileDescriptor profileFd, int userId) { 635 // Collect information about the target of the Intent. 636 ActivityInfo aInfo; 637 try { 638 ResolveInfo rInfo = 639 AppGlobals.getPackageManager().resolveIntent( 640 intent, resolvedType, 641 PackageManager.MATCH_DEFAULT_ONLY 642 | ActivityManagerService.STOCK_PM_FLAGS, userId); 643 aInfo = rInfo != null ? rInfo.activityInfo : null; 644 } catch (RemoteException e) { 645 aInfo = null; 646 } 647 648 if (aInfo != null) { 649 // Store the found target back into the intent, because now that 650 // we have it we never want to do this again. For example, if the 651 // user navigates back to this point in the history, we should 652 // always restart the exact same activity. 653 intent.setComponent(new ComponentName( 654 aInfo.applicationInfo.packageName, aInfo.name)); 655 656 // Don't debug things in the system process 657 if ((startFlags&ActivityManager.START_FLAG_DEBUG) != 0) { 658 if (!aInfo.processName.equals("system")) { 659 mService.setDebugApp(aInfo.processName, true, false); 660 } 661 } 662 663 if ((startFlags&ActivityManager.START_FLAG_OPENGL_TRACES) != 0) { 664 if (!aInfo.processName.equals("system")) { 665 mService.setOpenGlTraceApp(aInfo.applicationInfo, aInfo.processName); 666 } 667 } 668 669 if (profileFile != null) { 670 if (!aInfo.processName.equals("system")) { 671 mService.setProfileApp(aInfo.applicationInfo, aInfo.processName, 672 profileFile, profileFd, 673 (startFlags&ActivityManager.START_FLAG_AUTO_STOP_PROFILER) != 0); 674 } 675 } 676 } 677 return aInfo; 678 } 679 680 void startHomeActivity(Intent intent, ActivityInfo aInfo) { 681 moveHomeToTop(); 682 startActivityLocked(null, intent, null, aInfo, null, null, null, null, 0, 0, 0, null, 0, 683 null, false, null, null); 684 } 685 686 final int startActivityMayWait(IApplicationThread caller, int callingUid, 687 String callingPackage, Intent intent, String resolvedType, 688 IVoiceInteractionSession voiceSession, IVoiceInteractor voiceInteractor, 689 IBinder resultTo, String resultWho, int requestCode, int startFlags, String profileFile, 690 ParcelFileDescriptor profileFd, WaitResult outResult, Configuration config, 691 Bundle options, int userId, IActivityContainer iContainer) { 692 // Refuse possible leaked file descriptors 693 if (intent != null && intent.hasFileDescriptors()) { 694 throw new IllegalArgumentException("File descriptors passed in Intent"); 695 } 696 boolean componentSpecified = intent.getComponent() != null; 697 698 // Don't modify the client's object! 699 intent = new Intent(intent); 700 701 // Collect information about the target of the Intent. 702 ActivityInfo aInfo = resolveActivity(intent, resolvedType, startFlags, 703 profileFile, profileFd, userId); 704 705 ActivityContainer container = (ActivityContainer)iContainer; 706 synchronized (mService) { 707 int callingPid; 708 if (callingUid >= 0) { 709 callingPid = -1; 710 } else if (caller == null) { 711 callingPid = Binder.getCallingPid(); 712 callingUid = Binder.getCallingUid(); 713 } else { 714 callingPid = callingUid = -1; 715 } 716 717 final ActivityStack stack; 718 if (container == null || container.mStack.isOnHomeDisplay()) { 719 stack = getFocusedStack(); 720 } else { 721 stack = container.mStack; 722 } 723 stack.mConfigWillChange = config != null 724 && mService.mConfiguration.diff(config) != 0; 725 if (DEBUG_CONFIGURATION) Slog.v(TAG, 726 "Starting activity when config will change = " + stack.mConfigWillChange); 727 728 final long origId = Binder.clearCallingIdentity(); 729 730 if (aInfo != null && 731 (aInfo.applicationInfo.flags&ApplicationInfo.FLAG_CANT_SAVE_STATE) != 0) { 732 // This may be a heavy-weight process! Check to see if we already 733 // have another, different heavy-weight process running. 734 if (aInfo.processName.equals(aInfo.applicationInfo.packageName)) { 735 if (mService.mHeavyWeightProcess != null && 736 (mService.mHeavyWeightProcess.info.uid != aInfo.applicationInfo.uid || 737 !mService.mHeavyWeightProcess.processName.equals(aInfo.processName))) { 738 int realCallingUid = callingUid; 739 if (caller != null) { 740 ProcessRecord callerApp = mService.getRecordForAppLocked(caller); 741 if (callerApp != null) { 742 realCallingUid = callerApp.info.uid; 743 } else { 744 Slog.w(TAG, "Unable to find app for caller " + caller 745 + " (pid=" + callingPid + ") when starting: " 746 + intent.toString()); 747 ActivityOptions.abort(options); 748 return ActivityManager.START_PERMISSION_DENIED; 749 } 750 } 751 752 IIntentSender target = mService.getIntentSenderLocked( 753 ActivityManager.INTENT_SENDER_ACTIVITY, "android", 754 realCallingUid, userId, null, null, 0, new Intent[] { intent }, 755 new String[] { resolvedType }, PendingIntent.FLAG_CANCEL_CURRENT 756 | PendingIntent.FLAG_ONE_SHOT, null); 757 758 Intent newIntent = new Intent(); 759 if (requestCode >= 0) { 760 // Caller is requesting a result. 761 newIntent.putExtra(HeavyWeightSwitcherActivity.KEY_HAS_RESULT, true); 762 } 763 newIntent.putExtra(HeavyWeightSwitcherActivity.KEY_INTENT, 764 new IntentSender(target)); 765 if (mService.mHeavyWeightProcess.activities.size() > 0) { 766 ActivityRecord hist = mService.mHeavyWeightProcess.activities.get(0); 767 newIntent.putExtra(HeavyWeightSwitcherActivity.KEY_CUR_APP, 768 hist.packageName); 769 newIntent.putExtra(HeavyWeightSwitcherActivity.KEY_CUR_TASK, 770 hist.task.taskId); 771 } 772 newIntent.putExtra(HeavyWeightSwitcherActivity.KEY_NEW_APP, 773 aInfo.packageName); 774 newIntent.setFlags(intent.getFlags()); 775 newIntent.setClassName("android", 776 HeavyWeightSwitcherActivity.class.getName()); 777 intent = newIntent; 778 resolvedType = null; 779 caller = null; 780 callingUid = Binder.getCallingUid(); 781 callingPid = Binder.getCallingPid(); 782 componentSpecified = true; 783 try { 784 ResolveInfo rInfo = 785 AppGlobals.getPackageManager().resolveIntent( 786 intent, null, 787 PackageManager.MATCH_DEFAULT_ONLY 788 | ActivityManagerService.STOCK_PM_FLAGS, userId); 789 aInfo = rInfo != null ? rInfo.activityInfo : null; 790 aInfo = mService.getActivityInfoForUser(aInfo, userId); 791 } catch (RemoteException e) { 792 aInfo = null; 793 } 794 } 795 } 796 } 797 798 int res = startActivityLocked(caller, intent, resolvedType, aInfo, 799 voiceSession, voiceInteractor, resultTo, resultWho, 800 requestCode, callingPid, callingUid, callingPackage, startFlags, options, 801 componentSpecified, null, container); 802 803 if (stack.mConfigWillChange) { 804 // If the caller also wants to switch to a new configuration, 805 // do so now. This allows a clean switch, as we are waiting 806 // for the current activity to pause (so we will not destroy 807 // it), and have not yet started the next activity. 808 mService.enforceCallingPermission(android.Manifest.permission.CHANGE_CONFIGURATION, 809 "updateConfiguration()"); 810 stack.mConfigWillChange = false; 811 if (DEBUG_CONFIGURATION) Slog.v(TAG, 812 "Updating to new configuration after starting activity."); 813 mService.updateConfigurationLocked(config, null, false, false); 814 } 815 816 Binder.restoreCallingIdentity(origId); 817 818 if (outResult != null) { 819 outResult.result = res; 820 if (res == ActivityManager.START_SUCCESS) { 821 mWaitingActivityLaunched.add(outResult); 822 do { 823 try { 824 mService.wait(); 825 } catch (InterruptedException e) { 826 } 827 } while (!outResult.timeout && outResult.who == null); 828 } else if (res == ActivityManager.START_TASK_TO_FRONT) { 829 ActivityRecord r = stack.topRunningActivityLocked(null); 830 if (r.nowVisible) { 831 outResult.timeout = false; 832 outResult.who = new ComponentName(r.info.packageName, r.info.name); 833 outResult.totalTime = 0; 834 outResult.thisTime = 0; 835 } else { 836 outResult.thisTime = SystemClock.uptimeMillis(); 837 mWaitingActivityVisible.add(outResult); 838 do { 839 try { 840 mService.wait(); 841 } catch (InterruptedException e) { 842 } 843 } while (!outResult.timeout && outResult.who == null); 844 } 845 } 846 } 847 848 return res; 849 } 850 } 851 852 final int startActivities(IApplicationThread caller, int callingUid, String callingPackage, 853 Intent[] intents, String[] resolvedTypes, IBinder resultTo, 854 Bundle options, int userId) { 855 if (intents == null) { 856 throw new NullPointerException("intents is null"); 857 } 858 if (resolvedTypes == null) { 859 throw new NullPointerException("resolvedTypes is null"); 860 } 861 if (intents.length != resolvedTypes.length) { 862 throw new IllegalArgumentException("intents are length different than resolvedTypes"); 863 } 864 865 866 int callingPid; 867 if (callingUid >= 0) { 868 callingPid = -1; 869 } else if (caller == null) { 870 callingPid = Binder.getCallingPid(); 871 callingUid = Binder.getCallingUid(); 872 } else { 873 callingPid = callingUid = -1; 874 } 875 final long origId = Binder.clearCallingIdentity(); 876 try { 877 synchronized (mService) { 878 ActivityRecord[] outActivity = new ActivityRecord[1]; 879 for (int i=0; i<intents.length; i++) { 880 Intent intent = intents[i]; 881 if (intent == null) { 882 continue; 883 } 884 885 // Refuse possible leaked file descriptors 886 if (intent != null && intent.hasFileDescriptors()) { 887 throw new IllegalArgumentException("File descriptors passed in Intent"); 888 } 889 890 boolean componentSpecified = intent.getComponent() != null; 891 892 // Don't modify the client's object! 893 intent = new Intent(intent); 894 895 // Collect information about the target of the Intent. 896 ActivityInfo aInfo = resolveActivity(intent, resolvedTypes[i], 897 0, null, null, userId); 898 // TODO: New, check if this is correct 899 aInfo = mService.getActivityInfoForUser(aInfo, userId); 900 901 if (aInfo != null && 902 (aInfo.applicationInfo.flags & ApplicationInfo.FLAG_CANT_SAVE_STATE) 903 != 0) { 904 throw new IllegalArgumentException( 905 "FLAG_CANT_SAVE_STATE not supported here"); 906 } 907 908 Bundle theseOptions; 909 if (options != null && i == intents.length-1) { 910 theseOptions = options; 911 } else { 912 theseOptions = null; 913 } 914 int res = startActivityLocked(caller, intent, resolvedTypes[i], 915 aInfo, null, null, resultTo, null, -1, callingPid, callingUid, callingPackage, 916 0, theseOptions, componentSpecified, outActivity, null); 917 if (res < 0) { 918 return res; 919 } 920 921 resultTo = outActivity[0] != null ? outActivity[0].appToken : null; 922 } 923 } 924 } finally { 925 Binder.restoreCallingIdentity(origId); 926 } 927 928 return ActivityManager.START_SUCCESS; 929 } 930 931 final boolean realStartActivityLocked(ActivityRecord r, 932 ProcessRecord app, boolean andResume, boolean checkConfig) 933 throws RemoteException { 934 935 r.startFreezingScreenLocked(app, 0); 936 if (false) Slog.d(TAG, "realStartActivity: setting app visibility true"); 937 mWindowManager.setAppVisibility(r.appToken, true); 938 939 // schedule launch ticks to collect information about slow apps. 940 r.startLaunchTickingLocked(); 941 942 // Have the window manager re-evaluate the orientation of 943 // the screen based on the new activity order. Note that 944 // as a result of this, it can call back into the activity 945 // manager with a new orientation. We don't care about that, 946 // because the activity is not currently running so we are 947 // just restarting it anyway. 948 if (checkConfig) { 949 Configuration config = mWindowManager.updateOrientationFromAppTokens( 950 mService.mConfiguration, 951 r.mayFreezeScreenLocked(app) ? r.appToken : null); 952 mService.updateConfigurationLocked(config, r, false, false); 953 } 954 955 r.app = app; 956 app.waitingToKill = null; 957 r.launchCount++; 958 r.lastLaunchTime = SystemClock.uptimeMillis(); 959 960 if (localLOGV) Slog.v(TAG, "Launching: " + r); 961 962 int idx = app.activities.indexOf(r); 963 if (idx < 0) { 964 app.activities.add(r); 965 } 966 mService.updateLruProcessLocked(app, true, null); 967 mService.updateOomAdjLocked(); 968 969 final ActivityStack stack = r.task.stack; 970 try { 971 if (app.thread == null) { 972 throw new RemoteException(); 973 } 974 List<ResultInfo> results = null; 975 List<Intent> newIntents = null; 976 if (andResume) { 977 results = r.results; 978 newIntents = r.newIntents; 979 } 980 if (DEBUG_SWITCH) Slog.v(TAG, "Launching: " + r 981 + " icicle=" + r.icicle 982 + " with results=" + results + " newIntents=" + newIntents 983 + " andResume=" + andResume); 984 if (andResume) { 985 EventLog.writeEvent(EventLogTags.AM_RESTART_ACTIVITY, 986 r.userId, System.identityHashCode(r), 987 r.task.taskId, r.shortComponentName); 988 } 989 if (r.isHomeActivity() && r.isNotResolverActivity()) { 990 // Home process is the root process of the task. 991 mService.mHomeProcess = r.task.mActivities.get(0).app; 992 } 993 mService.ensurePackageDexOpt(r.intent.getComponent().getPackageName()); 994 r.sleeping = false; 995 r.forceNewConfig = false; 996 mService.showAskCompatModeDialogLocked(r); 997 r.compat = mService.compatibilityInfoForPackageLocked(r.info.applicationInfo); 998 String profileFile = null; 999 ParcelFileDescriptor profileFd = null; 1000 boolean profileAutoStop = false; 1001 if (mService.mProfileApp != null && mService.mProfileApp.equals(app.processName)) { 1002 if (mService.mProfileProc == null || mService.mProfileProc == app) { 1003 mService.mProfileProc = app; 1004 profileFile = mService.mProfileFile; 1005 profileFd = mService.mProfileFd; 1006 profileAutoStop = mService.mAutoStopProfiler; 1007 } 1008 } 1009 app.hasShownUi = true; 1010 app.pendingUiClean = true; 1011 if (profileFd != null) { 1012 try { 1013 profileFd = profileFd.dup(); 1014 } catch (IOException e) { 1015 if (profileFd != null) { 1016 try { 1017 profileFd.close(); 1018 } catch (IOException o) { 1019 } 1020 profileFd = null; 1021 } 1022 } 1023 } 1024 1025 app.forceProcessStateUpTo(ActivityManager.PROCESS_STATE_TOP); 1026 app.thread.scheduleLaunchActivity(new Intent(r.intent), r.appToken, 1027 System.identityHashCode(r), r.info, 1028 new Configuration(mService.mConfiguration), r.compat, r.task.voiceInteractor, 1029 app.repProcState, r.icicle, r.persistentState, results, newIntents, !andResume, 1030 mService.isNextTransitionForward(), profileFile, profileFd, profileAutoStop 1031 ); 1032 1033 if ((app.info.flags&ApplicationInfo.FLAG_CANT_SAVE_STATE) != 0) { 1034 // This may be a heavy-weight process! Note that the package 1035 // manager will ensure that only activity can run in the main 1036 // process of the .apk, which is the only thing that will be 1037 // considered heavy-weight. 1038 if (app.processName.equals(app.info.packageName)) { 1039 if (mService.mHeavyWeightProcess != null 1040 && mService.mHeavyWeightProcess != app) { 1041 Slog.w(TAG, "Starting new heavy weight process " + app 1042 + " when already running " 1043 + mService.mHeavyWeightProcess); 1044 } 1045 mService.mHeavyWeightProcess = app; 1046 Message msg = mService.mHandler.obtainMessage( 1047 ActivityManagerService.POST_HEAVY_NOTIFICATION_MSG); 1048 msg.obj = r; 1049 mService.mHandler.sendMessage(msg); 1050 } 1051 } 1052 1053 } catch (RemoteException e) { 1054 if (r.launchFailed) { 1055 // This is the second time we failed -- finish activity 1056 // and give up. 1057 Slog.e(TAG, "Second failure launching " 1058 + r.intent.getComponent().flattenToShortString() 1059 + ", giving up", e); 1060 mService.appDiedLocked(app, app.pid, app.thread); 1061 stack.requestFinishActivityLocked(r.appToken, Activity.RESULT_CANCELED, null, 1062 "2nd-crash", false); 1063 return false; 1064 } 1065 1066 // This is the first time we failed -- restart process and 1067 // retry. 1068 app.activities.remove(r); 1069 throw e; 1070 } 1071 1072 r.launchFailed = false; 1073 if (stack.updateLRUListLocked(r)) { 1074 Slog.w(TAG, "Activity " + r 1075 + " being launched, but already in LRU list"); 1076 } 1077 1078 if (andResume) { 1079 // As part of the process of launching, ActivityThread also performs 1080 // a resume. 1081 stack.minimalResumeActivityLocked(r); 1082 } else { 1083 // This activity is not starting in the resumed state... which 1084 // should look like we asked it to pause+stop (but remain visible), 1085 // and it has done so and reported back the current icicle and 1086 // other state. 1087 if (DEBUG_STATES) Slog.v(TAG, "Moving to STOPPED: " + r 1088 + " (starting in stopped state)"); 1089 r.state = ActivityState.STOPPED; 1090 r.stopped = true; 1091 } 1092 1093 // Launch the new version setup screen if needed. We do this -after- 1094 // launching the initial activity (that is, home), so that it can have 1095 // a chance to initialize itself while in the background, making the 1096 // switch back to it faster and look better. 1097 if (isFrontStack(stack)) { 1098 mService.startSetupActivityLocked(); 1099 } 1100 1101 return true; 1102 } 1103 1104 void startSpecificActivityLocked(ActivityRecord r, 1105 boolean andResume, boolean checkConfig) { 1106 // Is this activity's application already running? 1107 ProcessRecord app = mService.getProcessRecordLocked(r.processName, 1108 r.info.applicationInfo.uid, true); 1109 1110 r.task.stack.setLaunchTime(r); 1111 1112 if (app != null && app.thread != null) { 1113 try { 1114 if ((r.info.flags&ActivityInfo.FLAG_MULTIPROCESS) == 0 1115 || !"android".equals(r.info.packageName)) { 1116 // Don't add this if it is a platform component that is marked 1117 // to run in multiple processes, because this is actually 1118 // part of the framework so doesn't make sense to track as a 1119 // separate apk in the process. 1120 app.addPackage(r.info.packageName, mService.mProcessStats); 1121 } 1122 realStartActivityLocked(r, app, andResume, checkConfig); 1123 return; 1124 } catch (RemoteException e) { 1125 Slog.w(TAG, "Exception when starting activity " 1126 + r.intent.getComponent().flattenToShortString(), e); 1127 } 1128 1129 // If a dead object exception was thrown -- fall through to 1130 // restart the application. 1131 } 1132 1133 mService.startProcessLocked(r.processName, r.info.applicationInfo, true, 0, 1134 "activity", r.intent.getComponent(), false, false, true); 1135 } 1136 1137 final int startActivityLocked(IApplicationThread caller, 1138 Intent intent, String resolvedType, ActivityInfo aInfo, 1139 IVoiceInteractionSession voiceSession, IVoiceInteractor voiceInteractor, 1140 IBinder resultTo, String resultWho, int requestCode, 1141 int callingPid, int callingUid, String callingPackage, int startFlags, Bundle options, 1142 boolean componentSpecified, ActivityRecord[] outActivity, ActivityContainer container) { 1143 int err = ActivityManager.START_SUCCESS; 1144 1145 ProcessRecord callerApp = null; 1146 if (caller != null) { 1147 callerApp = mService.getRecordForAppLocked(caller); 1148 if (callerApp != null) { 1149 callingPid = callerApp.pid; 1150 callingUid = callerApp.info.uid; 1151 } else { 1152 Slog.w(TAG, "Unable to find app for caller " + caller 1153 + " (pid=" + callingPid + ") when starting: " 1154 + intent.toString()); 1155 err = ActivityManager.START_PERMISSION_DENIED; 1156 } 1157 } 1158 1159 if (err == ActivityManager.START_SUCCESS) { 1160 final int userId = aInfo != null ? UserHandle.getUserId(aInfo.applicationInfo.uid) : 0; 1161 Slog.i(TAG, "START u" + userId + " {" + intent.toShortString(true, true, true, false) 1162 + "} from pid " + (callerApp != null ? callerApp.pid : callingPid) 1163 + " on display " + (container == null ? (mFocusedStack == null ? 1164 Display.DEFAULT_DISPLAY : mFocusedStack.mDisplayId) : 1165 (container.mActivityDisplay == null ? Display.DEFAULT_DISPLAY : 1166 container.mActivityDisplay.mDisplayId))); 1167 } 1168 1169 ActivityRecord sourceRecord = null; 1170 ActivityRecord resultRecord = null; 1171 if (resultTo != null) { 1172 sourceRecord = isInAnyStackLocked(resultTo); 1173 if (DEBUG_RESULTS) Slog.v( 1174 TAG, "Will send result to " + resultTo + " " + sourceRecord); 1175 if (sourceRecord != null) { 1176 if (requestCode >= 0 && !sourceRecord.finishing) { 1177 resultRecord = sourceRecord; 1178 } 1179 } 1180 } 1181 ActivityStack resultStack = resultRecord == null ? null : resultRecord.task.stack; 1182 1183 final int launchFlags = intent.getFlags(); 1184 1185 if ((launchFlags&Intent.FLAG_ACTIVITY_FORWARD_RESULT) != 0 1186 && sourceRecord != null) { 1187 // Transfer the result target from the source activity to the new 1188 // one being started, including any failures. 1189 if (requestCode >= 0) { 1190 ActivityOptions.abort(options); 1191 return ActivityManager.START_FORWARD_AND_REQUEST_CONFLICT; 1192 } 1193 resultRecord = sourceRecord.resultTo; 1194 resultWho = sourceRecord.resultWho; 1195 requestCode = sourceRecord.requestCode; 1196 sourceRecord.resultTo = null; 1197 if (resultRecord != null) { 1198 resultRecord.removeResultsLocked( 1199 sourceRecord, resultWho, requestCode); 1200 } 1201 if (sourceRecord.launchedFromUid == callingUid) { 1202 // The new activity is being launched from the same uid as the previous 1203 // activity in the flow, and asking to forward its result back to the 1204 // previous. In this case the activity is serving as a trampoline between 1205 // the two, so we also want to update its launchedFromPackage to be the 1206 // same as the previous activity. Note that this is safe, since we know 1207 // these two packages come from the same uid; the caller could just as 1208 // well have supplied that same package name itself. This specifially 1209 // deals with the case of an intent picker/chooser being launched in the app 1210 // flow to redirect to an activity picked by the user, where we want the final 1211 // activity to consider it to have been launched by the previous app activity. 1212 callingPackage = sourceRecord.launchedFromPackage; 1213 } 1214 } 1215 1216 if (err == ActivityManager.START_SUCCESS && intent.getComponent() == null) { 1217 // We couldn't find a class that can handle the given Intent. 1218 // That's the end of that! 1219 err = ActivityManager.START_INTENT_NOT_RESOLVED; 1220 } 1221 1222 if (err == ActivityManager.START_SUCCESS && aInfo == null) { 1223 // We couldn't find the specific class specified in the Intent. 1224 // Also the end of the line. 1225 err = ActivityManager.START_CLASS_NOT_FOUND; 1226 } 1227 1228 if (err == ActivityManager.START_SUCCESS && sourceRecord != null 1229 && sourceRecord.task.voiceSession != null) { 1230 // If this activity is being launched as part of a voice session, we need 1231 // to ensure that it is safe to do so. If the upcoming activity will also 1232 // be part of the voice session, we can only launch it if it has explicitly 1233 // said it supports the VOICE category, or it is a part of the calling app. 1234 if ((launchFlags&Intent.FLAG_ACTIVITY_NEW_TASK) == 0 1235 && sourceRecord.info.applicationInfo.uid != aInfo.applicationInfo.uid) { 1236 try { 1237 if (!AppGlobals.getPackageManager().activitySupportsIntent(intent.getComponent(), 1238 intent, resolvedType)) { 1239 err = ActivityManager.START_NOT_VOICE_COMPATIBLE; 1240 } 1241 } catch (RemoteException e) { 1242 err = ActivityManager.START_NOT_VOICE_COMPATIBLE; 1243 } 1244 } 1245 } 1246 1247 if (err == ActivityManager.START_SUCCESS && voiceSession != null) { 1248 // If the caller is starting a new voice session, just make sure the target 1249 // is actually allowing it to run this way. 1250 try { 1251 if (!AppGlobals.getPackageManager().activitySupportsIntent(intent.getComponent(), 1252 intent, resolvedType)) { 1253 err = ActivityManager.START_NOT_VOICE_COMPATIBLE; 1254 } 1255 } catch (RemoteException e) { 1256 err = ActivityManager.START_NOT_VOICE_COMPATIBLE; 1257 } 1258 } 1259 1260 if (err != ActivityManager.START_SUCCESS) { 1261 if (resultRecord != null) { 1262 resultStack.sendActivityResultLocked(-1, 1263 resultRecord, resultWho, requestCode, 1264 Activity.RESULT_CANCELED, null); 1265 } 1266 setDismissKeyguard(false); 1267 ActivityOptions.abort(options); 1268 return err; 1269 } 1270 1271 final int startAnyPerm = mService.checkPermission( 1272 START_ANY_ACTIVITY, callingPid, callingUid); 1273 final int componentPerm = mService.checkComponentPermission(aInfo.permission, callingPid, 1274 callingUid, aInfo.applicationInfo.uid, aInfo.exported); 1275 if (startAnyPerm != PERMISSION_GRANTED && componentPerm != PERMISSION_GRANTED) { 1276 if (resultRecord != null) { 1277 resultStack.sendActivityResultLocked(-1, 1278 resultRecord, resultWho, requestCode, 1279 Activity.RESULT_CANCELED, null); 1280 } 1281 setDismissKeyguard(false); 1282 String msg; 1283 if (!aInfo.exported) { 1284 msg = "Permission Denial: starting " + intent.toString() 1285 + " from " + callerApp + " (pid=" + callingPid 1286 + ", uid=" + callingUid + ")" 1287 + " not exported from uid " + aInfo.applicationInfo.uid; 1288 } else { 1289 msg = "Permission Denial: starting " + intent.toString() 1290 + " from " + callerApp + " (pid=" + callingPid 1291 + ", uid=" + callingUid + ")" 1292 + " requires " + aInfo.permission; 1293 } 1294 Slog.w(TAG, msg); 1295 throw new SecurityException(msg); 1296 } 1297 1298 boolean abort = !mService.mIntentFirewall.checkStartActivity(intent, callingUid, 1299 callingPid, resolvedType, aInfo.applicationInfo); 1300 1301 if (mService.mController != null) { 1302 try { 1303 // The Intent we give to the watcher has the extra data 1304 // stripped off, since it can contain private information. 1305 Intent watchIntent = intent.cloneFilter(); 1306 abort |= !mService.mController.activityStarting(watchIntent, 1307 aInfo.applicationInfo.packageName); 1308 } catch (RemoteException e) { 1309 mService.mController = null; 1310 } 1311 } 1312 1313 if (abort) { 1314 if (resultRecord != null) { 1315 resultStack.sendActivityResultLocked(-1, resultRecord, resultWho, requestCode, 1316 Activity.RESULT_CANCELED, null); 1317 } 1318 // We pretend to the caller that it was really started, but 1319 // they will just get a cancel result. 1320 setDismissKeyguard(false); 1321 ActivityOptions.abort(options); 1322 return ActivityManager.START_SUCCESS; 1323 } 1324 1325 ActivityRecord r = new ActivityRecord(mService, callerApp, callingUid, callingPackage, 1326 intent, resolvedType, aInfo, mService.mConfiguration, resultRecord, resultWho, 1327 requestCode, componentSpecified, this, container, options); 1328 if (outActivity != null) { 1329 outActivity[0] = r; 1330 } 1331 1332 final ActivityStack stack = getFocusedStack(); 1333 if (voiceSession == null && (stack.mResumedActivity == null 1334 || stack.mResumedActivity.info.applicationInfo.uid != callingUid)) { 1335 if (!mService.checkAppSwitchAllowedLocked(callingPid, callingUid, "Activity start")) { 1336 PendingActivityLaunch pal = 1337 new PendingActivityLaunch(r, sourceRecord, startFlags, stack); 1338 mService.mPendingActivityLaunches.add(pal); 1339 setDismissKeyguard(false); 1340 ActivityOptions.abort(options); 1341 return ActivityManager.START_SWITCHES_CANCELED; 1342 } 1343 } 1344 1345 if (mService.mDidAppSwitch) { 1346 // This is the second allowed switch since we stopped switches, 1347 // so now just generally allow switches. Use case: user presses 1348 // home (switches disabled, switch to home, mDidAppSwitch now true); 1349 // user taps a home icon (coming from home so allowed, we hit here 1350 // and now allow anyone to switch again). 1351 mService.mAppSwitchesAllowedTime = 0; 1352 } else { 1353 mService.mDidAppSwitch = true; 1354 } 1355 1356 mService.doPendingActivityLaunchesLocked(false); 1357 1358 err = startActivityUncheckedLocked(r, sourceRecord, voiceSession, voiceInteractor, 1359 startFlags, true, options); 1360 1361 if (allPausedActivitiesComplete()) { 1362 // If someone asked to have the keyguard dismissed on the next 1363 // activity start, but we are not actually doing an activity 1364 // switch... just dismiss the keyguard now, because we 1365 // probably want to see whatever is behind it. 1366 dismissKeyguard(); 1367 } 1368 return err; 1369 } 1370 1371 ActivityStack adjustStackFocus(ActivityRecord r) { 1372 final TaskRecord task = r.task; 1373 if (r.isApplicationActivity() || (task != null && task.isApplicationTask())) { 1374 if (task != null) { 1375 final ActivityStack taskStack = task.stack; 1376 if (taskStack.isOnHomeDisplay()) { 1377 if (mFocusedStack != taskStack) { 1378 if (DEBUG_FOCUS || DEBUG_STACK) Slog.d(TAG, "adjustStackFocus: Setting " + 1379 "focused stack to r=" + r + " task=" + task); 1380 mFocusedStack = taskStack; 1381 } else { 1382 if (DEBUG_FOCUS || DEBUG_STACK) Slog.d(TAG, 1383 "adjustStackFocus: Focused stack already=" + mFocusedStack); 1384 } 1385 } 1386 return taskStack; 1387 } 1388 1389 final ActivityContainer container = r.mInitialActivityContainer; 1390 if (container != null) { 1391 // The first time put it on the desired stack, after this put on task stack. 1392 r.mInitialActivityContainer = null; 1393 return container.mStack; 1394 } 1395 1396 if (mFocusedStack != mHomeStack) { 1397 if (DEBUG_FOCUS || DEBUG_STACK) Slog.d(TAG, 1398 "adjustStackFocus: Have a focused stack=" + mFocusedStack); 1399 return mFocusedStack; 1400 } 1401 1402 final ArrayList<ActivityStack> homeDisplayStacks = mHomeStack.mStacks; 1403 for (int stackNdx = homeDisplayStacks.size() - 1; stackNdx >= 0; --stackNdx) { 1404 final ActivityStack stack = homeDisplayStacks.get(stackNdx); 1405 if (!stack.isHomeStack()) { 1406 if (DEBUG_FOCUS || DEBUG_STACK) Slog.d(TAG, 1407 "adjustStackFocus: Setting focused stack=" + stack); 1408 mFocusedStack = stack; 1409 return mFocusedStack; 1410 } 1411 } 1412 1413 // Need to create an app stack for this user. 1414 int stackId = createStackOnDisplay(getNextStackId(), Display.DEFAULT_DISPLAY); 1415 if (DEBUG_FOCUS || DEBUG_STACK) Slog.d(TAG, "adjustStackFocus: New stack r=" + r + 1416 " stackId=" + stackId); 1417 mFocusedStack = getStack(stackId); 1418 return mFocusedStack; 1419 } 1420 return mHomeStack; 1421 } 1422 1423 void setFocusedStack(ActivityRecord r) { 1424 if (r != null) { 1425 final TaskRecord task = r.task; 1426 boolean isHomeActivity = !r.isApplicationActivity(); 1427 if (!isHomeActivity && task != null) { 1428 isHomeActivity = !task.isApplicationTask(); 1429 } 1430 if (!isHomeActivity && task != null) { 1431 final ActivityRecord parent = task.stack.mActivityContainer.mParentActivity; 1432 isHomeActivity = parent != null && parent.isHomeActivity(); 1433 } 1434 moveHomeStack(isHomeActivity); 1435 } 1436 } 1437 1438 final int startActivityUncheckedLocked(ActivityRecord r, 1439 ActivityRecord sourceRecord, 1440 IVoiceInteractionSession voiceSession, IVoiceInteractor voiceInteractor, int startFlags, 1441 boolean doResume, Bundle options) { 1442 final Intent intent = r.intent; 1443 final int callingUid = r.launchedFromUid; 1444 1445 int launchFlags = intent.getFlags(); 1446 1447 // We'll invoke onUserLeaving before onPause only if the launching 1448 // activity did not explicitly state that this is an automated launch. 1449 mUserLeaving = (launchFlags&Intent.FLAG_ACTIVITY_NO_USER_ACTION) == 0; 1450 if (DEBUG_USER_LEAVING) Slog.v(TAG, "startActivity() => mUserLeaving=" + mUserLeaving); 1451 1452 // If the caller has asked not to resume at this point, we make note 1453 // of this in the record so that we can skip it when trying to find 1454 // the top running activity. 1455 if (!doResume) { 1456 r.delayedResume = true; 1457 } 1458 1459 ActivityRecord notTop = (launchFlags&Intent.FLAG_ACTIVITY_PREVIOUS_IS_TOP) != 0 ? r : null; 1460 1461 // If the onlyIfNeeded flag is set, then we can do this if the activity 1462 // being launched is the same as the one making the call... or, as 1463 // a special case, if we do not know the caller then we count the 1464 // current top activity as the caller. 1465 if ((startFlags&ActivityManager.START_FLAG_ONLY_IF_NEEDED) != 0) { 1466 ActivityRecord checkedCaller = sourceRecord; 1467 if (checkedCaller == null) { 1468 checkedCaller = getFocusedStack().topRunningNonDelayedActivityLocked(notTop); 1469 } 1470 if (!checkedCaller.realActivity.equals(r.realActivity)) { 1471 // Caller is not the same as launcher, so always needed. 1472 startFlags &= ~ActivityManager.START_FLAG_ONLY_IF_NEEDED; 1473 } 1474 } 1475 1476 switch (r.info.documentLaunchMode) { 1477 case ActivityInfo.DOCUMENT_LAUNCH_NONE: 1478 break; 1479 case ActivityInfo.DOCUMENT_LAUNCH_ALWAYS: 1480 intent.addFlags( 1481 Intent.FLAG_ACTIVITY_NEW_DOCUMENT | Intent.FLAG_ACTIVITY_MULTIPLE_TASK); 1482 break; 1483 case ActivityInfo.DOCUMENT_LAUNCH_INTO_EXISTING: 1484 intent.addFlags(Intent.FLAG_ACTIVITY_NEW_DOCUMENT); 1485 break; 1486 } 1487 final boolean newDocument = intent.isDocument(); 1488 if (sourceRecord == null) { 1489 // This activity is not being started from another... in this 1490 // case we -always- start a new task. 1491 if ((launchFlags & Intent.FLAG_ACTIVITY_NEW_TASK) == 0) { 1492 Slog.w(TAG, "startActivity called from non-Activity context; forcing " + 1493 "Intent.FLAG_ACTIVITY_NEW_TASK for: " + intent); 1494 launchFlags |= Intent.FLAG_ACTIVITY_NEW_TASK; 1495 } 1496 } else if (newDocument) { 1497 if (r.launchMode != ActivityInfo.LAUNCH_MULTIPLE) { 1498 Slog.w(TAG, "FLAG_ACTIVITY_NEW_DOCUMENT and launchMode != \"standard\""); 1499 r.launchMode = ActivityInfo.LAUNCH_MULTIPLE; 1500 } 1501 } else if (sourceRecord.launchMode == ActivityInfo.LAUNCH_SINGLE_INSTANCE) { 1502 // The original activity who is starting us is running as a single 1503 // instance... this new activity it is starting must go on its 1504 // own task. 1505 launchFlags |= Intent.FLAG_ACTIVITY_NEW_TASK; 1506 } else if (r.launchMode == ActivityInfo.LAUNCH_SINGLE_INSTANCE 1507 || r.launchMode == ActivityInfo.LAUNCH_SINGLE_TASK) { 1508 // The activity being started is a single instance... it always 1509 // gets launched into its own task. 1510 launchFlags |= Intent.FLAG_ACTIVITY_NEW_TASK; 1511 } 1512 1513 ActivityInfo newTaskInfo = null; 1514 Intent newTaskIntent = null; 1515 final ActivityStack sourceStack; 1516 if (sourceRecord != null) { 1517 if (sourceRecord.finishing) { 1518 // If the source is finishing, we can't further count it as our source. This 1519 // is because the task it is associated with may now be empty and on its way out, 1520 // so we don't want to blindly throw it in to that task. Instead we will take 1521 // the NEW_TASK flow and try to find a task for it. But save the task information 1522 // so it can be used when creating the new task. 1523 if ((launchFlags & Intent.FLAG_ACTIVITY_NEW_TASK) == 0) { 1524 Slog.w(TAG, "startActivity called from finishing " + sourceRecord 1525 + "; forcing " + "Intent.FLAG_ACTIVITY_NEW_TASK for: " + intent); 1526 launchFlags |= Intent.FLAG_ACTIVITY_NEW_TASK; 1527 newTaskInfo = sourceRecord.info; 1528 newTaskIntent = sourceRecord.task.intent; 1529 } 1530 sourceRecord = null; 1531 sourceStack = null; 1532 } else { 1533 sourceStack = sourceRecord.task.stack; 1534 } 1535 } else { 1536 sourceStack = null; 1537 } 1538 1539 if (r.resultTo != null && (launchFlags & Intent.FLAG_ACTIVITY_NEW_TASK) != 0) { 1540 // For whatever reason this activity is being launched into a new 1541 // task... yet the caller has requested a result back. Well, that 1542 // is pretty messed up, so instead immediately send back a cancel 1543 // and let the new task continue launched as normal without a 1544 // dependency on its originator. 1545 Slog.w(TAG, "Activity is launching as a new task, so cancelling activity result."); 1546 r.resultTo.task.stack.sendActivityResultLocked(-1, 1547 r.resultTo, r.resultWho, r.requestCode, 1548 Activity.RESULT_CANCELED, null); 1549 r.resultTo = null; 1550 } 1551 1552 boolean addingToTask = false; 1553 boolean movedHome = false; 1554 TaskRecord reuseTask = null; 1555 ActivityStack targetStack; 1556 if (((launchFlags & Intent.FLAG_ACTIVITY_NEW_TASK) != 0 && 1557 (launchFlags & Intent.FLAG_ACTIVITY_MULTIPLE_TASK) == 0) 1558 || r.launchMode == ActivityInfo.LAUNCH_SINGLE_TASK 1559 || r.launchMode == ActivityInfo.LAUNCH_SINGLE_INSTANCE) { 1560 // If bring to front is requested, and no result is requested, and 1561 // we can find a task that was started with this same 1562 // component, then instead of launching bring that one to the front. 1563 if (r.resultTo == null) { 1564 // See if there is a task to bring to the front. If this is 1565 // a SINGLE_INSTANCE activity, there can be one and only one 1566 // instance of it in the history, and it is always in its own 1567 // unique task, so we do a special search. 1568 ActivityRecord intentActivity = r.launchMode != ActivityInfo.LAUNCH_SINGLE_INSTANCE 1569 ? findTaskLocked(r) 1570 : findActivityLocked(intent, r.info); 1571 if (intentActivity != null) { 1572 if (isLockTaskModeViolation(intentActivity.task)) { 1573 Slog.e(TAG, "moveTaskToFront: Attempt to violate Lock Task Mode"); 1574 return ActivityManager.START_RETURN_LOCK_TASK_MODE_VIOLATION; 1575 } 1576 if (r.task == null) { 1577 r.task = intentActivity.task; 1578 } 1579 targetStack = intentActivity.task.stack; 1580 targetStack.mLastPausedActivity = null; 1581 if (DEBUG_TASKS) Slog.d(TAG, "Bring to front target: " + targetStack 1582 + " from " + intentActivity); 1583 targetStack.moveToFront(); 1584 if (intentActivity.task.intent == null) { 1585 // This task was started because of movement of 1586 // the activity based on affinity... now that we 1587 // are actually launching it, we can assign the 1588 // base intent. 1589 intentActivity.task.setIntent(intent, r.info); 1590 } 1591 // If the target task is not in the front, then we need 1592 // to bring it to the front... except... well, with 1593 // SINGLE_TASK_LAUNCH it's not entirely clear. We'd like 1594 // to have the same behavior as if a new instance was 1595 // being started, which means not bringing it to the front 1596 // if the caller is not itself in the front. 1597 final ActivityStack lastStack = getLastStack(); 1598 ActivityRecord curTop = lastStack == null? 1599 null : lastStack.topRunningNonDelayedActivityLocked(notTop); 1600 if (curTop != null && (curTop.task != intentActivity.task || 1601 curTop.task != lastStack.topTask())) { 1602 r.intent.addFlags(Intent.FLAG_ACTIVITY_BROUGHT_TO_FRONT); 1603 if (sourceRecord == null || (sourceStack.topActivity() != null && 1604 sourceStack.topActivity().task == sourceRecord.task)) { 1605 // We really do want to push this one into the 1606 // user's face, right now. 1607 movedHome = true; 1608 targetStack.moveTaskToFrontLocked(intentActivity.task, r, options); 1609 if ((launchFlags & 1610 (FLAG_ACTIVITY_NEW_TASK | FLAG_ACTIVITY_TASK_ON_HOME)) 1611 == (FLAG_ACTIVITY_NEW_TASK | FLAG_ACTIVITY_TASK_ON_HOME)) { 1612 // Caller wants to appear on home activity. 1613 intentActivity.task.mOnTopOfHome = true; 1614 } 1615 options = null; 1616 } 1617 } 1618 // If the caller has requested that the target task be 1619 // reset, then do so. 1620 if ((launchFlags&Intent.FLAG_ACTIVITY_RESET_TASK_IF_NEEDED) != 0) { 1621 intentActivity = targetStack.resetTaskIfNeededLocked(intentActivity, r); 1622 } 1623 if ((startFlags&ActivityManager.START_FLAG_ONLY_IF_NEEDED) != 0) { 1624 // We don't need to start a new activity, and 1625 // the client said not to do anything if that 1626 // is the case, so this is it! And for paranoia, make 1627 // sure we have correctly resumed the top activity. 1628 if (doResume) { 1629 resumeTopActivitiesLocked(targetStack, null, options); 1630 } else { 1631 ActivityOptions.abort(options); 1632 } 1633 return ActivityManager.START_RETURN_INTENT_TO_CALLER; 1634 } 1635 if ((launchFlags & 1636 (Intent.FLAG_ACTIVITY_NEW_TASK|Intent.FLAG_ACTIVITY_CLEAR_TASK)) 1637 == (Intent.FLAG_ACTIVITY_NEW_TASK|Intent.FLAG_ACTIVITY_CLEAR_TASK)) { 1638 // The caller has requested to completely replace any 1639 // existing task with its new activity. Well that should 1640 // not be too hard... 1641 reuseTask = intentActivity.task; 1642 reuseTask.performClearTaskLocked(); 1643 reuseTask.setIntent(r.intent, r.info); 1644 } else if ((launchFlags&Intent.FLAG_ACTIVITY_CLEAR_TOP) != 0 1645 || r.launchMode == ActivityInfo.LAUNCH_SINGLE_TASK 1646 || r.launchMode == ActivityInfo.LAUNCH_SINGLE_INSTANCE) { 1647 // In this situation we want to remove all activities 1648 // from the task up to the one being started. In most 1649 // cases this means we are resetting the task to its 1650 // initial state. 1651 ActivityRecord top = 1652 intentActivity.task.performClearTaskLocked(r, launchFlags); 1653 if (top != null) { 1654 if (top.frontOfTask) { 1655 // Activity aliases may mean we use different 1656 // intents for the top activity, so make sure 1657 // the task now has the identity of the new 1658 // intent. 1659 top.task.setIntent(r.intent, r.info); 1660 } 1661 ActivityStack.logStartActivity(EventLogTags.AM_NEW_INTENT, 1662 r, top.task); 1663 top.deliverNewIntentLocked(callingUid, r.intent); 1664 } else { 1665 // A special case: we need to 1666 // start the activity because it is not currently 1667 // running, and the caller has asked to clear the 1668 // current task to have this activity at the top. 1669 addingToTask = true; 1670 // Now pretend like this activity is being started 1671 // by the top of its task, so it is put in the 1672 // right place. 1673 sourceRecord = intentActivity; 1674 } 1675 } else if (r.realActivity.equals(intentActivity.task.realActivity)) { 1676 // In this case the top activity on the task is the 1677 // same as the one being launched, so we take that 1678 // as a request to bring the task to the foreground. 1679 // If the top activity in the task is the root 1680 // activity, deliver this new intent to it if it 1681 // desires. 1682 if (((launchFlags&Intent.FLAG_ACTIVITY_SINGLE_TOP) != 0 1683 || r.launchMode == ActivityInfo.LAUNCH_SINGLE_TOP) 1684 && intentActivity.realActivity.equals(r.realActivity)) { 1685 ActivityStack.logStartActivity(EventLogTags.AM_NEW_INTENT, r, 1686 intentActivity.task); 1687 if (intentActivity.frontOfTask) { 1688 intentActivity.task.setIntent(r.intent, r.info); 1689 } 1690 intentActivity.deliverNewIntentLocked(callingUid, r.intent); 1691 } else if (!r.intent.filterEquals(intentActivity.task.intent)) { 1692 // In this case we are launching the root activity 1693 // of the task, but with a different intent. We 1694 // should start a new instance on top. 1695 addingToTask = true; 1696 sourceRecord = intentActivity; 1697 } 1698 } else if ((launchFlags&Intent.FLAG_ACTIVITY_RESET_TASK_IF_NEEDED) == 0) { 1699 // In this case an activity is being launched in to an 1700 // existing task, without resetting that task. This 1701 // is typically the situation of launching an activity 1702 // from a notification or shortcut. We want to place 1703 // the new activity on top of the current task. 1704 addingToTask = true; 1705 sourceRecord = intentActivity; 1706 } else if (!intentActivity.task.rootWasReset) { 1707 // In this case we are launching in to an existing task 1708 // that has not yet been started from its front door. 1709 // The current task has been brought to the front. 1710 // Ideally, we'd probably like to place this new task 1711 // at the bottom of its stack, but that's a little hard 1712 // to do with the current organization of the code so 1713 // for now we'll just drop it. 1714 intentActivity.task.setIntent(r.intent, r.info); 1715 } 1716 if (!addingToTask && reuseTask == null) { 1717 // We didn't do anything... but it was needed (a.k.a., client 1718 // don't use that intent!) And for paranoia, make 1719 // sure we have correctly resumed the top activity. 1720 if (doResume) { 1721 targetStack.resumeTopActivityLocked(null, options); 1722 } else { 1723 ActivityOptions.abort(options); 1724 } 1725 return ActivityManager.START_TASK_TO_FRONT; 1726 } 1727 } 1728 } 1729 } 1730 1731 //String uri = r.intent.toURI(); 1732 //Intent intent2 = new Intent(uri); 1733 //Slog.i(TAG, "Given intent: " + r.intent); 1734 //Slog.i(TAG, "URI is: " + uri); 1735 //Slog.i(TAG, "To intent: " + intent2); 1736 1737 if (r.packageName != null) { 1738 // If the activity being launched is the same as the one currently 1739 // at the top, then we need to check if it should only be launched 1740 // once. 1741 ActivityStack topStack = getFocusedStack(); 1742 ActivityRecord top = topStack.topRunningNonDelayedActivityLocked(notTop); 1743 if (top != null && r.resultTo == null) { 1744 if (top.realActivity.equals(r.realActivity) && top.userId == r.userId) { 1745 if (top.app != null && top.app.thread != null) { 1746 if ((launchFlags & Intent.FLAG_ACTIVITY_SINGLE_TOP) != 0 1747 || r.launchMode == ActivityInfo.LAUNCH_SINGLE_TOP 1748 || r.launchMode == ActivityInfo.LAUNCH_SINGLE_TASK) { 1749 ActivityStack.logStartActivity(EventLogTags.AM_NEW_INTENT, top, 1750 top.task); 1751 // For paranoia, make sure we have correctly 1752 // resumed the top activity. 1753 topStack.mLastPausedActivity = null; 1754 if (doResume) { 1755 resumeTopActivitiesLocked(); 1756 } 1757 ActivityOptions.abort(options); 1758 if ((startFlags&ActivityManager.START_FLAG_ONLY_IF_NEEDED) != 0) { 1759 // We don't need to start a new activity, and 1760 // the client said not to do anything if that 1761 // is the case, so this is it! 1762 return ActivityManager.START_RETURN_INTENT_TO_CALLER; 1763 } 1764 top.deliverNewIntentLocked(callingUid, r.intent); 1765 return ActivityManager.START_DELIVERED_TO_TOP; 1766 } 1767 } 1768 } 1769 } 1770 1771 } else { 1772 if (r.resultTo != null) { 1773 r.resultTo.task.stack.sendActivityResultLocked(-1, r.resultTo, r.resultWho, 1774 r.requestCode, Activity.RESULT_CANCELED, null); 1775 } 1776 ActivityOptions.abort(options); 1777 return ActivityManager.START_CLASS_NOT_FOUND; 1778 } 1779 1780 boolean newTask = false; 1781 boolean keepCurTransition = false; 1782 1783 // Should this be considered a new task? 1784 if (r.resultTo == null && !addingToTask 1785 && (launchFlags&Intent.FLAG_ACTIVITY_NEW_TASK) != 0) { 1786 if (isLockTaskModeViolation(reuseTask)) { 1787 Slog.e(TAG, "Attempted Lock Task Mode violation r=" + r); 1788 return ActivityManager.START_RETURN_LOCK_TASK_MODE_VIOLATION; 1789 } 1790 targetStack = adjustStackFocus(r); 1791 targetStack.moveToFront(); 1792 if (reuseTask == null) { 1793 r.setTask(targetStack.createTaskRecord(getNextTaskId(), 1794 newTaskInfo != null ? newTaskInfo : r.info, 1795 newTaskIntent != null ? newTaskIntent : intent, 1796 voiceSession, voiceInteractor, true), null, true); 1797 if (DEBUG_TASKS) Slog.v(TAG, "Starting new activity " + r + " in new task " + 1798 r.task); 1799 } else { 1800 r.setTask(reuseTask, reuseTask, true); 1801 } 1802 newTask = true; 1803 if (!movedHome) { 1804 if ((launchFlags & 1805 (Intent.FLAG_ACTIVITY_NEW_TASK|Intent.FLAG_ACTIVITY_TASK_ON_HOME)) 1806 == (Intent.FLAG_ACTIVITY_NEW_TASK|Intent.FLAG_ACTIVITY_TASK_ON_HOME)) { 1807 // Caller wants to appear on home activity, so before starting 1808 // their own activity we will bring home to the front. 1809 r.task.mOnTopOfHome = r.task.stack.isOnHomeDisplay(); 1810 } 1811 } 1812 } else if (sourceRecord != null) { 1813 TaskRecord sourceTask = sourceRecord.task; 1814 if (isLockTaskModeViolation(sourceTask)) { 1815 Slog.e(TAG, "Attempted Lock Task Mode violation r=" + r); 1816 return ActivityManager.START_RETURN_LOCK_TASK_MODE_VIOLATION; 1817 } 1818 targetStack = sourceTask.stack; 1819 targetStack.moveToFront(); 1820 mWindowManager.moveTaskToTop(targetStack.topTask().taskId); 1821 if (!addingToTask && 1822 (launchFlags&Intent.FLAG_ACTIVITY_CLEAR_TOP) != 0) { 1823 // In this case, we are adding the activity to an existing 1824 // task, but the caller has asked to clear that task if the 1825 // activity is already running. 1826 ActivityRecord top = sourceTask.performClearTaskLocked(r, launchFlags); 1827 keepCurTransition = true; 1828 if (top != null) { 1829 ActivityStack.logStartActivity(EventLogTags.AM_NEW_INTENT, r, top.task); 1830 top.deliverNewIntentLocked(callingUid, r.intent); 1831 // For paranoia, make sure we have correctly 1832 // resumed the top activity. 1833 targetStack.mLastPausedActivity = null; 1834 if (doResume) { 1835 targetStack.resumeTopActivityLocked(null); 1836 } 1837 ActivityOptions.abort(options); 1838 return ActivityManager.START_DELIVERED_TO_TOP; 1839 } 1840 } else if (!addingToTask && 1841 (launchFlags&Intent.FLAG_ACTIVITY_REORDER_TO_FRONT) != 0) { 1842 // In this case, we are launching an activity in our own task 1843 // that may already be running somewhere in the history, and 1844 // we want to shuffle it to the front of the stack if so. 1845 final ActivityRecord top = sourceTask.findActivityInHistoryLocked(r); 1846 if (top != null) { 1847 final TaskRecord task = top.task; 1848 task.moveActivityToFrontLocked(top); 1849 ActivityStack.logStartActivity(EventLogTags.AM_NEW_INTENT, r, task); 1850 top.updateOptionsLocked(options); 1851 top.deliverNewIntentLocked(callingUid, r.intent); 1852 targetStack.mLastPausedActivity = null; 1853 if (doResume) { 1854 targetStack.resumeTopActivityLocked(null); 1855 } 1856 return ActivityManager.START_DELIVERED_TO_TOP; 1857 } 1858 } 1859 // An existing activity is starting this new activity, so we want 1860 // to keep the new one in the same task as the one that is starting 1861 // it. 1862 r.setTask(sourceTask, sourceRecord.thumbHolder, false); 1863 if (DEBUG_TASKS) Slog.v(TAG, "Starting new activity " + r 1864 + " in existing task " + r.task + " from source " + sourceRecord); 1865 1866 } else { 1867 // This not being started from an existing activity, and not part 1868 // of a new task... just put it in the top task, though these days 1869 // this case should never happen. 1870 targetStack = adjustStackFocus(r); 1871 targetStack.moveToFront(); 1872 ActivityRecord prev = targetStack.topActivity(); 1873 r.setTask(prev != null ? prev.task 1874 : targetStack.createTaskRecord(getNextTaskId(), r.info, intent, null, null, true), 1875 null, true); 1876 mWindowManager.moveTaskToTop(r.task.taskId); 1877 if (DEBUG_TASKS) Slog.v(TAG, "Starting new activity " + r 1878 + " in new guessed " + r.task); 1879 } 1880 1881 mService.grantUriPermissionFromIntentLocked(callingUid, r.packageName, 1882 intent, r.getUriPermissionsLocked()); 1883 1884 if (newTask) { 1885 EventLog.writeEvent(EventLogTags.AM_CREATE_TASK, r.userId, r.task.taskId); 1886 } 1887 ActivityStack.logStartActivity(EventLogTags.AM_CREATE_ACTIVITY, r, r.task); 1888 targetStack.mLastPausedActivity = null; 1889 targetStack.startActivityLocked(r, newTask, doResume, keepCurTransition, options); 1890 mService.setFocusedActivityLocked(r); 1891 return ActivityManager.START_SUCCESS; 1892 } 1893 1894 void acquireLaunchWakelock() { 1895 if (VALIDATE_WAKE_LOCK_CALLER && Binder.getCallingUid() != Process.myUid()) { 1896 throw new IllegalStateException("Calling must be system uid"); 1897 } 1898 mLaunchingActivity.acquire(); 1899 if (!mHandler.hasMessages(LAUNCH_TIMEOUT_MSG)) { 1900 // To be safe, don't allow the wake lock to be held for too long. 1901 mHandler.sendEmptyMessageDelayed(LAUNCH_TIMEOUT_MSG, LAUNCH_TIMEOUT); 1902 } 1903 } 1904 1905 // Checked. 1906 final ActivityRecord activityIdleInternalLocked(final IBinder token, boolean fromTimeout, 1907 Configuration config) { 1908 if (localLOGV) Slog.v(TAG, "Activity idle: " + token); 1909 1910 ArrayList<ActivityRecord> stops = null; 1911 ArrayList<ActivityRecord> finishes = null; 1912 ArrayList<UserStartedState> startingUsers = null; 1913 int NS = 0; 1914 int NF = 0; 1915 boolean booting = false; 1916 boolean enableScreen = false; 1917 boolean activityRemoved = false; 1918 1919 ActivityRecord r = ActivityRecord.forToken(token); 1920 if (r != null) { 1921 if (DEBUG_IDLE) Slog.d(TAG, "activityIdleInternalLocked: Callers=" + 1922 Debug.getCallers(4)); 1923 mHandler.removeMessages(IDLE_TIMEOUT_MSG, r); 1924 r.finishLaunchTickingLocked(); 1925 if (fromTimeout) { 1926 reportActivityLaunchedLocked(fromTimeout, r, -1, -1); 1927 } 1928 1929 // This is a hack to semi-deal with a race condition 1930 // in the client where it can be constructed with a 1931 // newer configuration from when we asked it to launch. 1932 // We'll update with whatever configuration it now says 1933 // it used to launch. 1934 if (config != null) { 1935 r.configuration = config; 1936 } 1937 1938 // We are now idle. If someone is waiting for a thumbnail from 1939 // us, we can now deliver. 1940 r.idle = true; 1941 1942 //Slog.i(TAG, "IDLE: mBooted=" + mBooted + ", fromTimeout=" + fromTimeout); 1943 if (!mService.mBooted && isFrontStack(r.task.stack)) { 1944 mService.mBooted = true; 1945 enableScreen = true; 1946 } 1947 } 1948 1949 if (allResumedActivitiesIdle()) { 1950 if (r != null) { 1951 mService.scheduleAppGcsLocked(); 1952 } 1953 1954 if (mLaunchingActivity.isHeld()) { 1955 mHandler.removeMessages(LAUNCH_TIMEOUT_MSG); 1956 if (VALIDATE_WAKE_LOCK_CALLER && 1957 Binder.getCallingUid() != Process.myUid()) { 1958 throw new IllegalStateException("Calling must be system uid"); 1959 } 1960 mLaunchingActivity.release(); 1961 } 1962 ensureActivitiesVisibleLocked(null, 0); 1963 } 1964 1965 // Atomically retrieve all of the other things to do. 1966 stops = processStoppingActivitiesLocked(true); 1967 NS = stops != null ? stops.size() : 0; 1968 if ((NF=mFinishingActivities.size()) > 0) { 1969 finishes = new ArrayList<ActivityRecord>(mFinishingActivities); 1970 mFinishingActivities.clear(); 1971 } 1972 1973 if (isFrontStack(mHomeStack)) { 1974 booting = mService.mBooting; 1975 mService.mBooting = false; 1976 } 1977 1978 if (mStartingUsers.size() > 0) { 1979 startingUsers = new ArrayList<UserStartedState>(mStartingUsers); 1980 mStartingUsers.clear(); 1981 } 1982 1983 // Stop any activities that are scheduled to do so but have been 1984 // waiting for the next one to start. 1985 for (int i = 0; i < NS; i++) { 1986 r = stops.get(i); 1987 final ActivityStack stack = r.task.stack; 1988 if (r.finishing) { 1989 stack.finishCurrentActivityLocked(r, ActivityStack.FINISH_IMMEDIATELY, false); 1990 } else { 1991 stack.stopActivityLocked(r); 1992 } 1993 } 1994 1995 // Finish any activities that are scheduled to do so but have been 1996 // waiting for the next one to start. 1997 for (int i = 0; i < NF; i++) { 1998 r = finishes.get(i); 1999 activityRemoved |= r.task.stack.destroyActivityLocked(r, true, false, "finish-idle"); 2000 } 2001 2002 if (booting) { 2003 mService.finishBooting(); 2004 } else { 2005 // Complete user switch 2006 if (startingUsers != null) { 2007 for (int i = 0; i < startingUsers.size(); i++) { 2008 mService.finishUserSwitch(startingUsers.get(i)); 2009 } 2010 } 2011 // Complete starting up of background users 2012 if (mStartingBackgroundUsers.size() > 0) { 2013 startingUsers = new ArrayList<UserStartedState>(mStartingBackgroundUsers); 2014 mStartingBackgroundUsers.clear(); 2015 for (int i = 0; i < startingUsers.size(); i++) { 2016 mService.finishUserBoot(startingUsers.get(i)); 2017 } 2018 } 2019 } 2020 2021 mService.trimApplications(); 2022 //dump(); 2023 //mWindowManager.dump(); 2024 2025 if (enableScreen) { 2026 mService.enableScreenAfterBoot(); 2027 } 2028 2029 if (activityRemoved) { 2030 resumeTopActivitiesLocked(); 2031 } 2032 2033 return r; 2034 } 2035 2036 boolean handleAppDiedLocked(ProcessRecord app) { 2037 boolean hasVisibleActivities = false; 2038 for (int displayNdx = mActivityDisplays.size() - 1; displayNdx >= 0; --displayNdx) { 2039 final ArrayList<ActivityStack> stacks = mActivityDisplays.valueAt(displayNdx).mStacks; 2040 for (int stackNdx = stacks.size() - 1; stackNdx >= 0; --stackNdx) { 2041 hasVisibleActivities |= stacks.get(stackNdx).handleAppDiedLocked(app); 2042 } 2043 } 2044 return hasVisibleActivities; 2045 } 2046 2047 void closeSystemDialogsLocked() { 2048 for (int displayNdx = mActivityDisplays.size() - 1; displayNdx >= 0; --displayNdx) { 2049 final ArrayList<ActivityStack> stacks = mActivityDisplays.valueAt(displayNdx).mStacks; 2050 for (int stackNdx = stacks.size() - 1; stackNdx >= 0; --stackNdx) { 2051 stacks.get(stackNdx).closeSystemDialogsLocked(); 2052 } 2053 } 2054 } 2055 2056 void removeUserLocked(int userId) { 2057 mUserStackInFront.delete(userId); 2058 } 2059 2060 /** 2061 * @return true if some activity was finished (or would have finished if doit were true). 2062 */ 2063 boolean forceStopPackageLocked(String name, boolean doit, boolean evenPersistent, int userId) { 2064 boolean didSomething = false; 2065 for (int displayNdx = mActivityDisplays.size() - 1; displayNdx >= 0; --displayNdx) { 2066 final ArrayList<ActivityStack> stacks = mActivityDisplays.valueAt(displayNdx).mStacks; 2067 final int numStacks = stacks.size(); 2068 for (int stackNdx = 0; stackNdx < numStacks; ++stackNdx) { 2069 final ActivityStack stack = stacks.get(stackNdx); 2070 if (stack.forceStopPackageLocked(name, doit, evenPersistent, userId)) { 2071 didSomething = true; 2072 } 2073 } 2074 } 2075 return didSomething; 2076 } 2077 2078 void updatePreviousProcessLocked(ActivityRecord r) { 2079 // Now that this process has stopped, we may want to consider 2080 // it to be the previous app to try to keep around in case 2081 // the user wants to return to it. 2082 2083 // First, found out what is currently the foreground app, so that 2084 // we don't blow away the previous app if this activity is being 2085 // hosted by the process that is actually still the foreground. 2086 ProcessRecord fgApp = null; 2087 for (int displayNdx = mActivityDisplays.size() - 1; displayNdx >= 0; --displayNdx) { 2088 final ArrayList<ActivityStack> stacks = mActivityDisplays.valueAt(displayNdx).mStacks; 2089 for (int stackNdx = stacks.size() - 1; stackNdx >= 0; --stackNdx) { 2090 final ActivityStack stack = stacks.get(stackNdx); 2091 if (isFrontStack(stack)) { 2092 if (stack.mResumedActivity != null) { 2093 fgApp = stack.mResumedActivity.app; 2094 } else if (stack.mPausingActivity != null) { 2095 fgApp = stack.mPausingActivity.app; 2096 } 2097 break; 2098 } 2099 } 2100 } 2101 2102 // Now set this one as the previous process, only if that really 2103 // makes sense to. 2104 if (r.app != null && fgApp != null && r.app != fgApp 2105 && r.lastVisibleTime > mService.mPreviousProcessVisibleTime 2106 && r.app != mService.mHomeProcess) { 2107 mService.mPreviousProcess = r.app; 2108 mService.mPreviousProcessVisibleTime = r.lastVisibleTime; 2109 } 2110 } 2111 2112 boolean resumeTopActivitiesLocked() { 2113 return resumeTopActivitiesLocked(null, null, null); 2114 } 2115 2116 boolean resumeTopActivitiesLocked(ActivityStack targetStack, ActivityRecord target, 2117 Bundle targetOptions) { 2118 if (targetStack == null) { 2119 targetStack = getFocusedStack(); 2120 } 2121 // Do targetStack first. 2122 boolean result = false; 2123 if (isFrontStack(targetStack)) { 2124 result = targetStack.resumeTopActivityLocked(target, targetOptions); 2125 } 2126 for (int displayNdx = mActivityDisplays.size() - 1; displayNdx >= 0; --displayNdx) { 2127 final ArrayList<ActivityStack> stacks = mActivityDisplays.valueAt(displayNdx).mStacks; 2128 for (int stackNdx = stacks.size() - 1; stackNdx >= 0; --stackNdx) { 2129 final ActivityStack stack = stacks.get(stackNdx); 2130 if (stack == targetStack) { 2131 // Already started above. 2132 continue; 2133 } 2134 if (isFrontStack(stack)) { 2135 stack.resumeTopActivityLocked(null); 2136 } 2137 } 2138 } 2139 return result; 2140 } 2141 2142 void finishTopRunningActivityLocked(ProcessRecord app) { 2143 for (int displayNdx = mActivityDisplays.size() - 1; displayNdx >= 0; --displayNdx) { 2144 final ArrayList<ActivityStack> stacks = mActivityDisplays.valueAt(displayNdx).mStacks; 2145 final int numStacks = stacks.size(); 2146 for (int stackNdx = 0; stackNdx < numStacks; ++stackNdx) { 2147 final ActivityStack stack = stacks.get(stackNdx); 2148 stack.finishTopRunningActivityLocked(app); 2149 } 2150 } 2151 } 2152 2153 void findTaskToMoveToFrontLocked(TaskRecord task, int flags, Bundle options) { 2154 if ((flags & ActivityManager.MOVE_TASK_NO_USER_ACTION) == 0) { 2155 mUserLeaving = true; 2156 } 2157 if ((flags & ActivityManager.MOVE_TASK_WITH_HOME) != 0) { 2158 // Caller wants the home activity moved with it. To accomplish this, 2159 // we'll just indicate that this task returns to the home task. 2160 task.mOnTopOfHome = true; 2161 } 2162 task.stack.moveTaskToFrontLocked(task, null, options); 2163 if (DEBUG_STACK) Slog.d(TAG, "findTaskToMoveToFront: moved to front of stack=" 2164 + task.stack); 2165 } 2166 2167 ActivityStack getStack(int stackId) { 2168 ActivityContainer activityContainer = mActivityContainers.get(stackId); 2169 if (activityContainer != null) { 2170 return activityContainer.mStack; 2171 } 2172 return null; 2173 } 2174 2175 ArrayList<ActivityStack> getStacks() { 2176 ArrayList<ActivityStack> allStacks = new ArrayList<ActivityStack>(); 2177 for (int displayNdx = mActivityDisplays.size() - 1; displayNdx >= 0; --displayNdx) { 2178 allStacks.addAll(mActivityDisplays.valueAt(displayNdx).mStacks); 2179 } 2180 return allStacks; 2181 } 2182 2183 IBinder getHomeActivityToken() { 2184 final ArrayList<TaskRecord> tasks = mHomeStack.getAllTasks(); 2185 for (int taskNdx = tasks.size() - 1; taskNdx >= 0; --taskNdx) { 2186 final TaskRecord task = tasks.get(taskNdx); 2187 if (task.isHomeTask()) { 2188 final ArrayList<ActivityRecord> activities = task.mActivities; 2189 for (int activityNdx = activities.size() - 1; activityNdx >= 0; --activityNdx) { 2190 final ActivityRecord r = activities.get(activityNdx); 2191 if (r.isHomeActivity()) { 2192 return r.appToken; 2193 } 2194 } 2195 } 2196 } 2197 return null; 2198 } 2199 2200 ActivityContainer createActivityContainer(ActivityRecord parentActivity, 2201 IActivityContainerCallback callback) { 2202 ActivityContainer activityContainer = new VirtualActivityContainer(parentActivity, callback); 2203 mActivityContainers.put(activityContainer.mStackId, activityContainer); 2204 parentActivity.mChildContainers.add(activityContainer); 2205 return activityContainer; 2206 } 2207 2208 void removeChildActivityContainers(ActivityRecord parentActivity) { 2209 final ArrayList<ActivityContainer> childStacks = parentActivity.mChildContainers; 2210 for (int containerNdx = childStacks.size() - 1; containerNdx >= 0; --containerNdx) { 2211 ActivityContainer container = childStacks.remove(containerNdx); 2212 container.release(); 2213 } 2214 } 2215 2216 void deleteActivityContainer(IActivityContainer container) { 2217 ActivityContainer activityContainer = (ActivityContainer)container; 2218 if (activityContainer != null) { 2219 activityContainer.mStack.finishAllActivitiesLocked(); 2220 final ActivityRecord parent = activityContainer.mParentActivity; 2221 if (parent != null) { 2222 parent.mChildContainers.remove(activityContainer); 2223 } 2224 final int stackId = activityContainer.mStackId; 2225 mActivityContainers.remove(stackId); 2226 mWindowManager.removeStack(stackId); 2227 } 2228 } 2229 2230 private int createStackOnDisplay(int stackId, int displayId) { 2231 ActivityDisplay activityDisplay = mActivityDisplays.get(displayId); 2232 if (activityDisplay == null) { 2233 return -1; 2234 } 2235 2236 ActivityContainer activityContainer = new ActivityContainer(stackId); 2237 mActivityContainers.put(stackId, activityContainer); 2238 activityContainer.attachToDisplayLocked(activityDisplay); 2239 return stackId; 2240 } 2241 2242 int getNextStackId() { 2243 while (true) { 2244 if (++mLastStackId <= HOME_STACK_ID) { 2245 mLastStackId = HOME_STACK_ID + 1; 2246 } 2247 if (getStack(mLastStackId) == null) { 2248 break; 2249 } 2250 } 2251 return mLastStackId; 2252 } 2253 2254 void moveTaskToStack(int taskId, int stackId, boolean toTop) { 2255 final TaskRecord task = anyTaskForIdLocked(taskId); 2256 if (task == null) { 2257 return; 2258 } 2259 final ActivityStack stack = getStack(stackId); 2260 if (stack == null) { 2261 Slog.w(TAG, "moveTaskToStack: no stack for id=" + stackId); 2262 return; 2263 } 2264 task.stack.removeTask(task); 2265 stack.addTask(task, toTop, true); 2266 mWindowManager.addTask(taskId, stackId, toTop); 2267 resumeTopActivitiesLocked(); 2268 } 2269 2270 ActivityRecord findTaskLocked(ActivityRecord r) { 2271 if (DEBUG_TASKS) Slog.d(TAG, "Looking for task of " + r); 2272 for (int displayNdx = mActivityDisplays.size() - 1; displayNdx >= 0; --displayNdx) { 2273 final ArrayList<ActivityStack> stacks = mActivityDisplays.valueAt(displayNdx).mStacks; 2274 for (int stackNdx = stacks.size() - 1; stackNdx >= 0; --stackNdx) { 2275 final ActivityStack stack = stacks.get(stackNdx); 2276 if (!r.isApplicationActivity() && !stack.isHomeStack()) { 2277 if (DEBUG_TASKS) Slog.d(TAG, "Skipping stack: " + stack); 2278 continue; 2279 } 2280 final ActivityRecord ar = stack.findTaskLocked(r); 2281 if (ar != null) { 2282 return ar; 2283 } 2284 } 2285 } 2286 if (DEBUG_TASKS) Slog.d(TAG, "No task found"); 2287 return null; 2288 } 2289 2290 ActivityRecord findActivityLocked(Intent intent, ActivityInfo info) { 2291 for (int displayNdx = mActivityDisplays.size() - 1; displayNdx >= 0; --displayNdx) { 2292 final ArrayList<ActivityStack> stacks = mActivityDisplays.valueAt(displayNdx).mStacks; 2293 for (int stackNdx = stacks.size() - 1; stackNdx >= 0; --stackNdx) { 2294 final ActivityRecord ar = stacks.get(stackNdx).findActivityLocked(intent, info); 2295 if (ar != null) { 2296 return ar; 2297 } 2298 } 2299 } 2300 return null; 2301 } 2302 2303 void goingToSleepLocked() { 2304 scheduleSleepTimeout(); 2305 if (!mGoingToSleep.isHeld()) { 2306 mGoingToSleep.acquire(); 2307 if (mLaunchingActivity.isHeld()) { 2308 if (VALIDATE_WAKE_LOCK_CALLER && Binder.getCallingUid() != Process.myUid()) { 2309 throw new IllegalStateException("Calling must be system uid"); 2310 } 2311 mLaunchingActivity.release(); 2312 mService.mHandler.removeMessages(LAUNCH_TIMEOUT_MSG); 2313 } 2314 } 2315 checkReadyForSleepLocked(); 2316 setLockTaskModeLocked(null); 2317 } 2318 2319 boolean shutdownLocked(int timeout) { 2320 goingToSleepLocked(); 2321 2322 boolean timedout = false; 2323 final long endTime = System.currentTimeMillis() + timeout; 2324 while (true) { 2325 boolean cantShutdown = false; 2326 for (int displayNdx = mActivityDisplays.size() - 1; displayNdx >= 0; --displayNdx) { 2327 final ArrayList<ActivityStack> stacks = mActivityDisplays.valueAt(displayNdx).mStacks; 2328 for (int stackNdx = stacks.size() - 1; stackNdx >= 0; --stackNdx) { 2329 cantShutdown |= stacks.get(stackNdx).checkReadyForSleepLocked(); 2330 } 2331 } 2332 if (cantShutdown) { 2333 long timeRemaining = endTime - System.currentTimeMillis(); 2334 if (timeRemaining > 0) { 2335 try { 2336 mService.wait(timeRemaining); 2337 } catch (InterruptedException e) { 2338 } 2339 } else { 2340 Slog.w(TAG, "Activity manager shutdown timed out"); 2341 timedout = true; 2342 break; 2343 } 2344 } else { 2345 break; 2346 } 2347 } 2348 2349 // Force checkReadyForSleep to complete. 2350 mSleepTimeout = true; 2351 checkReadyForSleepLocked(); 2352 2353 return timedout; 2354 } 2355 2356 void comeOutOfSleepIfNeededLocked() { 2357 removeSleepTimeouts(); 2358 if (mGoingToSleep.isHeld()) { 2359 mGoingToSleep.release(); 2360 } 2361 for (int displayNdx = mActivityDisplays.size() - 1; displayNdx >= 0; --displayNdx) { 2362 final ArrayList<ActivityStack> stacks = mActivityDisplays.valueAt(displayNdx).mStacks; 2363 for (int stackNdx = stacks.size() - 1; stackNdx >= 0; --stackNdx) { 2364 final ActivityStack stack = stacks.get(stackNdx); 2365 stack.awakeFromSleepingLocked(); 2366 if (isFrontStack(stack)) { 2367 resumeTopActivitiesLocked(); 2368 } 2369 } 2370 } 2371 mGoingToSleepActivities.clear(); 2372 } 2373 2374 void activitySleptLocked(ActivityRecord r) { 2375 mGoingToSleepActivities.remove(r); 2376 checkReadyForSleepLocked(); 2377 } 2378 2379 void checkReadyForSleepLocked() { 2380 if (!mService.isSleepingOrShuttingDown()) { 2381 // Do not care. 2382 return; 2383 } 2384 2385 if (!mSleepTimeout) { 2386 boolean dontSleep = false; 2387 for (int displayNdx = mActivityDisplays.size() - 1; displayNdx >= 0; --displayNdx) { 2388 final ArrayList<ActivityStack> stacks = mActivityDisplays.valueAt(displayNdx).mStacks; 2389 for (int stackNdx = stacks.size() - 1; stackNdx >= 0; --stackNdx) { 2390 dontSleep |= stacks.get(stackNdx).checkReadyForSleepLocked(); 2391 } 2392 } 2393 2394 if (mStoppingActivities.size() > 0) { 2395 // Still need to tell some activities to stop; can't sleep yet. 2396 if (DEBUG_PAUSE) Slog.v(TAG, "Sleep still need to stop " 2397 + mStoppingActivities.size() + " activities"); 2398 scheduleIdleLocked(); 2399 dontSleep = true; 2400 } 2401 2402 if (mGoingToSleepActivities.size() > 0) { 2403 // Still need to tell some activities to sleep; can't sleep yet. 2404 if (DEBUG_PAUSE) Slog.v(TAG, "Sleep still need to sleep " 2405 + mGoingToSleepActivities.size() + " activities"); 2406 dontSleep = true; 2407 } 2408 2409 if (dontSleep) { 2410 return; 2411 } 2412 } 2413 2414 for (int displayNdx = mActivityDisplays.size() - 1; displayNdx >= 0; --displayNdx) { 2415 final ArrayList<ActivityStack> stacks = mActivityDisplays.valueAt(displayNdx).mStacks; 2416 for (int stackNdx = stacks.size() - 1; stackNdx >= 0; --stackNdx) { 2417 stacks.get(stackNdx).goToSleep(); 2418 } 2419 } 2420 2421 removeSleepTimeouts(); 2422 2423 if (mGoingToSleep.isHeld()) { 2424 mGoingToSleep.release(); 2425 } 2426 if (mService.mShuttingDown) { 2427 mService.notifyAll(); 2428 } 2429 } 2430 2431 boolean reportResumedActivityLocked(ActivityRecord r) { 2432 final ActivityStack stack = r.task.stack; 2433 if (isFrontStack(stack)) { 2434 mService.updateUsageStats(r, true); 2435 } 2436 if (allResumedActivitiesComplete()) { 2437 ensureActivitiesVisibleLocked(null, 0); 2438 mWindowManager.executeAppTransition(); 2439 return true; 2440 } 2441 return false; 2442 } 2443 2444 void handleAppCrashLocked(ProcessRecord app) { 2445 for (int displayNdx = mActivityDisplays.size() - 1; displayNdx >= 0; --displayNdx) { 2446 final ArrayList<ActivityStack> stacks = mActivityDisplays.valueAt(displayNdx).mStacks; 2447 final int numStacks = stacks.size(); 2448 for (int stackNdx = 0; stackNdx < numStacks; ++stackNdx) { 2449 final ActivityStack stack = stacks.get(stackNdx); 2450 stack.handleAppCrashLocked(app); 2451 } 2452 } 2453 } 2454 2455 void ensureActivitiesVisibleLocked(ActivityRecord starting, int configChanges) { 2456 // First the front stacks. In case any are not fullscreen and are in front of home. 2457 for (int displayNdx = mActivityDisplays.size() - 1; displayNdx >= 0; --displayNdx) { 2458 final ArrayList<ActivityStack> stacks = mActivityDisplays.valueAt(displayNdx).mStacks; 2459 final int topStackNdx = stacks.size() - 1; 2460 for (int stackNdx = topStackNdx; stackNdx >= 0; --stackNdx) { 2461 final ActivityStack stack = stacks.get(stackNdx); 2462 stack.ensureActivitiesVisibleLocked(starting, configChanges); 2463 } 2464 } 2465 } 2466 2467 void scheduleDestroyAllActivities(ProcessRecord app, String reason) { 2468 for (int displayNdx = mActivityDisplays.size() - 1; displayNdx >= 0; --displayNdx) { 2469 final ArrayList<ActivityStack> stacks = mActivityDisplays.valueAt(displayNdx).mStacks; 2470 final int numStacks = stacks.size(); 2471 for (int stackNdx = 0; stackNdx < numStacks; ++stackNdx) { 2472 final ActivityStack stack = stacks.get(stackNdx); 2473 stack.scheduleDestroyActivities(app, false, reason); 2474 } 2475 } 2476 } 2477 2478 boolean switchUserLocked(int userId, UserStartedState uss) { 2479 mUserStackInFront.put(mCurrentUser, getFocusedStack().getStackId()); 2480 final int restoreStackId = mUserStackInFront.get(userId, HOME_STACK_ID); 2481 mCurrentUser = userId; 2482 2483 mStartingUsers.add(uss); 2484 for (int displayNdx = mActivityDisplays.size() - 1; displayNdx >= 0; --displayNdx) { 2485 final ArrayList<ActivityStack> stacks = mActivityDisplays.valueAt(displayNdx).mStacks; 2486 for (int stackNdx = stacks.size() - 1; stackNdx >= 0; --stackNdx) { 2487 final ActivityStack stack = stacks.get(stackNdx); 2488 stack.switchUserLocked(userId); 2489 TaskRecord task = stack.topTask(); 2490 if (task != null) { 2491 mWindowManager.moveTaskToTop(task.taskId); 2492 } 2493 } 2494 } 2495 2496 ActivityStack stack = getStack(restoreStackId); 2497 if (stack == null) { 2498 stack = mHomeStack; 2499 } 2500 final boolean homeInFront = stack.isHomeStack(); 2501 if (stack.isOnHomeDisplay()) { 2502 moveHomeStack(homeInFront); 2503 TaskRecord task = stack.topTask(); 2504 if (task != null) { 2505 mWindowManager.moveTaskToTop(task.taskId); 2506 } 2507 } else { 2508 // Stack was moved to another display while user was swapped out. 2509 resumeHomeActivity(null); 2510 } 2511 return homeInFront; 2512 } 2513 2514 /** 2515 * Add background users to send boot completed events to. 2516 * @param userId The user being started in the background 2517 * @param uss The state object for the user. 2518 */ 2519 public void startBackgroundUserLocked(int userId, UserStartedState uss) { 2520 mStartingBackgroundUsers.add(uss); 2521 } 2522 2523 final ArrayList<ActivityRecord> processStoppingActivitiesLocked(boolean remove) { 2524 int N = mStoppingActivities.size(); 2525 if (N <= 0) return null; 2526 2527 ArrayList<ActivityRecord> stops = null; 2528 2529 final boolean nowVisible = allResumedActivitiesVisible(); 2530 for (int i=0; i<N; i++) { 2531 ActivityRecord s = mStoppingActivities.get(i); 2532 if (localLOGV) Slog.v(TAG, "Stopping " + s + ": nowVisible=" 2533 + nowVisible + " waitingVisible=" + s.waitingVisible 2534 + " finishing=" + s.finishing); 2535 if (s.waitingVisible && nowVisible) { 2536 mWaitingVisibleActivities.remove(s); 2537 s.waitingVisible = false; 2538 if (s.finishing) { 2539 // If this activity is finishing, it is sitting on top of 2540 // everyone else but we now know it is no longer needed... 2541 // so get rid of it. Otherwise, we need to go through the 2542 // normal flow and hide it once we determine that it is 2543 // hidden by the activities in front of it. 2544 if (localLOGV) Slog.v(TAG, "Before stopping, can hide: " + s); 2545 mWindowManager.setAppVisibility(s.appToken, false); 2546 } 2547 } 2548 if ((!s.waitingVisible || mService.isSleepingOrShuttingDown()) && remove) { 2549 if (localLOGV) Slog.v(TAG, "Ready to stop: " + s); 2550 if (stops == null) { 2551 stops = new ArrayList<ActivityRecord>(); 2552 } 2553 stops.add(s); 2554 mStoppingActivities.remove(i); 2555 N--; 2556 i--; 2557 } 2558 } 2559 2560 return stops; 2561 } 2562 2563 void validateTopActivitiesLocked() { 2564 // FIXME 2565/* for (int stackNdx = stacks.size() - 1; stackNdx >= 0; --stackNdx) { 2566 final ActivityStack stack = stacks.get(stackNdx); 2567 final ActivityRecord r = stack.topRunningActivityLocked(null); 2568 final ActivityState state = r == null ? ActivityState.DESTROYED : r.state; 2569 if (isFrontStack(stack)) { 2570 if (r == null) { 2571 Slog.e(TAG, "validateTop...: null top activity, stack=" + stack); 2572 } else { 2573 final ActivityRecord pausing = stack.mPausingActivity; 2574 if (pausing != null && pausing == r) { 2575 Slog.e(TAG, "validateTop...: top stack has pausing activity r=" + r + 2576 " state=" + state); 2577 } 2578 if (state != ActivityState.INITIALIZING && state != ActivityState.RESUMED) { 2579 Slog.e(TAG, "validateTop...: activity in front not resumed r=" + r + 2580 " state=" + state); 2581 } 2582 } 2583 } else { 2584 final ActivityRecord resumed = stack.mResumedActivity; 2585 if (resumed != null && resumed == r) { 2586 Slog.e(TAG, "validateTop...: back stack has resumed activity r=" + r + 2587 " state=" + state); 2588 } 2589 if (r != null && (state == ActivityState.INITIALIZING 2590 || state == ActivityState.RESUMED)) { 2591 Slog.e(TAG, "validateTop...: activity in back resumed r=" + r + 2592 " state=" + state); 2593 } 2594 } 2595 } 2596*/ 2597 } 2598 2599 public void dump(PrintWriter pw, String prefix) { 2600 pw.print(prefix); pw.print("mDismissKeyguardOnNextActivity="); 2601 pw.println(mDismissKeyguardOnNextActivity); 2602 pw.print(prefix); pw.print("mFocusedStack=" + mFocusedStack); 2603 pw.print(" mLastFocusedStack="); pw.println(mLastFocusedStack); 2604 pw.print(prefix); pw.println("mSleepTimeout=" + mSleepTimeout); 2605 pw.print(prefix); pw.println("mCurTaskId=" + mCurTaskId); 2606 pw.print(prefix); pw.println("mUserStackInFront=" + mUserStackInFront); 2607 pw.print(prefix); pw.println("mActivityContainers=" + mActivityContainers); 2608 } 2609 2610 ArrayList<ActivityRecord> getDumpActivitiesLocked(String name) { 2611 return getFocusedStack().getDumpActivitiesLocked(name); 2612 } 2613 2614 static boolean printThisActivity(PrintWriter pw, ActivityRecord activity, String dumpPackage, 2615 boolean needSep, String prefix) { 2616 if (activity != null) { 2617 if (dumpPackage == null || dumpPackage.equals(activity.packageName)) { 2618 if (needSep) { 2619 pw.println(); 2620 } 2621 pw.print(prefix); 2622 pw.println(activity); 2623 return true; 2624 } 2625 } 2626 return false; 2627 } 2628 2629 boolean dumpActivitiesLocked(FileDescriptor fd, PrintWriter pw, boolean dumpAll, 2630 boolean dumpClient, String dumpPackage) { 2631 boolean printed = false; 2632 boolean needSep = false; 2633 for (int displayNdx = 0; displayNdx < mActivityDisplays.size(); ++displayNdx) { 2634 ActivityDisplay activityDisplay = mActivityDisplays.valueAt(displayNdx); 2635 pw.print("Display #"); pw.println(activityDisplay.mDisplayId); 2636 ArrayList<ActivityStack> stacks = activityDisplay.mStacks; 2637 final int numStacks = stacks.size(); 2638 for (int stackNdx = 0; stackNdx < numStacks; ++stackNdx) { 2639 final ActivityStack stack = stacks.get(stackNdx); 2640 StringBuilder stackHeader = new StringBuilder(128); 2641 stackHeader.append(" Stack #"); 2642 stackHeader.append(stack.mStackId); 2643 stackHeader.append(":"); 2644 printed |= stack.dumpActivitiesLocked(fd, pw, dumpAll, dumpClient, dumpPackage, 2645 needSep, stackHeader.toString()); 2646 printed |= dumpHistoryList(fd, pw, stack.mLRUActivities, " ", "Run", false, 2647 !dumpAll, false, dumpPackage, true, 2648 " Running activities (most recent first):", null); 2649 2650 needSep = printed; 2651 boolean pr = printThisActivity(pw, stack.mPausingActivity, dumpPackage, needSep, 2652 " mPausingActivity: "); 2653 if (pr) { 2654 printed = true; 2655 needSep = false; 2656 } 2657 pr = printThisActivity(pw, stack.mResumedActivity, dumpPackage, needSep, 2658 " mResumedActivity: "); 2659 if (pr) { 2660 printed = true; 2661 needSep = false; 2662 } 2663 if (dumpAll) { 2664 pr = printThisActivity(pw, stack.mLastPausedActivity, dumpPackage, needSep, 2665 " mLastPausedActivity: "); 2666 if (pr) { 2667 printed = true; 2668 needSep = true; 2669 } 2670 printed |= printThisActivity(pw, stack.mLastNoHistoryActivity, dumpPackage, 2671 needSep, " mLastNoHistoryActivity: "); 2672 } 2673 needSep = printed; 2674 } 2675 } 2676 2677 printed |= dumpHistoryList(fd, pw, mFinishingActivities, " ", "Fin", false, !dumpAll, 2678 false, dumpPackage, true, " Activities waiting to finish:", null); 2679 printed |= dumpHistoryList(fd, pw, mStoppingActivities, " ", "Stop", false, !dumpAll, 2680 false, dumpPackage, true, " Activities waiting to stop:", null); 2681 printed |= dumpHistoryList(fd, pw, mWaitingVisibleActivities, " ", "Wait", false, !dumpAll, 2682 false, dumpPackage, true, " Activities waiting for another to become visible:", 2683 null); 2684 printed |= dumpHistoryList(fd, pw, mGoingToSleepActivities, " ", "Sleep", false, !dumpAll, 2685 false, dumpPackage, true, " Activities waiting to sleep:", null); 2686 printed |= dumpHistoryList(fd, pw, mGoingToSleepActivities, " ", "Sleep", false, !dumpAll, 2687 false, dumpPackage, true, " Activities waiting to sleep:", null); 2688 2689 return printed; 2690 } 2691 2692 static boolean dumpHistoryList(FileDescriptor fd, PrintWriter pw, List<ActivityRecord> list, 2693 String prefix, String label, boolean complete, boolean brief, boolean client, 2694 String dumpPackage, boolean needNL, String header1, String header2) { 2695 TaskRecord lastTask = null; 2696 String innerPrefix = null; 2697 String[] args = null; 2698 boolean printed = false; 2699 for (int i=list.size()-1; i>=0; i--) { 2700 final ActivityRecord r = list.get(i); 2701 if (dumpPackage != null && !dumpPackage.equals(r.packageName)) { 2702 continue; 2703 } 2704 if (innerPrefix == null) { 2705 innerPrefix = prefix + " "; 2706 args = new String[0]; 2707 } 2708 printed = true; 2709 final boolean full = !brief && (complete || !r.isInHistory()); 2710 if (needNL) { 2711 pw.println(""); 2712 needNL = false; 2713 } 2714 if (header1 != null) { 2715 pw.println(header1); 2716 header1 = null; 2717 } 2718 if (header2 != null) { 2719 pw.println(header2); 2720 header2 = null; 2721 } 2722 if (lastTask != r.task) { 2723 lastTask = r.task; 2724 pw.print(prefix); 2725 pw.print(full ? "* " : " "); 2726 pw.println(lastTask); 2727 if (full) { 2728 lastTask.dump(pw, prefix + " "); 2729 } else if (complete) { 2730 // Complete + brief == give a summary. Isn't that obvious?!? 2731 if (lastTask.intent != null) { 2732 pw.print(prefix); pw.print(" "); 2733 pw.println(lastTask.intent.toInsecureStringWithClip()); 2734 } 2735 } 2736 } 2737 pw.print(prefix); pw.print(full ? " * " : " "); pw.print(label); 2738 pw.print(" #"); pw.print(i); pw.print(": "); 2739 pw.println(r); 2740 if (full) { 2741 r.dump(pw, innerPrefix); 2742 } else if (complete) { 2743 // Complete + brief == give a summary. Isn't that obvious?!? 2744 pw.print(innerPrefix); pw.println(r.intent.toInsecureString()); 2745 if (r.app != null) { 2746 pw.print(innerPrefix); pw.println(r.app); 2747 } 2748 } 2749 if (client && r.app != null && r.app.thread != null) { 2750 // flush anything that is already in the PrintWriter since the thread is going 2751 // to write to the file descriptor directly 2752 pw.flush(); 2753 try { 2754 TransferPipe tp = new TransferPipe(); 2755 try { 2756 r.app.thread.dumpActivity(tp.getWriteFd().getFileDescriptor(), 2757 r.appToken, innerPrefix, args); 2758 // Short timeout, since blocking here can 2759 // deadlock with the application. 2760 tp.go(fd, 2000); 2761 } finally { 2762 tp.kill(); 2763 } 2764 } catch (IOException e) { 2765 pw.println(innerPrefix + "Failure while dumping the activity: " + e); 2766 } catch (RemoteException e) { 2767 pw.println(innerPrefix + "Got a RemoteException while dumping the activity"); 2768 } 2769 needNL = true; 2770 } 2771 } 2772 return printed; 2773 } 2774 2775 void scheduleIdleTimeoutLocked(ActivityRecord next) { 2776 if (DEBUG_IDLE) Slog.d(TAG, "scheduleIdleTimeoutLocked: Callers=" + Debug.getCallers(4)); 2777 Message msg = mHandler.obtainMessage(IDLE_TIMEOUT_MSG, next); 2778 mHandler.sendMessageDelayed(msg, IDLE_TIMEOUT); 2779 } 2780 2781 final void scheduleIdleLocked() { 2782 mHandler.sendEmptyMessage(IDLE_NOW_MSG); 2783 } 2784 2785 void removeTimeoutsForActivityLocked(ActivityRecord r) { 2786 if (DEBUG_IDLE) Slog.d(TAG, "removeTimeoutsForActivity: Callers=" + Debug.getCallers(4)); 2787 mHandler.removeMessages(IDLE_TIMEOUT_MSG, r); 2788 } 2789 2790 final void scheduleResumeTopActivities() { 2791 if (!mHandler.hasMessages(RESUME_TOP_ACTIVITY_MSG)) { 2792 mHandler.sendEmptyMessage(RESUME_TOP_ACTIVITY_MSG); 2793 } 2794 } 2795 2796 void removeSleepTimeouts() { 2797 mSleepTimeout = false; 2798 mHandler.removeMessages(SLEEP_TIMEOUT_MSG); 2799 } 2800 2801 final void scheduleSleepTimeout() { 2802 removeSleepTimeouts(); 2803 mHandler.sendEmptyMessageDelayed(SLEEP_TIMEOUT_MSG, SLEEP_TIMEOUT); 2804 } 2805 2806 @Override 2807 public void onDisplayAdded(int displayId) { 2808 mHandler.sendMessage(mHandler.obtainMessage(HANDLE_DISPLAY_ADDED, displayId, 0)); 2809 } 2810 2811 @Override 2812 public void onDisplayRemoved(int displayId) { 2813 mHandler.sendMessage(mHandler.obtainMessage(HANDLE_DISPLAY_REMOVED, displayId, 0)); 2814 } 2815 2816 @Override 2817 public void onDisplayChanged(int displayId) { 2818 mHandler.sendMessage(mHandler.obtainMessage(HANDLE_DISPLAY_CHANGED, displayId, 0)); 2819 } 2820 2821 public void handleDisplayAddedLocked(int displayId) { 2822 boolean newDisplay; 2823 synchronized (mService) { 2824 newDisplay = mActivityDisplays.get(displayId) == null; 2825 if (newDisplay) { 2826 ActivityDisplay activityDisplay = new ActivityDisplay(displayId); 2827 mActivityDisplays.put(displayId, activityDisplay); 2828 } 2829 } 2830 if (newDisplay) { 2831 mWindowManager.onDisplayAdded(displayId); 2832 } 2833 } 2834 2835 public void handleDisplayRemovedLocked(int displayId) { 2836 synchronized (mService) { 2837 ActivityDisplay activityDisplay = mActivityDisplays.get(displayId); 2838 if (activityDisplay != null) { 2839 ArrayList<ActivityStack> stacks = activityDisplay.mStacks; 2840 for (int stackNdx = stacks.size() - 1; stackNdx >= 0; --stackNdx) { 2841 stacks.get(stackNdx).mActivityContainer.detachLocked(); 2842 } 2843 mActivityDisplays.remove(displayId); 2844 } 2845 } 2846 mWindowManager.onDisplayRemoved(displayId); 2847 } 2848 2849 public void handleDisplayChangedLocked(int displayId) { 2850 synchronized (mService) { 2851 ActivityDisplay activityDisplay = mActivityDisplays.get(displayId); 2852 if (activityDisplay != null) { 2853 // TODO: Update the bounds. 2854 } 2855 } 2856 mWindowManager.onDisplayChanged(displayId); 2857 } 2858 2859 StackInfo getStackInfo(ActivityStack stack) { 2860 StackInfo info = new StackInfo(); 2861 mWindowManager.getStackBounds(stack.mStackId, info.bounds); 2862 info.displayId = Display.DEFAULT_DISPLAY; 2863 info.stackId = stack.mStackId; 2864 2865 ArrayList<TaskRecord> tasks = stack.getAllTasks(); 2866 final int numTasks = tasks.size(); 2867 int[] taskIds = new int[numTasks]; 2868 String[] taskNames = new String[numTasks]; 2869 for (int i = 0; i < numTasks; ++i) { 2870 final TaskRecord task = tasks.get(i); 2871 taskIds[i] = task.taskId; 2872 taskNames[i] = task.origActivity != null ? task.origActivity.flattenToString() 2873 : task.realActivity != null ? task.realActivity.flattenToString() 2874 : task.getTopActivity() != null ? task.getTopActivity().packageName 2875 : "unknown"; 2876 } 2877 info.taskIds = taskIds; 2878 info.taskNames = taskNames; 2879 return info; 2880 } 2881 2882 StackInfo getStackInfoLocked(int stackId) { 2883 ActivityStack stack = getStack(stackId); 2884 if (stack != null) { 2885 return getStackInfo(stack); 2886 } 2887 return null; 2888 } 2889 2890 ArrayList<StackInfo> getAllStackInfosLocked() { 2891 ArrayList<StackInfo> list = new ArrayList<StackInfo>(); 2892 for (int displayNdx = 0; displayNdx < mActivityDisplays.size(); ++displayNdx) { 2893 ArrayList<ActivityStack> stacks = mActivityDisplays.valueAt(displayNdx).mStacks; 2894 for (int ndx = stacks.size() - 1; ndx >= 0; --ndx) { 2895 list.add(getStackInfo(stacks.get(ndx))); 2896 } 2897 } 2898 return list; 2899 } 2900 2901 void setLockTaskModeLocked(TaskRecord task) { 2902 if (task == null) { 2903 // Take out of lock task mode. 2904 mLockTaskModeTask = null; 2905 return; 2906 } 2907 if (isLockTaskModeViolation(task)) { 2908 Slog.e(TAG, "setLockTaskMode: Attempt to start a second Lock Task Mode task."); 2909 return; 2910 } 2911 mLockTaskModeTask = task; 2912 findTaskToMoveToFrontLocked(task, 0, null); 2913 resumeTopActivitiesLocked(); 2914 } 2915 2916 boolean isLockTaskModeViolation(TaskRecord task) { 2917 return mLockTaskModeTask != null && mLockTaskModeTask != task; 2918 } 2919 2920 void endLockTaskModeIfTaskEnding(TaskRecord task) { 2921 if (mLockTaskModeTask != null && mLockTaskModeTask == task) { 2922 mLockTaskModeTask = null; 2923 } 2924 } 2925 2926 boolean isInLockTaskMode() { 2927 return mLockTaskModeTask != null; 2928 } 2929 2930 private final class ActivityStackSupervisorHandler extends Handler { 2931 2932 public ActivityStackSupervisorHandler(Looper looper) { 2933 super(looper); 2934 } 2935 2936 void activityIdleInternal(ActivityRecord r) { 2937 synchronized (mService) { 2938 activityIdleInternalLocked(r != null ? r.appToken : null, true, null); 2939 } 2940 } 2941 2942 @Override 2943 public void handleMessage(Message msg) { 2944 switch (msg.what) { 2945 case IDLE_TIMEOUT_MSG: { 2946 if (DEBUG_IDLE) Slog.d(TAG, "handleMessage: IDLE_TIMEOUT_MSG: r=" + msg.obj); 2947 if (mService.mDidDexOpt) { 2948 mService.mDidDexOpt = false; 2949 Message nmsg = mHandler.obtainMessage(IDLE_TIMEOUT_MSG); 2950 nmsg.obj = msg.obj; 2951 mHandler.sendMessageDelayed(nmsg, IDLE_TIMEOUT); 2952 return; 2953 } 2954 // We don't at this point know if the activity is fullscreen, 2955 // so we need to be conservative and assume it isn't. 2956 activityIdleInternal((ActivityRecord)msg.obj); 2957 } break; 2958 case IDLE_NOW_MSG: { 2959 if (DEBUG_IDLE) Slog.d(TAG, "handleMessage: IDLE_NOW_MSG: r=" + msg.obj); 2960 activityIdleInternal((ActivityRecord)msg.obj); 2961 } break; 2962 case RESUME_TOP_ACTIVITY_MSG: { 2963 synchronized (mService) { 2964 resumeTopActivitiesLocked(); 2965 } 2966 } break; 2967 case SLEEP_TIMEOUT_MSG: { 2968 synchronized (mService) { 2969 if (mService.isSleepingOrShuttingDown()) { 2970 Slog.w(TAG, "Sleep timeout! Sleeping now."); 2971 mSleepTimeout = true; 2972 checkReadyForSleepLocked(); 2973 } 2974 } 2975 } break; 2976 case LAUNCH_TIMEOUT_MSG: { 2977 if (mService.mDidDexOpt) { 2978 mService.mDidDexOpt = false; 2979 mHandler.sendEmptyMessageDelayed(LAUNCH_TIMEOUT_MSG, LAUNCH_TIMEOUT); 2980 return; 2981 } 2982 synchronized (mService) { 2983 if (mLaunchingActivity.isHeld()) { 2984 Slog.w(TAG, "Launch timeout has expired, giving up wake lock!"); 2985 if (VALIDATE_WAKE_LOCK_CALLER 2986 && Binder.getCallingUid() != Process.myUid()) { 2987 throw new IllegalStateException("Calling must be system uid"); 2988 } 2989 mLaunchingActivity.release(); 2990 } 2991 } 2992 } break; 2993 case HANDLE_DISPLAY_ADDED: { 2994 handleDisplayAddedLocked(msg.arg1); 2995 } break; 2996 case HANDLE_DISPLAY_CHANGED: { 2997 handleDisplayChangedLocked(msg.arg1); 2998 } break; 2999 case HANDLE_DISPLAY_REMOVED: { 3000 handleDisplayRemovedLocked(msg.arg1); 3001 } break; 3002 case CONTAINER_CALLBACK_VISIBILITY: { 3003 final ActivityContainer container = (ActivityContainer) msg.obj; 3004 try { 3005 // We only send this message if mCallback is non-null. 3006 container.mCallback.setVisible(container.asBinder(), msg.arg1 == 1); 3007 } catch (RemoteException e) { 3008 } 3009 } 3010 } 3011 } 3012 } 3013 3014 class ActivityContainer extends android.app.IActivityContainer.Stub { 3015 final static int FORCE_NEW_TASK_FLAGS = Intent.FLAG_ACTIVITY_NEW_TASK | 3016 Intent.FLAG_ACTIVITY_MULTIPLE_TASK; 3017 final int mStackId; 3018 IActivityContainerCallback mCallback = null; 3019 final ActivityStack mStack; 3020 ActivityRecord mParentActivity = null; 3021 String mIdString; 3022 3023 boolean mVisible = true; 3024 3025 /** Display this ActivityStack is currently on. Null if not attached to a Display. */ 3026 ActivityDisplay mActivityDisplay; 3027 3028 final static int CONTAINER_STATE_HAS_SURFACE = 0; 3029 final static int CONTAINER_STATE_NO_SURFACE = 1; 3030 final static int CONTAINER_STATE_FINISHING = 2; 3031 int mContainerState = CONTAINER_STATE_HAS_SURFACE; 3032 3033 ActivityContainer(int stackId) { 3034 synchronized (mService) { 3035 mStackId = stackId; 3036 mStack = new ActivityStack(this); 3037 mIdString = "ActivtyContainer{" + mStackId + "}"; 3038 if (DEBUG_STACK) Slog.d(TAG, "Creating " + this); 3039 } 3040 } 3041 3042 void attachToDisplayLocked(ActivityDisplay activityDisplay) { 3043 if (DEBUG_STACK) Slog.d(TAG, "attachToDisplayLocked: " + this 3044 + " to display=" + activityDisplay); 3045 mActivityDisplay = activityDisplay; 3046 mStack.mDisplayId = activityDisplay.mDisplayId; 3047 mStack.mStacks = activityDisplay.mStacks; 3048 3049 activityDisplay.attachActivities(mStack); 3050 mWindowManager.attachStack(mStackId, activityDisplay.mDisplayId); 3051 } 3052 3053 @Override 3054 public void attachToDisplay(int displayId) { 3055 synchronized (mService) { 3056 ActivityDisplay activityDisplay = mActivityDisplays.get(displayId); 3057 if (activityDisplay == null) { 3058 return; 3059 } 3060 attachToDisplayLocked(activityDisplay); 3061 } 3062 } 3063 3064 @Override 3065 public int getDisplayId() { 3066 if (mActivityDisplay != null) { 3067 return mActivityDisplay.mDisplayId; 3068 } 3069 return -1; 3070 } 3071 3072 @Override 3073 public boolean injectEvent(InputEvent event) { 3074 final long origId = Binder.clearCallingIdentity(); 3075 try { 3076 if (mActivityDisplay != null) { 3077 return mInputManagerInternal.injectInputEvent(event, 3078 mActivityDisplay.mDisplayId, 3079 InputManager.INJECT_INPUT_EVENT_MODE_ASYNC); 3080 } 3081 return false; 3082 } finally { 3083 Binder.restoreCallingIdentity(origId); 3084 } 3085 } 3086 3087 @Override 3088 public void release() { 3089 mContainerState = CONTAINER_STATE_FINISHING; 3090 mStack.finishAllActivitiesLocked(); 3091 detachLocked(); 3092 mWindowManager.removeStack(mStackId); 3093 } 3094 3095 private void detachLocked() { 3096 if (DEBUG_STACK) Slog.d(TAG, "detachLocked: " + this + " from display=" 3097 + mActivityDisplay + " Callers=" + Debug.getCallers(2)); 3098 if (mActivityDisplay != null) { 3099 mActivityDisplay.detachActivitiesLocked(mStack); 3100 mActivityDisplay = null; 3101 mStack.mDisplayId = -1; 3102 mStack.mStacks = null; 3103 mWindowManager.detachStack(mStackId); 3104 } 3105 } 3106 3107 @Override 3108 public final int startActivity(Intent intent) { 3109 mService.enforceNotIsolatedCaller("ActivityContainer.startActivity"); 3110 int userId = mService.handleIncomingUser(Binder.getCallingPid(), 3111 Binder.getCallingUid(), mCurrentUser, false, true, "ActivityContainer", null); 3112 // TODO: Switch to user app stacks here. 3113 intent.addFlags(FORCE_NEW_TASK_FLAGS); 3114 String mimeType = intent.getType(); 3115 if (mimeType == null && intent.getData() != null 3116 && "content".equals(intent.getData().getScheme())) { 3117 mimeType = mService.getProviderMimeType(intent.getData(), userId); 3118 } 3119 return startActivityMayWait(null, -1, null, intent, mimeType, null, null, null, null, 0, 0, null, 3120 null, null, null, null, userId, this); 3121 } 3122 3123 @Override 3124 public final int startActivityIntentSender(IIntentSender intentSender) { 3125 mService.enforceNotIsolatedCaller("ActivityContainer.startActivityIntentSender"); 3126 3127 if (!(intentSender instanceof PendingIntentRecord)) { 3128 throw new IllegalArgumentException("Bad PendingIntent object"); 3129 } 3130 3131 return ((PendingIntentRecord)intentSender).sendInner(0, null, null, null, null, null, 3132 null, 0, FORCE_NEW_TASK_FLAGS, FORCE_NEW_TASK_FLAGS, null, this); 3133 } 3134 3135 private void checkEmbeddedAllowedInner(Intent intent, String resolvedType) { 3136 int userId = mService.handleIncomingUser(Binder.getCallingPid(), 3137 Binder.getCallingUid(), mCurrentUser, false, true, "ActivityContainer", null); 3138 if (resolvedType == null) { 3139 resolvedType = intent.getType(); 3140 if (resolvedType == null && intent.getData() != null 3141 && "content".equals(intent.getData().getScheme())) { 3142 resolvedType = mService.getProviderMimeType(intent.getData(), userId); 3143 } 3144 } 3145 ActivityInfo aInfo = resolveActivity(intent, resolvedType, 0, null, null, userId); 3146 if (aInfo != null && (aInfo.flags & ActivityInfo.FLAG_ALLOW_EMBEDDED) == 0) { 3147 throw new SecurityException( 3148 "Attempt to embed activity that has not set allowEmbedded=\"true\""); 3149 } 3150 } 3151 3152 /** Throw a SecurityException if allowEmbedded is not true */ 3153 @Override 3154 public final void checkEmbeddedAllowed(Intent intent) { 3155 checkEmbeddedAllowedInner(intent, null); 3156 } 3157 3158 /** Throw a SecurityException if allowEmbedded is not true */ 3159 @Override 3160 public final void checkEmbeddedAllowedIntentSender(IIntentSender intentSender) { 3161 if (!(intentSender instanceof PendingIntentRecord)) { 3162 throw new IllegalArgumentException("Bad PendingIntent object"); 3163 } 3164 PendingIntentRecord pendingIntent = (PendingIntentRecord) intentSender; 3165 checkEmbeddedAllowedInner(pendingIntent.key.requestIntent, 3166 pendingIntent.key.requestResolvedType); 3167 } 3168 3169 @Override 3170 public IBinder asBinder() { 3171 return this; 3172 } 3173 3174 @Override 3175 public void setSurface(Surface surface, int width, int height, int density) { 3176 mService.enforceNotIsolatedCaller("ActivityContainer.attachToSurface"); 3177 } 3178 3179 ActivityStackSupervisor getOuter() { 3180 return ActivityStackSupervisor.this; 3181 } 3182 3183 boolean isAttached() { 3184 return mActivityDisplay != null; 3185 } 3186 3187 void getBounds(Point outBounds) { 3188 if (mActivityDisplay != null) { 3189 mActivityDisplay.getBounds(outBounds); 3190 } else { 3191 outBounds.set(0, 0); 3192 } 3193 } 3194 3195 // TODO: Make sure every change to ActivityRecord.visible results in a call to this. 3196 void setVisible(boolean visible) { 3197 if (mVisible != visible) { 3198 mVisible = visible; 3199 if (mCallback != null) { 3200 mHandler.obtainMessage(CONTAINER_CALLBACK_VISIBILITY, visible ? 1 : 0, 3201 0 /* unused */, this).sendToTarget(); 3202 } 3203 } 3204 } 3205 3206 void setDrawn() { 3207 } 3208 3209 @Override 3210 public String toString() { 3211 return mIdString + (mActivityDisplay == null ? "N" : "A"); 3212 } 3213 } 3214 3215 private class VirtualActivityContainer extends ActivityContainer { 3216 Surface mSurface; 3217 boolean mDrawn = false; 3218 3219 VirtualActivityContainer(ActivityRecord parent, IActivityContainerCallback callback) { 3220 super(getNextStackId()); 3221 mParentActivity = parent; 3222 mCallback = callback; 3223 mContainerState = CONTAINER_STATE_NO_SURFACE; 3224 mIdString = "VirtualActivtyContainer{" + mStackId + ", parent=" + mParentActivity + "}"; 3225 } 3226 3227 @Override 3228 public void setSurface(Surface surface, int width, int height, int density) { 3229 super.setSurface(surface, width, height, density); 3230 3231 synchronized (mService) { 3232 final long origId = Binder.clearCallingIdentity(); 3233 try { 3234 setSurfaceLocked(surface, width, height, density); 3235 } finally { 3236 Binder.restoreCallingIdentity(origId); 3237 } 3238 } 3239 } 3240 3241 private void setSurfaceLocked(Surface surface, int width, int height, int density) { 3242 if (mContainerState == CONTAINER_STATE_FINISHING) { 3243 return; 3244 } 3245 VirtualActivityDisplay virtualActivityDisplay = 3246 (VirtualActivityDisplay) mActivityDisplay; 3247 if (virtualActivityDisplay == null) { 3248 virtualActivityDisplay = 3249 new VirtualActivityDisplay(width, height, density); 3250 mActivityDisplay = virtualActivityDisplay; 3251 mActivityDisplays.put(virtualActivityDisplay.mDisplayId, virtualActivityDisplay); 3252 attachToDisplayLocked(virtualActivityDisplay); 3253 } 3254 3255 if (mSurface != null) { 3256 mSurface.release(); 3257 } 3258 3259 mSurface = surface; 3260 if (surface != null) { 3261 mStack.resumeTopActivityLocked(null); 3262 } else { 3263 mContainerState = CONTAINER_STATE_NO_SURFACE; 3264 ((VirtualActivityDisplay) mActivityDisplay).setSurface(null); 3265 if (mStack.mPausingActivity == null && mStack.mResumedActivity != null) { 3266 mStack.startPausingLocked(false, true); 3267 } 3268 } 3269 3270 setSurfaceIfReady(); 3271 3272 if (DEBUG_STACK) Slog.d(TAG, "setSurface: " + this + " to display=" 3273 + virtualActivityDisplay); 3274 } 3275 3276 @Override 3277 boolean isAttached() { 3278 return mSurface != null && super.isAttached(); 3279 } 3280 3281 @Override 3282 void setDrawn() { 3283 synchronized (mService) { 3284 mDrawn = true; 3285 setSurfaceIfReady(); 3286 } 3287 } 3288 3289 private void setSurfaceIfReady() { 3290 if (DEBUG_STACK) Slog.v(TAG, "setSurfaceIfReady: mDrawn=" + mDrawn + 3291 " mContainerState=" + mContainerState + " mSurface=" + mSurface); 3292 if (mDrawn && mSurface != null && mContainerState == CONTAINER_STATE_NO_SURFACE) { 3293 ((VirtualActivityDisplay) mActivityDisplay).setSurface(mSurface); 3294 mContainerState = CONTAINER_STATE_HAS_SURFACE; 3295 } 3296 } 3297 } 3298 3299 /** Exactly one of these classes per Display in the system. Capable of holding zero or more 3300 * attached {@link ActivityStack}s */ 3301 class ActivityDisplay { 3302 /** Actual Display this object tracks. */ 3303 int mDisplayId; 3304 Display mDisplay; 3305 DisplayInfo mDisplayInfo = new DisplayInfo(); 3306 3307 /** All of the stacks on this display. Order matters, topmost stack is in front of all other 3308 * stacks, bottommost behind. Accessed directly by ActivityManager package classes */ 3309 final ArrayList<ActivityStack> mStacks = new ArrayList<ActivityStack>(); 3310 3311 ActivityDisplay() { 3312 } 3313 3314 ActivityDisplay(int displayId) { 3315 init(mDisplayManager.getDisplay(displayId)); 3316 } 3317 3318 void init(Display display) { 3319 mDisplay = display; 3320 mDisplayId = display.getDisplayId(); 3321 mDisplay.getDisplayInfo(mDisplayInfo); 3322 } 3323 3324 void attachActivities(ActivityStack stack) { 3325 if (DEBUG_STACK) Slog.v(TAG, "attachActivities: attaching " + stack + " to displayId=" 3326 + mDisplayId); 3327 mStacks.add(stack); 3328 } 3329 3330 void detachActivitiesLocked(ActivityStack stack) { 3331 if (DEBUG_STACK) Slog.v(TAG, "detachActivitiesLocked: detaching " + stack 3332 + " from displayId=" + mDisplayId); 3333 mStacks.remove(stack); 3334 } 3335 3336 void getBounds(Point bounds) { 3337 mDisplay.getDisplayInfo(mDisplayInfo); 3338 bounds.x = mDisplayInfo.appWidth; 3339 bounds.y = mDisplayInfo.appHeight; 3340 } 3341 3342 @Override 3343 public String toString() { 3344 return "ActivityDisplay={" + mDisplayId + " numStacks=" + mStacks.size() + "}"; 3345 } 3346 } 3347 3348 class VirtualActivityDisplay extends ActivityDisplay { 3349 VirtualDisplay mVirtualDisplay; 3350 3351 VirtualActivityDisplay(int width, int height, int density) { 3352 DisplayManagerGlobal dm = DisplayManagerGlobal.getInstance(); 3353 mVirtualDisplay = dm.createVirtualDisplay(mService.mContext, VIRTUAL_DISPLAY_BASE_NAME, 3354 width, height, density, null, DisplayManager.VIRTUAL_DISPLAY_FLAG_PUBLIC | 3355 DisplayManager.VIRTUAL_DISPLAY_FLAG_OWN_CONTENT_ONLY); 3356 3357 init(mVirtualDisplay.getDisplay()); 3358 3359 mWindowManager.handleDisplayAdded(mDisplayId); 3360 } 3361 3362 void setSurface(Surface surface) { 3363 if (mVirtualDisplay != null) { 3364 mVirtualDisplay.setSurface(surface); 3365 } 3366 } 3367 3368 @Override 3369 void detachActivitiesLocked(ActivityStack stack) { 3370 super.detachActivitiesLocked(stack); 3371 if (mVirtualDisplay != null) { 3372 mVirtualDisplay.release(); 3373 mVirtualDisplay = null; 3374 } 3375 } 3376 3377 @Override 3378 public String toString() { 3379 return "VirtualActivityDisplay={" + mDisplayId + "}"; 3380 } 3381 } 3382} 3383