ActivityStackSupervisor.java revision b53d97c4571f8ed09e92eee64301969b96ff1e4d
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.ActivityOptions; 38import android.app.AppGlobals; 39import android.app.IActivityManager; 40import android.app.IApplicationThread; 41import android.app.IThumbnailReceiver; 42import android.app.PendingIntent; 43import android.app.ActivityManager.RunningTaskInfo; 44import android.app.IActivityManager.WaitResult; 45import android.app.ResultInfo; 46import android.content.ComponentName; 47import android.content.Context; 48import android.content.IIntentSender; 49import android.content.Intent; 50import android.content.IntentSender; 51import android.content.pm.ActivityInfo; 52import android.content.pm.ApplicationInfo; 53import android.content.pm.PackageManager; 54import android.content.pm.ResolveInfo; 55import android.content.res.Configuration; 56import android.os.Binder; 57import android.os.Bundle; 58import android.os.Debug; 59import android.os.Handler; 60import android.os.IBinder; 61import android.os.Looper; 62import android.os.Message; 63import android.os.ParcelFileDescriptor; 64import android.os.PowerManager; 65import android.os.Process; 66import android.os.RemoteException; 67import android.os.SystemClock; 68import android.os.UserHandle; 69import android.util.EventLog; 70import android.util.Slog; 71import android.util.SparseIntArray; 72 73import com.android.internal.app.HeavyWeightSwitcherActivity; 74import com.android.internal.os.TransferPipe; 75import com.android.server.am.ActivityManagerService.PendingActivityLaunch; 76import com.android.server.am.ActivityStack.ActivityState; 77import com.android.server.wm.StackBox; 78import com.android.server.wm.WindowManagerService; 79 80import java.io.FileDescriptor; 81import java.io.IOException; 82import java.io.PrintWriter; 83import java.util.ArrayList; 84import java.util.List; 85 86public final class ActivityStackSupervisor { 87 static final boolean DEBUG = ActivityManagerService.DEBUG || false; 88 static final boolean DEBUG_ADD_REMOVE = DEBUG || false; 89 static final boolean DEBUG_APP = DEBUG || false; 90 static final boolean DEBUG_SAVED_STATE = DEBUG || false; 91 static final boolean DEBUG_STATES = DEBUG || false; 92 static final boolean DEBUG_IDLE = DEBUG || false; 93 94 public static final int HOME_STACK_ID = 0; 95 96 /** How long we wait until giving up on the last activity telling us it is idle. */ 97 static final int IDLE_TIMEOUT = 10*1000; 98 99 /** How long we can hold the sleep wake lock before giving up. */ 100 static final int SLEEP_TIMEOUT = 5*1000; 101 102 // How long we can hold the launch wake lock before giving up. 103 static final int LAUNCH_TIMEOUT = 10*1000; 104 105 static final int IDLE_TIMEOUT_MSG = FIRST_SUPERVISOR_STACK_MSG; 106 static final int IDLE_NOW_MSG = FIRST_SUPERVISOR_STACK_MSG + 1; 107 static final int RESUME_TOP_ACTIVITY_MSG = FIRST_SUPERVISOR_STACK_MSG + 2; 108 static final int SLEEP_TIMEOUT_MSG = FIRST_SUPERVISOR_STACK_MSG + 3; 109 static final int LAUNCH_TIMEOUT_MSG = FIRST_SUPERVISOR_STACK_MSG + 4; 110 111 // For debugging to make sure the caller when acquiring/releasing our 112 // wake lock is the system process. 113 static final boolean VALIDATE_WAKE_LOCK_CALLER = false; 114 115 final ActivityManagerService mService; 116 final Context mContext; 117 final Looper mLooper; 118 119 final ActivityStackSupervisorHandler mHandler; 120 121 /** Short cut */ 122 WindowManagerService mWindowManager; 123 124 /** Dismiss the keyguard after the next activity is displayed? */ 125 boolean mDismissKeyguardOnNextActivity = false; 126 127 /** Identifier counter for all ActivityStacks */ 128 private int mLastStackId = HOME_STACK_ID; 129 130 /** Task identifier that activities are currently being started in. Incremented each time a 131 * new task is created. */ 132 private int mCurTaskId = 0; 133 134 /** The current user */ 135 private int mCurrentUser; 136 137 /** The stack containing the launcher app */ 138 private ActivityStack mHomeStack; 139 140 /** The non-home stack currently receiving input or launching the next activity. If home is 141 * in front then mHomeStack overrides mFocusedStack. 142 * DO NOT ACCESS DIRECTLY - It may be null, use getFocusedStack() */ 143 private ActivityStack mFocusedStack; 144 145 /** All the non-launcher stacks */ 146 private ArrayList<ActivityStack> mStacks = new ArrayList<ActivityStack>(); 147 148 private static final int STACK_STATE_HOME_IN_FRONT = 0; 149 private static final int STACK_STATE_HOME_TO_BACK = 1; 150 private static final int STACK_STATE_HOME_IN_BACK = 2; 151 private static final int STACK_STATE_HOME_TO_FRONT = 3; 152 private int mStackState = STACK_STATE_HOME_IN_FRONT; 153 154 /** List of activities that are waiting for a new activity to become visible before completing 155 * whatever operation they are supposed to do. */ 156 final ArrayList<ActivityRecord> mWaitingVisibleActivities = new ArrayList<ActivityRecord>(); 157 158 /** List of processes waiting to find out about the next visible activity. */ 159 final ArrayList<IActivityManager.WaitResult> mWaitingActivityVisible = 160 new ArrayList<IActivityManager.WaitResult>(); 161 162 /** List of processes waiting to find out about the next launched activity. */ 163 final ArrayList<IActivityManager.WaitResult> mWaitingActivityLaunched = 164 new ArrayList<IActivityManager.WaitResult>(); 165 166 /** List of activities that are ready to be stopped, but waiting for the next activity to 167 * settle down before doing so. */ 168 final ArrayList<ActivityRecord> mStoppingActivities = new ArrayList<ActivityRecord>(); 169 170 /** List of activities that are ready to be finished, but waiting for the previous activity to 171 * settle down before doing so. It contains ActivityRecord objects. */ 172 final ArrayList<ActivityRecord> mFinishingActivities = new ArrayList<ActivityRecord>(); 173 174 /** List of activities that are in the process of going to sleep. */ 175 final ArrayList<ActivityRecord> mGoingToSleepActivities = new ArrayList<ActivityRecord>(); 176 177 /** List of ActivityRecord objects that have been finished and must still report back to a 178 * pending thumbnail receiver. */ 179 final ArrayList<ActivityRecord> mCancelledThumbnails = new ArrayList<ActivityRecord>(); 180 181 /** Used on user changes */ 182 final ArrayList<UserStartedState> mStartingUsers = new ArrayList<UserStartedState>(); 183 184 /** Set to indicate whether to issue an onUserLeaving callback when a newly launched activity 185 * is being brought in front of us. */ 186 boolean mUserLeaving = false; 187 188 /** Set when we have taken too long waiting to go to sleep. */ 189 boolean mSleepTimeout = false; 190 191 /** 192 * We don't want to allow the device to go to sleep while in the process 193 * of launching an activity. This is primarily to allow alarm intent 194 * receivers to launch an activity and get that to run before the device 195 * goes back to sleep. 196 */ 197 final PowerManager.WakeLock mLaunchingActivity; 198 199 /** 200 * Set when the system is going to sleep, until we have 201 * successfully paused the current activity and released our wake lock. 202 * At that point the system is allowed to actually sleep. 203 */ 204 final PowerManager.WakeLock mGoingToSleep; 205 206 /** Stack id of the front stack when user switched, indexed by userId. */ 207 SparseIntArray mUserStackInFront = new SparseIntArray(2); 208 209 public ActivityStackSupervisor(ActivityManagerService service, Context context, 210 Looper looper) { 211 mService = service; 212 mContext = context; 213 mLooper = looper; 214 PowerManager pm = (PowerManager)context.getSystemService(Context.POWER_SERVICE); 215 mGoingToSleep = pm.newWakeLock(PowerManager.PARTIAL_WAKE_LOCK, "ActivityManager-Sleep"); 216 mHandler = new ActivityStackSupervisorHandler(looper); 217 if (VALIDATE_WAKE_LOCK_CALLER && Binder.getCallingUid() != Process.myUid()) { 218 throw new IllegalStateException("Calling must be system uid"); 219 } 220 mLaunchingActivity = 221 pm.newWakeLock(PowerManager.PARTIAL_WAKE_LOCK, "ActivityManager-Launch"); 222 mLaunchingActivity.setReferenceCounted(false); 223 } 224 225 void setWindowManager(WindowManagerService wm) { 226 mWindowManager = wm; 227 mHomeStack = new ActivityStack(mService, mContext, mLooper, HOME_STACK_ID); 228 mStacks.add(mHomeStack); 229 } 230 231 void dismissKeyguard() { 232 if (ActivityManagerService.DEBUG_LOCKSCREEN) mService.logLockScreen(""); 233 if (mDismissKeyguardOnNextActivity) { 234 mDismissKeyguardOnNextActivity = false; 235 mWindowManager.dismissKeyguard(); 236 } 237 } 238 239 ActivityStack getFocusedStack() { 240 if (mFocusedStack == null) { 241 return mHomeStack; 242 } 243 switch (mStackState) { 244 case STACK_STATE_HOME_IN_FRONT: 245 case STACK_STATE_HOME_TO_FRONT: 246 return mHomeStack; 247 case STACK_STATE_HOME_IN_BACK: 248 case STACK_STATE_HOME_TO_BACK: 249 default: 250 return mFocusedStack; 251 } 252 } 253 254 ActivityStack getLastStack() { 255 switch (mStackState) { 256 case STACK_STATE_HOME_IN_FRONT: 257 case STACK_STATE_HOME_TO_BACK: 258 return mHomeStack; 259 case STACK_STATE_HOME_TO_FRONT: 260 case STACK_STATE_HOME_IN_BACK: 261 default: 262 return mFocusedStack; 263 } 264 } 265 266 boolean isFrontStack(ActivityStack stack) { 267 return !(stack.isHomeStack() ^ getFocusedStack().isHomeStack()); 268 } 269 270 void moveHomeStack(boolean toFront) { 271 final boolean homeInFront = isFrontStack(mHomeStack); 272 if (homeInFront ^ toFront) { 273 if (DEBUG_STACK) Slog.d(TAG, "moveHomeTask: mStackState old=" + 274 stackStateToString(mStackState) + " new=" + stackStateToString(homeInFront ? 275 STACK_STATE_HOME_TO_BACK : STACK_STATE_HOME_TO_FRONT)); 276 mStackState = homeInFront ? STACK_STATE_HOME_TO_BACK : STACK_STATE_HOME_TO_FRONT; 277 } 278 } 279 280 void moveHomeToTop() { 281 moveHomeStack(true); 282 mHomeStack.moveHomeTaskToTop(); 283 } 284 285 boolean resumeHomeActivity(ActivityRecord prev) { 286 moveHomeToTop(); 287 if (prev != null) { 288 prev.task.mOnTopOfHome = false; 289 } 290 ActivityRecord r = mHomeStack.topRunningActivityLocked(null); 291 if (r != null && r.isHomeActivity()) { 292 mService.setFocusedActivityLocked(r); 293 return resumeTopActivitiesLocked(mHomeStack, prev, null); 294 } 295 return mService.startHomeActivityLocked(mCurrentUser); 296 } 297 298 void setDismissKeyguard(boolean dismiss) { 299 if (ActivityManagerService.DEBUG_LOCKSCREEN) mService.logLockScreen(" dismiss=" + dismiss); 300 mDismissKeyguardOnNextActivity = dismiss; 301 } 302 303 TaskRecord anyTaskForIdLocked(int id) { 304 for (int stackNdx = mStacks.size() - 1; stackNdx >= 0; --stackNdx) { 305 ActivityStack stack = mStacks.get(stackNdx); 306 TaskRecord task = stack.taskForIdLocked(id); 307 if (task != null) { 308 return task; 309 } 310 } 311 return null; 312 } 313 314 ActivityRecord isInAnyStackLocked(IBinder token) { 315 for (int stackNdx = mStacks.size() - 1; stackNdx >= 0; --stackNdx) { 316 final ActivityRecord r = mStacks.get(stackNdx).isInStackLocked(token); 317 if (r != null) { 318 return r; 319 } 320 } 321 return null; 322 } 323 324 int getNextTaskId() { 325 do { 326 mCurTaskId++; 327 if (mCurTaskId <= 0) { 328 mCurTaskId = 1; 329 } 330 } while (anyTaskForIdLocked(mCurTaskId) != null); 331 return mCurTaskId; 332 } 333 334 void removeTask(TaskRecord task) { 335 mWindowManager.removeTask(task.taskId); 336 final ActivityStack stack = task.stack; 337 final ActivityRecord r = stack.mResumedActivity; 338 if (r != null && r.task == task) { 339 stack.mResumedActivity = null; 340 } 341 if (stack.removeTask(task) && !stack.isHomeStack()) { 342 if (DEBUG_STACK) Slog.i(TAG, "removeTask: removing stack " + stack); 343 mStacks.remove(stack); 344 final int stackId = stack.mStackId; 345 final int nextStackId = mWindowManager.removeStack(stackId); 346 // TODO: Perhaps we need to let the ActivityManager determine the next focus... 347 if (mFocusedStack == null || mFocusedStack.mStackId == stackId) { 348 // If this is the last app stack, set mFocusedStack to null. 349 mFocusedStack = nextStackId == HOME_STACK_ID ? null : getStack(nextStackId); 350 } 351 } 352 } 353 354 ActivityRecord resumedAppLocked() { 355 ActivityStack stack = getFocusedStack(); 356 if (stack == null) { 357 return null; 358 } 359 ActivityRecord resumedActivity = stack.mResumedActivity; 360 if (resumedActivity == null || resumedActivity.app == null) { 361 resumedActivity = stack.mPausingActivity; 362 if (resumedActivity == null || resumedActivity.app == null) { 363 resumedActivity = stack.topRunningActivityLocked(null); 364 } 365 } 366 return resumedActivity; 367 } 368 369 boolean attachApplicationLocked(ProcessRecord app, boolean headless) throws Exception { 370 boolean didSomething = false; 371 final String processName = app.processName; 372 for (int stackNdx = mStacks.size() - 1; stackNdx >= 0; --stackNdx) { 373 final ActivityStack stack = mStacks.get(stackNdx); 374 if (!isFrontStack(stack)) { 375 continue; 376 } 377 ActivityRecord hr = stack.topRunningActivityLocked(null); 378 if (hr != null) { 379 if (hr.app == null && app.uid == hr.info.applicationInfo.uid 380 && processName.equals(hr.processName)) { 381 try { 382 if (headless) { 383 Slog.e(TAG, "Starting activities not supported on headless device: " 384 + hr); 385 } else if (realStartActivityLocked(hr, app, true, true)) { 386 didSomething = true; 387 } 388 } catch (Exception e) { 389 Slog.w(TAG, "Exception in new application when starting activity " 390 + hr.intent.getComponent().flattenToShortString(), e); 391 throw e; 392 } 393 } 394 } 395 } 396 if (!didSomething) { 397 ensureActivitiesVisibleLocked(null, 0); 398 } 399 return didSomething; 400 } 401 402 boolean allResumedActivitiesIdle() { 403 for (int stackNdx = mStacks.size() - 1; stackNdx >= 0; --stackNdx) { 404 final ActivityStack stack = mStacks.get(stackNdx); 405 if (!isFrontStack(stack)) { 406 continue; 407 } 408 final ActivityRecord resumedActivity = stack.mResumedActivity; 409 if (resumedActivity == null || !resumedActivity.idle) { 410 return false; 411 } 412 } 413 return true; 414 } 415 416 boolean allResumedActivitiesComplete() { 417 for (int stackNdx = mStacks.size() - 1; stackNdx >= 0; --stackNdx) { 418 final ActivityStack stack = mStacks.get(stackNdx); 419 if (isFrontStack(stack)) { 420 final ActivityRecord r = stack.mResumedActivity; 421 if (r != null && r.state != ActivityState.RESUMED) { 422 return false; 423 } 424 } 425 } 426 // TODO: Not sure if this should check if all Paused are complete too. 427 switch (mStackState) { 428 case STACK_STATE_HOME_TO_BACK: 429 if (DEBUG_STACK) Slog.d(TAG, "allResumedActivitiesComplete: mStackState old=" + 430 stackStateToString(STACK_STATE_HOME_TO_BACK) + " new=" + 431 stackStateToString(STACK_STATE_HOME_IN_BACK)); 432 mStackState = STACK_STATE_HOME_IN_BACK; 433 break; 434 case STACK_STATE_HOME_TO_FRONT: 435 if (DEBUG_STACK) Slog.d(TAG, "allResumedActivitiesComplete: mStackState old=" + 436 stackStateToString(STACK_STATE_HOME_TO_FRONT) + " new=" + 437 stackStateToString(STACK_STATE_HOME_IN_FRONT)); 438 mStackState = STACK_STATE_HOME_IN_FRONT; 439 break; 440 } 441 return true; 442 } 443 444 boolean allResumedActivitiesVisible() { 445 for (int stackNdx = mStacks.size() - 1; stackNdx >= 0; --stackNdx) { 446 final ActivityStack stack = mStacks.get(stackNdx); 447 final ActivityRecord r = stack.mResumedActivity; 448 if (r != null && (!r.nowVisible || r.waitingVisible)) { 449 return false; 450 } 451 } 452 return true; 453 } 454 455 /** 456 * Pause all activities in either all of the stacks or just the back stacks. 457 * @param userLeaving Passed to pauseActivity() to indicate whether to call onUserLeaving(). 458 * @return true if any activity was paused as a result of this call. 459 */ 460 boolean pauseBackStacks(boolean userLeaving) { 461 boolean someActivityPaused = false; 462 for (int stackNdx = mStacks.size() - 1; stackNdx >= 0; --stackNdx) { 463 final ActivityStack stack = mStacks.get(stackNdx); 464 if (!isFrontStack(stack) && stack.mResumedActivity != null) { 465 if (DEBUG_STATES) Slog.d(TAG, "pauseBackStacks: stack=" + stack + 466 " mResumedActivity=" + stack.mResumedActivity); 467 stack.startPausingLocked(userLeaving, false); 468 someActivityPaused = true; 469 } 470 } 471 return someActivityPaused; 472 } 473 474 boolean allPausedActivitiesComplete() { 475 boolean pausing = true; 476 for (int stackNdx = mStacks.size() - 1; stackNdx >= 0; --stackNdx) { 477 final ActivityStack stack = mStacks.get(stackNdx); 478 final ActivityRecord r = stack.mPausingActivity; 479 if (r != null && r.state != ActivityState.PAUSED 480 && r.state != ActivityState.STOPPED 481 && r.state != ActivityState.STOPPING) { 482 if (DEBUG_STATES) { 483 Slog.d(TAG, "allPausedActivitiesComplete: r=" + r + " state=" + r.state); 484 pausing = false; 485 } else { 486 return false; 487 } 488 } 489 } 490 return pausing; 491 } 492 493 void reportActivityVisibleLocked(ActivityRecord r) { 494 for (int i = mWaitingActivityVisible.size()-1; i >= 0; i--) { 495 WaitResult w = mWaitingActivityVisible.get(i); 496 w.timeout = false; 497 if (r != null) { 498 w.who = new ComponentName(r.info.packageName, r.info.name); 499 } 500 w.totalTime = SystemClock.uptimeMillis() - w.thisTime; 501 w.thisTime = w.totalTime; 502 } 503 mService.notifyAll(); 504 dismissKeyguard(); 505 } 506 507 void reportActivityLaunchedLocked(boolean timeout, ActivityRecord r, 508 long thisTime, long totalTime) { 509 for (int i = mWaitingActivityLaunched.size() - 1; i >= 0; i--) { 510 WaitResult w = mWaitingActivityLaunched.remove(i); 511 w.timeout = timeout; 512 if (r != null) { 513 w.who = new ComponentName(r.info.packageName, r.info.name); 514 } 515 w.thisTime = thisTime; 516 w.totalTime = totalTime; 517 } 518 mService.notifyAll(); 519 } 520 521 ActivityRecord topRunningActivityLocked() { 522 final ActivityStack focusedStack = getFocusedStack(); 523 ActivityRecord r = focusedStack.topRunningActivityLocked(null); 524 if (r != null) { 525 return r; 526 } 527 528 for (int stackNdx = mStacks.size() - 1; stackNdx >= 0; --stackNdx) { 529 final ActivityStack stack = mStacks.get(stackNdx); 530 if (stack != focusedStack && isFrontStack(stack)) { 531 r = stack.topRunningActivityLocked(null); 532 if (r != null) { 533 return r; 534 } 535 } 536 } 537 return null; 538 } 539 540 ActivityRecord getTasksLocked(int maxNum, IThumbnailReceiver receiver, 541 PendingThumbnailsRecord pending, List<RunningTaskInfo> list) { 542 ActivityRecord r = null; 543 544 // Gather all of the running tasks for each stack into runningTaskLists. 545 final int numStacks = mStacks.size(); 546 ArrayList<RunningTaskInfo>[] runningTaskLists = new ArrayList[numStacks]; 547 for (int stackNdx = numStacks - 1; stackNdx >= 0; --stackNdx) { 548 final ActivityStack stack = mStacks.get(stackNdx); 549 ArrayList<RunningTaskInfo> stackTaskList = new ArrayList<RunningTaskInfo>(); 550 runningTaskLists[stackNdx] = stackTaskList; 551 final ActivityRecord ar = stack.getTasksLocked(receiver, pending, stackTaskList); 552 if (isFrontStack(stack)) { 553 r = ar; 554 } 555 } 556 557 // The lists are already sorted from most recent to oldest. Just pull the most recent off 558 // each list and add it to list. Stop when all lists are empty or maxNum reached. 559 while (maxNum > 0) { 560 long mostRecentActiveTime = Long.MIN_VALUE; 561 ArrayList<RunningTaskInfo> selectedStackList = null; 562 for (int stackNdx = 0; stackNdx < numStacks; ++stackNdx) { 563 ArrayList<RunningTaskInfo> stackTaskList = runningTaskLists[stackNdx]; 564 if (!stackTaskList.isEmpty()) { 565 final long lastActiveTime = stackTaskList.get(0).lastActiveTime; 566 if (lastActiveTime > mostRecentActiveTime) { 567 mostRecentActiveTime = lastActiveTime; 568 selectedStackList = stackTaskList; 569 } 570 } 571 } 572 if (selectedStackList != null) { 573 list.add(selectedStackList.remove(0)); 574 --maxNum; 575 } else { 576 break; 577 } 578 } 579 580 return r; 581 } 582 583 ActivityInfo resolveActivity(Intent intent, String resolvedType, int startFlags, 584 String profileFile, ParcelFileDescriptor profileFd, int userId) { 585 // Collect information about the target of the Intent. 586 ActivityInfo aInfo; 587 try { 588 ResolveInfo rInfo = 589 AppGlobals.getPackageManager().resolveIntent( 590 intent, resolvedType, 591 PackageManager.MATCH_DEFAULT_ONLY 592 | ActivityManagerService.STOCK_PM_FLAGS, userId); 593 aInfo = rInfo != null ? rInfo.activityInfo : null; 594 } catch (RemoteException e) { 595 aInfo = null; 596 } 597 598 if (aInfo != null) { 599 // Store the found target back into the intent, because now that 600 // we have it we never want to do this again. For example, if the 601 // user navigates back to this point in the history, we should 602 // always restart the exact same activity. 603 intent.setComponent(new ComponentName( 604 aInfo.applicationInfo.packageName, aInfo.name)); 605 606 // Don't debug things in the system process 607 if ((startFlags&ActivityManager.START_FLAG_DEBUG) != 0) { 608 if (!aInfo.processName.equals("system")) { 609 mService.setDebugApp(aInfo.processName, true, false); 610 } 611 } 612 613 if ((startFlags&ActivityManager.START_FLAG_OPENGL_TRACES) != 0) { 614 if (!aInfo.processName.equals("system")) { 615 mService.setOpenGlTraceApp(aInfo.applicationInfo, aInfo.processName); 616 } 617 } 618 619 if (profileFile != null) { 620 if (!aInfo.processName.equals("system")) { 621 mService.setProfileApp(aInfo.applicationInfo, aInfo.processName, 622 profileFile, profileFd, 623 (startFlags&ActivityManager.START_FLAG_AUTO_STOP_PROFILER) != 0); 624 } 625 } 626 } 627 return aInfo; 628 } 629 630 void startHomeActivity(Intent intent, ActivityInfo aInfo) { 631 moveHomeToTop(); 632 startActivityLocked(null, intent, null, aInfo, null, null, 0, 0, 0, null, 0, 633 null, false, null); 634 } 635 636 final int startActivityMayWait(IApplicationThread caller, int callingUid, 637 String callingPackage, Intent intent, String resolvedType, IBinder resultTo, 638 String resultWho, int requestCode, int startFlags, String profileFile, 639 ParcelFileDescriptor profileFd, WaitResult outResult, Configuration config, 640 Bundle options, int userId) { 641 // Refuse possible leaked file descriptors 642 if (intent != null && intent.hasFileDescriptors()) { 643 throw new IllegalArgumentException("File descriptors passed in Intent"); 644 } 645 boolean componentSpecified = intent.getComponent() != null; 646 647 // Don't modify the client's object! 648 intent = new Intent(intent); 649 650 // Collect information about the target of the Intent. 651 ActivityInfo aInfo = resolveActivity(intent, resolvedType, startFlags, 652 profileFile, profileFd, userId); 653 654 synchronized (mService) { 655 int callingPid; 656 if (callingUid >= 0) { 657 callingPid = -1; 658 } else if (caller == null) { 659 callingPid = Binder.getCallingPid(); 660 callingUid = Binder.getCallingUid(); 661 } else { 662 callingPid = callingUid = -1; 663 } 664 665 final ActivityStack stack = getFocusedStack(); 666 stack.mConfigWillChange = config != null 667 && mService.mConfiguration.diff(config) != 0; 668 if (DEBUG_CONFIGURATION) Slog.v(TAG, 669 "Starting activity when config will change = " + stack.mConfigWillChange); 670 671 final long origId = Binder.clearCallingIdentity(); 672 673 if (aInfo != null && 674 (aInfo.applicationInfo.flags&ApplicationInfo.FLAG_CANT_SAVE_STATE) != 0) { 675 // This may be a heavy-weight process! Check to see if we already 676 // have another, different heavy-weight process running. 677 if (aInfo.processName.equals(aInfo.applicationInfo.packageName)) { 678 if (mService.mHeavyWeightProcess != null && 679 (mService.mHeavyWeightProcess.info.uid != aInfo.applicationInfo.uid || 680 !mService.mHeavyWeightProcess.processName.equals(aInfo.processName))) { 681 int realCallingUid = callingUid; 682 if (caller != null) { 683 ProcessRecord callerApp = mService.getRecordForAppLocked(caller); 684 if (callerApp != null) { 685 realCallingUid = callerApp.info.uid; 686 } else { 687 Slog.w(TAG, "Unable to find app for caller " + caller 688 + " (pid=" + callingPid + ") when starting: " 689 + intent.toString()); 690 ActivityOptions.abort(options); 691 return ActivityManager.START_PERMISSION_DENIED; 692 } 693 } 694 695 IIntentSender target = mService.getIntentSenderLocked( 696 ActivityManager.INTENT_SENDER_ACTIVITY, "android", 697 realCallingUid, userId, null, null, 0, new Intent[] { intent }, 698 new String[] { resolvedType }, PendingIntent.FLAG_CANCEL_CURRENT 699 | PendingIntent.FLAG_ONE_SHOT, null); 700 701 Intent newIntent = new Intent(); 702 if (requestCode >= 0) { 703 // Caller is requesting a result. 704 newIntent.putExtra(HeavyWeightSwitcherActivity.KEY_HAS_RESULT, true); 705 } 706 newIntent.putExtra(HeavyWeightSwitcherActivity.KEY_INTENT, 707 new IntentSender(target)); 708 if (mService.mHeavyWeightProcess.activities.size() > 0) { 709 ActivityRecord hist = mService.mHeavyWeightProcess.activities.get(0); 710 newIntent.putExtra(HeavyWeightSwitcherActivity.KEY_CUR_APP, 711 hist.packageName); 712 newIntent.putExtra(HeavyWeightSwitcherActivity.KEY_CUR_TASK, 713 hist.task.taskId); 714 } 715 newIntent.putExtra(HeavyWeightSwitcherActivity.KEY_NEW_APP, 716 aInfo.packageName); 717 newIntent.setFlags(intent.getFlags()); 718 newIntent.setClassName("android", 719 HeavyWeightSwitcherActivity.class.getName()); 720 intent = newIntent; 721 resolvedType = null; 722 caller = null; 723 callingUid = Binder.getCallingUid(); 724 callingPid = Binder.getCallingPid(); 725 componentSpecified = true; 726 try { 727 ResolveInfo rInfo = 728 AppGlobals.getPackageManager().resolveIntent( 729 intent, null, 730 PackageManager.MATCH_DEFAULT_ONLY 731 | ActivityManagerService.STOCK_PM_FLAGS, userId); 732 aInfo = rInfo != null ? rInfo.activityInfo : null; 733 aInfo = mService.getActivityInfoForUser(aInfo, userId); 734 } catch (RemoteException e) { 735 aInfo = null; 736 } 737 } 738 } 739 } 740 741 int res = startActivityLocked(caller, intent, resolvedType, 742 aInfo, resultTo, resultWho, requestCode, callingPid, callingUid, 743 callingPackage, startFlags, options, componentSpecified, null); 744 745 if (stack.mConfigWillChange) { 746 // If the caller also wants to switch to a new configuration, 747 // do so now. This allows a clean switch, as we are waiting 748 // for the current activity to pause (so we will not destroy 749 // it), and have not yet started the next activity. 750 mService.enforceCallingPermission(android.Manifest.permission.CHANGE_CONFIGURATION, 751 "updateConfiguration()"); 752 stack.mConfigWillChange = false; 753 if (DEBUG_CONFIGURATION) Slog.v(TAG, 754 "Updating to new configuration after starting activity."); 755 mService.updateConfigurationLocked(config, null, false, false); 756 } 757 758 Binder.restoreCallingIdentity(origId); 759 760 if (outResult != null) { 761 outResult.result = res; 762 if (res == ActivityManager.START_SUCCESS) { 763 mWaitingActivityLaunched.add(outResult); 764 do { 765 try { 766 mService.wait(); 767 } catch (InterruptedException e) { 768 } 769 } while (!outResult.timeout && outResult.who == null); 770 } else if (res == ActivityManager.START_TASK_TO_FRONT) { 771 ActivityRecord r = stack.topRunningActivityLocked(null); 772 if (r.nowVisible) { 773 outResult.timeout = false; 774 outResult.who = new ComponentName(r.info.packageName, r.info.name); 775 outResult.totalTime = 0; 776 outResult.thisTime = 0; 777 } else { 778 outResult.thisTime = SystemClock.uptimeMillis(); 779 mWaitingActivityVisible.add(outResult); 780 do { 781 try { 782 mService.wait(); 783 } catch (InterruptedException e) { 784 } 785 } while (!outResult.timeout && outResult.who == null); 786 } 787 } 788 } 789 790 return res; 791 } 792 } 793 794 final int startActivities(IApplicationThread caller, int callingUid, String callingPackage, 795 Intent[] intents, String[] resolvedTypes, IBinder resultTo, 796 Bundle options, int userId) { 797 if (intents == null) { 798 throw new NullPointerException("intents is null"); 799 } 800 if (resolvedTypes == null) { 801 throw new NullPointerException("resolvedTypes is null"); 802 } 803 if (intents.length != resolvedTypes.length) { 804 throw new IllegalArgumentException("intents are length different than resolvedTypes"); 805 } 806 807 808 int callingPid; 809 if (callingUid >= 0) { 810 callingPid = -1; 811 } else if (caller == null) { 812 callingPid = Binder.getCallingPid(); 813 callingUid = Binder.getCallingUid(); 814 } else { 815 callingPid = callingUid = -1; 816 } 817 final long origId = Binder.clearCallingIdentity(); 818 try { 819 synchronized (mService) { 820 ActivityRecord[] outActivity = new ActivityRecord[1]; 821 for (int i=0; i<intents.length; i++) { 822 Intent intent = intents[i]; 823 if (intent == null) { 824 continue; 825 } 826 827 // Refuse possible leaked file descriptors 828 if (intent != null && intent.hasFileDescriptors()) { 829 throw new IllegalArgumentException("File descriptors passed in Intent"); 830 } 831 832 boolean componentSpecified = intent.getComponent() != null; 833 834 // Don't modify the client's object! 835 intent = new Intent(intent); 836 837 // Collect information about the target of the Intent. 838 ActivityInfo aInfo = resolveActivity(intent, resolvedTypes[i], 839 0, null, null, userId); 840 // TODO: New, check if this is correct 841 aInfo = mService.getActivityInfoForUser(aInfo, userId); 842 843 if (aInfo != null && 844 (aInfo.applicationInfo.flags & ApplicationInfo.FLAG_CANT_SAVE_STATE) 845 != 0) { 846 throw new IllegalArgumentException( 847 "FLAG_CANT_SAVE_STATE not supported here"); 848 } 849 850 Bundle theseOptions; 851 if (options != null && i == intents.length-1) { 852 theseOptions = options; 853 } else { 854 theseOptions = null; 855 } 856 int res = startActivityLocked(caller, intent, resolvedTypes[i], 857 aInfo, resultTo, null, -1, callingPid, callingUid, callingPackage, 858 0, theseOptions, componentSpecified, outActivity); 859 if (res < 0) { 860 return res; 861 } 862 863 resultTo = outActivity[0] != null ? outActivity[0].appToken : null; 864 } 865 } 866 } finally { 867 Binder.restoreCallingIdentity(origId); 868 } 869 870 return ActivityManager.START_SUCCESS; 871 } 872 873 final boolean realStartActivityLocked(ActivityRecord r, 874 ProcessRecord app, boolean andResume, boolean checkConfig) 875 throws RemoteException { 876 877 r.startFreezingScreenLocked(app, 0); 878 if (false) Slog.d(TAG, "realStartActivity: setting app visibility true"); 879 mWindowManager.setAppVisibility(r.appToken, true); 880 881 // schedule launch ticks to collect information about slow apps. 882 r.startLaunchTickingLocked(); 883 884 // Have the window manager re-evaluate the orientation of 885 // the screen based on the new activity order. Note that 886 // as a result of this, it can call back into the activity 887 // manager with a new orientation. We don't care about that, 888 // because the activity is not currently running so we are 889 // just restarting it anyway. 890 if (checkConfig) { 891 Configuration config = mWindowManager.updateOrientationFromAppTokens( 892 mService.mConfiguration, 893 r.mayFreezeScreenLocked(app) ? r.appToken : null); 894 mService.updateConfigurationLocked(config, r, false, false); 895 } 896 897 r.app = app; 898 app.waitingToKill = null; 899 r.launchCount++; 900 r.lastLaunchTime = SystemClock.uptimeMillis(); 901 902 if (localLOGV) Slog.v(TAG, "Launching: " + r); 903 904 int idx = app.activities.indexOf(r); 905 if (idx < 0) { 906 app.activities.add(r); 907 } 908 mService.updateLruProcessLocked(app, true, true); 909 910 final ActivityStack stack = r.task.stack; 911 try { 912 if (app.thread == null) { 913 throw new RemoteException(); 914 } 915 List<ResultInfo> results = null; 916 List<Intent> newIntents = null; 917 if (andResume) { 918 results = r.results; 919 newIntents = r.newIntents; 920 } 921 if (DEBUG_SWITCH) Slog.v(TAG, "Launching: " + r 922 + " icicle=" + r.icicle 923 + " with results=" + results + " newIntents=" + newIntents 924 + " andResume=" + andResume); 925 if (andResume) { 926 EventLog.writeEvent(EventLogTags.AM_RESTART_ACTIVITY, 927 r.userId, System.identityHashCode(r), 928 r.task.taskId, r.shortComponentName); 929 } 930 if (r.isHomeActivity() && r.isNotResolverActivity()) { 931 // Home process is the root process of the task. 932 mService.mHomeProcess = r.task.mActivities.get(0).app; 933 } 934 mService.ensurePackageDexOpt(r.intent.getComponent().getPackageName()); 935 r.sleeping = false; 936 r.forceNewConfig = false; 937 mService.showAskCompatModeDialogLocked(r); 938 r.compat = mService.compatibilityInfoForPackageLocked(r.info.applicationInfo); 939 String profileFile = null; 940 ParcelFileDescriptor profileFd = null; 941 boolean profileAutoStop = false; 942 if (mService.mProfileApp != null && mService.mProfileApp.equals(app.processName)) { 943 if (mService.mProfileProc == null || mService.mProfileProc == app) { 944 mService.mProfileProc = app; 945 profileFile = mService.mProfileFile; 946 profileFd = mService.mProfileFd; 947 profileAutoStop = mService.mAutoStopProfiler; 948 } 949 } 950 app.hasShownUi = true; 951 app.pendingUiClean = true; 952 if (profileFd != null) { 953 try { 954 profileFd = profileFd.dup(); 955 } catch (IOException e) { 956 if (profileFd != null) { 957 try { 958 profileFd.close(); 959 } catch (IOException o) { 960 } 961 profileFd = null; 962 } 963 } 964 } 965 app.forceProcessStateUpTo(ActivityManager.PROCESS_STATE_TOP); 966 app.thread.scheduleLaunchActivity(new Intent(r.intent), r.appToken, 967 System.identityHashCode(r), r.info, 968 new Configuration(mService.mConfiguration), r.compat, 969 app.repProcState, r.icicle, results, newIntents, !andResume, 970 mService.isNextTransitionForward(), profileFile, profileFd, 971 profileAutoStop); 972 973 if ((app.info.flags&ApplicationInfo.FLAG_CANT_SAVE_STATE) != 0) { 974 // This may be a heavy-weight process! Note that the package 975 // manager will ensure that only activity can run in the main 976 // process of the .apk, which is the only thing that will be 977 // considered heavy-weight. 978 if (app.processName.equals(app.info.packageName)) { 979 if (mService.mHeavyWeightProcess != null 980 && mService.mHeavyWeightProcess != app) { 981 Slog.w(TAG, "Starting new heavy weight process " + app 982 + " when already running " 983 + mService.mHeavyWeightProcess); 984 } 985 mService.mHeavyWeightProcess = app; 986 Message msg = mService.mHandler.obtainMessage( 987 ActivityManagerService.POST_HEAVY_NOTIFICATION_MSG); 988 msg.obj = r; 989 mService.mHandler.sendMessage(msg); 990 } 991 } 992 993 } catch (RemoteException e) { 994 if (r.launchFailed) { 995 // This is the second time we failed -- finish activity 996 // and give up. 997 Slog.e(TAG, "Second failure launching " 998 + r.intent.getComponent().flattenToShortString() 999 + ", giving up", e); 1000 mService.appDiedLocked(app, app.pid, app.thread); 1001 stack.requestFinishActivityLocked(r.appToken, Activity.RESULT_CANCELED, null, 1002 "2nd-crash", false); 1003 return false; 1004 } 1005 1006 // This is the first time we failed -- restart process and 1007 // retry. 1008 app.activities.remove(r); 1009 throw e; 1010 } 1011 1012 r.launchFailed = false; 1013 if (stack.updateLRUListLocked(r)) { 1014 Slog.w(TAG, "Activity " + r 1015 + " being launched, but already in LRU list"); 1016 } 1017 1018 if (andResume) { 1019 // As part of the process of launching, ActivityThread also performs 1020 // a resume. 1021 stack.minimalResumeActivityLocked(r); 1022 } else { 1023 // This activity is not starting in the resumed state... which 1024 // should look like we asked it to pause+stop (but remain visible), 1025 // and it has done so and reported back the current icicle and 1026 // other state. 1027 if (DEBUG_STATES) Slog.v(TAG, "Moving to STOPPED: " + r 1028 + " (starting in stopped state)"); 1029 r.state = ActivityState.STOPPED; 1030 r.stopped = true; 1031 } 1032 1033 // Launch the new version setup screen if needed. We do this -after- 1034 // launching the initial activity (that is, home), so that it can have 1035 // a chance to initialize itself while in the background, making the 1036 // switch back to it faster and look better. 1037 if (isFrontStack(stack)) { 1038 mService.startSetupActivityLocked(); 1039 } 1040 1041 return true; 1042 } 1043 1044 void startSpecificActivityLocked(ActivityRecord r, 1045 boolean andResume, boolean checkConfig) { 1046 // Is this activity's application already running? 1047 ProcessRecord app = mService.getProcessRecordLocked(r.processName, 1048 r.info.applicationInfo.uid, true); 1049 1050 r.task.stack.setLaunchTime(r); 1051 1052 if (app != null && app.thread != null) { 1053 try { 1054 if ((r.info.flags&ActivityInfo.FLAG_MULTIPROCESS) == 0 1055 || !"android".equals(r.info.packageName)) { 1056 // Don't add this if it is a platform component that is marked 1057 // to run in multiple processes, because this is actually 1058 // part of the framework so doesn't make sense to track as a 1059 // separate apk in the process. 1060 app.addPackage(r.info.packageName, mService.mProcessStats); 1061 } 1062 realStartActivityLocked(r, app, andResume, checkConfig); 1063 return; 1064 } catch (RemoteException e) { 1065 Slog.w(TAG, "Exception when starting activity " 1066 + r.intent.getComponent().flattenToShortString(), e); 1067 } 1068 1069 // If a dead object exception was thrown -- fall through to 1070 // restart the application. 1071 } 1072 1073 mService.startProcessLocked(r.processName, r.info.applicationInfo, true, 0, 1074 "activity", r.intent.getComponent(), false, false, true); 1075 } 1076 1077 final int startActivityLocked(IApplicationThread caller, 1078 Intent intent, String resolvedType, ActivityInfo aInfo, IBinder resultTo, 1079 String resultWho, int requestCode, 1080 int callingPid, int callingUid, String callingPackage, int startFlags, Bundle options, 1081 boolean componentSpecified, ActivityRecord[] outActivity) { 1082 int err = ActivityManager.START_SUCCESS; 1083 1084 ProcessRecord callerApp = null; 1085 if (caller != null) { 1086 callerApp = mService.getRecordForAppLocked(caller); 1087 if (callerApp != null) { 1088 callingPid = callerApp.pid; 1089 callingUid = callerApp.info.uid; 1090 } else { 1091 Slog.w(TAG, "Unable to find app for caller " + caller 1092 + " (pid=" + callingPid + ") when starting: " 1093 + intent.toString()); 1094 err = ActivityManager.START_PERMISSION_DENIED; 1095 } 1096 } 1097 1098 if (err == ActivityManager.START_SUCCESS) { 1099 final int userId = aInfo != null ? UserHandle.getUserId(aInfo.applicationInfo.uid) : 0; 1100 Slog.i(TAG, "START u" + userId + " {" + intent.toShortString(true, true, true, false) 1101 + "} from pid " + (callerApp != null ? callerApp.pid : callingPid)); 1102 } 1103 1104 ActivityRecord sourceRecord = null; 1105 ActivityRecord resultRecord = null; 1106 if (resultTo != null) { 1107 sourceRecord = isInAnyStackLocked(resultTo); 1108 if (DEBUG_RESULTS) Slog.v( 1109 TAG, "Will send result to " + resultTo + " " + sourceRecord); 1110 if (sourceRecord != null) { 1111 if (requestCode >= 0 && !sourceRecord.finishing) { 1112 resultRecord = sourceRecord; 1113 } 1114 } 1115 } 1116 ActivityStack resultStack = resultRecord == null ? null : resultRecord.task.stack; 1117 1118 int launchFlags = intent.getFlags(); 1119 1120 if ((launchFlags&Intent.FLAG_ACTIVITY_FORWARD_RESULT) != 0 1121 && sourceRecord != null) { 1122 // Transfer the result target from the source activity to the new 1123 // one being started, including any failures. 1124 if (requestCode >= 0) { 1125 ActivityOptions.abort(options); 1126 return ActivityManager.START_FORWARD_AND_REQUEST_CONFLICT; 1127 } 1128 resultRecord = sourceRecord.resultTo; 1129 resultWho = sourceRecord.resultWho; 1130 requestCode = sourceRecord.requestCode; 1131 sourceRecord.resultTo = null; 1132 if (resultRecord != null) { 1133 resultRecord.removeResultsLocked( 1134 sourceRecord, resultWho, requestCode); 1135 } 1136 } 1137 1138 if (err == ActivityManager.START_SUCCESS && intent.getComponent() == null) { 1139 // We couldn't find a class that can handle the given Intent. 1140 // That's the end of that! 1141 err = ActivityManager.START_INTENT_NOT_RESOLVED; 1142 } 1143 1144 if (err == ActivityManager.START_SUCCESS && aInfo == null) { 1145 // We couldn't find the specific class specified in the Intent. 1146 // Also the end of the line. 1147 err = ActivityManager.START_CLASS_NOT_FOUND; 1148 } 1149 1150 if (err != ActivityManager.START_SUCCESS) { 1151 if (resultRecord != null) { 1152 resultStack.sendActivityResultLocked(-1, 1153 resultRecord, resultWho, requestCode, 1154 Activity.RESULT_CANCELED, null); 1155 } 1156 setDismissKeyguard(false); 1157 ActivityOptions.abort(options); 1158 return err; 1159 } 1160 1161 final int startAnyPerm = mService.checkPermission( 1162 START_ANY_ACTIVITY, callingPid, callingUid); 1163 final int componentPerm = mService.checkComponentPermission(aInfo.permission, callingPid, 1164 callingUid, aInfo.applicationInfo.uid, aInfo.exported); 1165 if (startAnyPerm != PERMISSION_GRANTED && componentPerm != PERMISSION_GRANTED) { 1166 if (resultRecord != null) { 1167 resultStack.sendActivityResultLocked(-1, 1168 resultRecord, resultWho, requestCode, 1169 Activity.RESULT_CANCELED, null); 1170 } 1171 setDismissKeyguard(false); 1172 String msg; 1173 if (!aInfo.exported) { 1174 msg = "Permission Denial: starting " + intent.toString() 1175 + " from " + callerApp + " (pid=" + callingPid 1176 + ", uid=" + callingUid + ")" 1177 + " not exported from uid " + aInfo.applicationInfo.uid; 1178 } else { 1179 msg = "Permission Denial: starting " + intent.toString() 1180 + " from " + callerApp + " (pid=" + callingPid 1181 + ", uid=" + callingUid + ")" 1182 + " requires " + aInfo.permission; 1183 } 1184 Slog.w(TAG, msg); 1185 throw new SecurityException(msg); 1186 } 1187 1188 boolean abort = !mService.mIntentFirewall.checkStartActivity(intent, callingUid, 1189 callingPid, resolvedType, aInfo.applicationInfo); 1190 1191 if (mService.mController != null) { 1192 try { 1193 // The Intent we give to the watcher has the extra data 1194 // stripped off, since it can contain private information. 1195 Intent watchIntent = intent.cloneFilter(); 1196 abort |= !mService.mController.activityStarting(watchIntent, 1197 aInfo.applicationInfo.packageName); 1198 } catch (RemoteException e) { 1199 mService.mController = null; 1200 } 1201 } 1202 1203 if (abort) { 1204 if (resultRecord != null) { 1205 resultStack.sendActivityResultLocked(-1, resultRecord, resultWho, requestCode, 1206 Activity.RESULT_CANCELED, null); 1207 } 1208 // We pretend to the caller that it was really started, but 1209 // they will just get a cancel result. 1210 setDismissKeyguard(false); 1211 ActivityOptions.abort(options); 1212 return ActivityManager.START_SUCCESS; 1213 } 1214 1215 ActivityRecord r = new ActivityRecord(mService, callerApp, callingUid, callingPackage, 1216 intent, resolvedType, aInfo, mService.mConfiguration, 1217 resultRecord, resultWho, requestCode, componentSpecified, this); 1218 if (outActivity != null) { 1219 outActivity[0] = r; 1220 } 1221 1222 final ActivityStack stack = getFocusedStack(); 1223 if (stack.mResumedActivity == null 1224 || stack.mResumedActivity.info.applicationInfo.uid != callingUid) { 1225 if (!mService.checkAppSwitchAllowedLocked(callingPid, callingUid, "Activity start")) { 1226 PendingActivityLaunch pal = 1227 new PendingActivityLaunch(r, sourceRecord, startFlags, stack); 1228 mService.mPendingActivityLaunches.add(pal); 1229 setDismissKeyguard(false); 1230 ActivityOptions.abort(options); 1231 return ActivityManager.START_SWITCHES_CANCELED; 1232 } 1233 } 1234 1235 if (mService.mDidAppSwitch) { 1236 // This is the second allowed switch since we stopped switches, 1237 // so now just generally allow switches. Use case: user presses 1238 // home (switches disabled, switch to home, mDidAppSwitch now true); 1239 // user taps a home icon (coming from home so allowed, we hit here 1240 // and now allow anyone to switch again). 1241 mService.mAppSwitchesAllowedTime = 0; 1242 } else { 1243 mService.mDidAppSwitch = true; 1244 } 1245 1246 mService.doPendingActivityLaunchesLocked(false); 1247 1248 err = startActivityUncheckedLocked(r, sourceRecord, startFlags, true, options); 1249 1250 if (allPausedActivitiesComplete()) { 1251 // If someone asked to have the keyguard dismissed on the next 1252 // activity start, but we are not actually doing an activity 1253 // switch... just dismiss the keyguard now, because we 1254 // probably want to see whatever is behind it. 1255 dismissKeyguard(); 1256 } 1257 return err; 1258 } 1259 1260 ActivityStack adjustStackFocus(ActivityRecord r) { 1261 final TaskRecord task = r.task; 1262 if (r.isApplicationActivity() || (task != null && task.isApplicationTask())) { 1263 if (task != null) { 1264 final ActivityStack taskStack = task.stack; 1265 if (mFocusedStack != taskStack) { 1266 if (DEBUG_FOCUS || DEBUG_STACK) Slog.d(TAG, 1267 "adjustStackFocus: Setting focused stack to r=" + r + " task=" + task); 1268 mFocusedStack = taskStack.isHomeStack() ? null : taskStack; 1269 } else { 1270 if (DEBUG_FOCUS || DEBUG_STACK) Slog.d(TAG, 1271 "adjustStackFocus: Focused stack already=" + mFocusedStack); 1272 } 1273 return taskStack; 1274 } 1275 1276 if (mFocusedStack != null) { 1277 if (DEBUG_FOCUS || DEBUG_STACK) Slog.d(TAG, 1278 "adjustStackFocus: Have a focused stack=" + mFocusedStack); 1279 return mFocusedStack; 1280 } 1281 1282 for (int stackNdx = mStacks.size() - 1; stackNdx > 0; --stackNdx) { 1283 ActivityStack stack = mStacks.get(stackNdx); 1284 if (!stack.isHomeStack()) { 1285 if (DEBUG_FOCUS || DEBUG_STACK) Slog.d(TAG, 1286 "adjustStackFocus: Setting focused stack=" + stack); 1287 mFocusedStack = stack; 1288 return mFocusedStack; 1289 } 1290 } 1291 1292 // Time to create the first app stack for this user. 1293 int stackId = 1294 mService.createStack(-1, HOME_STACK_ID, StackBox.TASK_STACK_GOES_OVER, 1.0f); 1295 if (DEBUG_FOCUS || DEBUG_STACK) Slog.d(TAG, "adjustStackFocus: New stack r=" + r + 1296 " stackId=" + stackId); 1297 mFocusedStack = getStack(stackId); 1298 return mFocusedStack; 1299 } 1300 return mHomeStack; 1301 } 1302 1303 void setFocusedStack(ActivityRecord r) { 1304 if (r == null) { 1305 return; 1306 } 1307 if (!r.isApplicationActivity() || (r.task != null && !r.task.isApplicationTask())) { 1308 if (mStackState != STACK_STATE_HOME_IN_FRONT) { 1309 if (DEBUG_STACK || DEBUG_FOCUS) Slog.d(TAG, "setFocusedStack: mStackState old=" + 1310 stackStateToString(mStackState) + " new=" + 1311 stackStateToString(STACK_STATE_HOME_TO_FRONT) + 1312 " Callers=" + Debug.getCallers(3)); 1313 mStackState = STACK_STATE_HOME_TO_FRONT; 1314 } 1315 } else { 1316 if (DEBUG_FOCUS || DEBUG_STACK) Slog.d(TAG, 1317 "setFocusedStack: Setting focused stack to r=" + r + " task=" + r.task + 1318 " Callers=" + Debug.getCallers(3)); 1319 final ActivityStack taskStack = r.task.stack; 1320 mFocusedStack = taskStack.isHomeStack() ? null : taskStack; 1321 if (mStackState != STACK_STATE_HOME_IN_BACK) { 1322 if (DEBUG_STACK) Slog.d(TAG, "setFocusedStack: mStackState old=" + 1323 stackStateToString(mStackState) + " new=" + 1324 stackStateToString(STACK_STATE_HOME_TO_BACK) + 1325 " Callers=" + Debug.getCallers(3)); 1326 mStackState = STACK_STATE_HOME_TO_BACK; 1327 } 1328 } 1329 } 1330 1331 final int startActivityUncheckedLocked(ActivityRecord r, 1332 ActivityRecord sourceRecord, int startFlags, boolean doResume, 1333 Bundle options) { 1334 final Intent intent = r.intent; 1335 final int callingUid = r.launchedFromUid; 1336 1337 int launchFlags = intent.getFlags(); 1338 1339 // We'll invoke onUserLeaving before onPause only if the launching 1340 // activity did not explicitly state that this is an automated launch. 1341 mUserLeaving = (launchFlags&Intent.FLAG_ACTIVITY_NO_USER_ACTION) == 0; 1342 if (DEBUG_USER_LEAVING) Slog.v(TAG, "startActivity() => mUserLeaving=" + mUserLeaving); 1343 1344 // If the caller has asked not to resume at this point, we make note 1345 // of this in the record so that we can skip it when trying to find 1346 // the top running activity. 1347 if (!doResume) { 1348 r.delayedResume = true; 1349 } 1350 1351 ActivityRecord notTop = (launchFlags&Intent.FLAG_ACTIVITY_PREVIOUS_IS_TOP) != 0 ? r : null; 1352 1353 // If the onlyIfNeeded flag is set, then we can do this if the activity 1354 // being launched is the same as the one making the call... or, as 1355 // a special case, if we do not know the caller then we count the 1356 // current top activity as the caller. 1357 if ((startFlags&ActivityManager.START_FLAG_ONLY_IF_NEEDED) != 0) { 1358 ActivityRecord checkedCaller = sourceRecord; 1359 if (checkedCaller == null) { 1360 checkedCaller = getFocusedStack().topRunningNonDelayedActivityLocked(notTop); 1361 } 1362 if (!checkedCaller.realActivity.equals(r.realActivity)) { 1363 // Caller is not the same as launcher, so always needed. 1364 startFlags &= ~ActivityManager.START_FLAG_ONLY_IF_NEEDED; 1365 } 1366 } 1367 1368 if (sourceRecord == null) { 1369 // This activity is not being started from another... in this 1370 // case we -always- start a new task. 1371 if ((launchFlags&Intent.FLAG_ACTIVITY_NEW_TASK) == 0) { 1372 Slog.w(TAG, "startActivity called from non-Activity context; forcing " + 1373 "Intent.FLAG_ACTIVITY_NEW_TASK for: " + intent); 1374 launchFlags |= Intent.FLAG_ACTIVITY_NEW_TASK; 1375 } 1376 } else if (sourceRecord.launchMode == ActivityInfo.LAUNCH_SINGLE_INSTANCE) { 1377 // The original activity who is starting us is running as a single 1378 // instance... this new activity it is starting must go on its 1379 // own task. 1380 launchFlags |= Intent.FLAG_ACTIVITY_NEW_TASK; 1381 } else if (r.launchMode == ActivityInfo.LAUNCH_SINGLE_INSTANCE 1382 || r.launchMode == ActivityInfo.LAUNCH_SINGLE_TASK) { 1383 // The activity being started is a single instance... it always 1384 // gets launched into its own task. 1385 launchFlags |= Intent.FLAG_ACTIVITY_NEW_TASK; 1386 } 1387 1388 final ActivityStack sourceStack; 1389 if (sourceRecord != null) { 1390 if (sourceRecord.finishing) { 1391 // If the source is finishing, we can't further count it as our source. This 1392 // is because the task it is associated with may now be empty and on its way out, 1393 // so we don't want to blindly throw it in to that task. Instead we will take 1394 // the NEW_TASK flow and try to find a task for it. 1395 if ((launchFlags&Intent.FLAG_ACTIVITY_NEW_TASK) == 0) { 1396 Slog.w(TAG, "startActivity called from finishing " + sourceRecord 1397 + "; forcing " + "Intent.FLAG_ACTIVITY_NEW_TASK for: " + intent); 1398 launchFlags |= Intent.FLAG_ACTIVITY_NEW_TASK; 1399 } 1400 sourceRecord = null; 1401 sourceStack = null; 1402 } else { 1403 sourceStack = sourceRecord.task.stack; 1404 } 1405 } else { 1406 sourceStack = null; 1407 } 1408 1409 if (r.resultTo != null && (launchFlags&Intent.FLAG_ACTIVITY_NEW_TASK) != 0) { 1410 // For whatever reason this activity is being launched into a new 1411 // task... yet the caller has requested a result back. Well, that 1412 // is pretty messed up, so instead immediately send back a cancel 1413 // and let the new task continue launched as normal without a 1414 // dependency on its originator. 1415 Slog.w(TAG, "Activity is launching as a new task, so cancelling activity result."); 1416 r.resultTo.task.stack.sendActivityResultLocked(-1, 1417 r.resultTo, r.resultWho, r.requestCode, 1418 Activity.RESULT_CANCELED, null); 1419 r.resultTo = null; 1420 } 1421 1422 boolean addingToTask = false; 1423 boolean movedHome = false; 1424 TaskRecord reuseTask = null; 1425 ActivityStack targetStack; 1426 if (((launchFlags&Intent.FLAG_ACTIVITY_NEW_TASK) != 0 && 1427 (launchFlags&Intent.FLAG_ACTIVITY_MULTIPLE_TASK) == 0) 1428 || r.launchMode == ActivityInfo.LAUNCH_SINGLE_TASK 1429 || r.launchMode == ActivityInfo.LAUNCH_SINGLE_INSTANCE) { 1430 // If bring to front is requested, and no result is requested, and 1431 // we can find a task that was started with this same 1432 // component, then instead of launching bring that one to the front. 1433 if (r.resultTo == null) { 1434 // See if there is a task to bring to the front. If this is 1435 // a SINGLE_INSTANCE activity, there can be one and only one 1436 // instance of it in the history, and it is always in its own 1437 // unique task, so we do a special search. 1438 ActivityRecord intentActivity = r.launchMode != ActivityInfo.LAUNCH_SINGLE_INSTANCE 1439 ? findTaskLocked(r) 1440 : findActivityLocked(intent, r.info); 1441 if (intentActivity != null) { 1442 if (r.task == null) { 1443 r.task = intentActivity.task; 1444 } 1445 targetStack = intentActivity.task.stack; 1446 targetStack.mLastPausedActivity = null; 1447 if (DEBUG_TASKS) Slog.d(TAG, "Bring to front target: " + targetStack 1448 + " from " + intentActivity); 1449 moveHomeStack(targetStack.isHomeStack()); 1450 if (intentActivity.task.intent == null) { 1451 // This task was started because of movement of 1452 // the activity based on affinity... now that we 1453 // are actually launching it, we can assign the 1454 // base intent. 1455 intentActivity.task.setIntent(intent, r.info); 1456 } 1457 // If the target task is not in the front, then we need 1458 // to bring it to the front... except... well, with 1459 // SINGLE_TASK_LAUNCH it's not entirely clear. We'd like 1460 // to have the same behavior as if a new instance was 1461 // being started, which means not bringing it to the front 1462 // if the caller is not itself in the front. 1463 final ActivityStack lastStack = getLastStack(); 1464 ActivityRecord curTop = lastStack == null? 1465 null : lastStack.topRunningNonDelayedActivityLocked(notTop); 1466 if (curTop != null && (curTop.task != intentActivity.task || 1467 curTop.task != lastStack.topTask())) { 1468 r.intent.addFlags(Intent.FLAG_ACTIVITY_BROUGHT_TO_FRONT); 1469 if (sourceRecord == null || (sourceStack.topActivity() != null && 1470 sourceStack.topActivity().task == sourceRecord.task)) { 1471 // We really do want to push this one into the 1472 // user's face, right now. 1473 movedHome = true; 1474 targetStack.moveTaskToFrontLocked(intentActivity.task, r, options); 1475 if ((launchFlags & 1476 (FLAG_ACTIVITY_NEW_TASK | FLAG_ACTIVITY_TASK_ON_HOME)) 1477 == (FLAG_ACTIVITY_NEW_TASK | FLAG_ACTIVITY_TASK_ON_HOME)) { 1478 // Caller wants to appear on home activity. 1479 intentActivity.task.mOnTopOfHome = true; 1480 } 1481 options = null; 1482 } 1483 } 1484 // If the caller has requested that the target task be 1485 // reset, then do so. 1486 if ((launchFlags&Intent.FLAG_ACTIVITY_RESET_TASK_IF_NEEDED) != 0) { 1487 intentActivity = targetStack.resetTaskIfNeededLocked(intentActivity, r); 1488 } 1489 if ((startFlags&ActivityManager.START_FLAG_ONLY_IF_NEEDED) != 0) { 1490 // We don't need to start a new activity, and 1491 // the client said not to do anything if that 1492 // is the case, so this is it! And for paranoia, make 1493 // sure we have correctly resumed the top activity. 1494 if (doResume) { 1495 resumeTopActivitiesLocked(targetStack, null, options); 1496 } else { 1497 ActivityOptions.abort(options); 1498 } 1499 if (r.task == null) Slog.v(TAG, 1500 "startActivityUncheckedLocked: task left null", 1501 new RuntimeException("here").fillInStackTrace()); 1502 return ActivityManager.START_RETURN_INTENT_TO_CALLER; 1503 } 1504 if ((launchFlags & 1505 (Intent.FLAG_ACTIVITY_NEW_TASK|Intent.FLAG_ACTIVITY_CLEAR_TASK)) 1506 == (Intent.FLAG_ACTIVITY_NEW_TASK|Intent.FLAG_ACTIVITY_CLEAR_TASK)) { 1507 // The caller has requested to completely replace any 1508 // existing task with its new activity. Well that should 1509 // not be too hard... 1510 reuseTask = intentActivity.task; 1511 reuseTask.performClearTaskLocked(); 1512 reuseTask.setIntent(r.intent, r.info); 1513 } else if ((launchFlags&Intent.FLAG_ACTIVITY_CLEAR_TOP) != 0 1514 || r.launchMode == ActivityInfo.LAUNCH_SINGLE_TASK 1515 || r.launchMode == ActivityInfo.LAUNCH_SINGLE_INSTANCE) { 1516 // In this situation we want to remove all activities 1517 // from the task up to the one being started. In most 1518 // cases this means we are resetting the task to its 1519 // initial state. 1520 ActivityRecord top = 1521 intentActivity.task.performClearTaskLocked(r, launchFlags); 1522 if (top != null) { 1523 if (top.frontOfTask) { 1524 // Activity aliases may mean we use different 1525 // intents for the top activity, so make sure 1526 // the task now has the identity of the new 1527 // intent. 1528 top.task.setIntent(r.intent, r.info); 1529 } 1530 ActivityStack.logStartActivity(EventLogTags.AM_NEW_INTENT, 1531 r, top.task); 1532 top.deliverNewIntentLocked(callingUid, r.intent); 1533 } else { 1534 // A special case: we need to 1535 // start the activity because it is not currently 1536 // running, and the caller has asked to clear the 1537 // current task to have this activity at the top. 1538 addingToTask = true; 1539 // Now pretend like this activity is being started 1540 // by the top of its task, so it is put in the 1541 // right place. 1542 sourceRecord = intentActivity; 1543 } 1544 } else if (r.realActivity.equals(intentActivity.task.realActivity)) { 1545 // In this case the top activity on the task is the 1546 // same as the one being launched, so we take that 1547 // as a request to bring the task to the foreground. 1548 // If the top activity in the task is the root 1549 // activity, deliver this new intent to it if it 1550 // desires. 1551 if (((launchFlags&Intent.FLAG_ACTIVITY_SINGLE_TOP) != 0 1552 || r.launchMode == ActivityInfo.LAUNCH_SINGLE_TOP) 1553 && intentActivity.realActivity.equals(r.realActivity)) { 1554 ActivityStack.logStartActivity(EventLogTags.AM_NEW_INTENT, r, 1555 intentActivity.task); 1556 if (intentActivity.frontOfTask) { 1557 intentActivity.task.setIntent(r.intent, r.info); 1558 } 1559 intentActivity.deliverNewIntentLocked(callingUid, r.intent); 1560 } else if (!r.intent.filterEquals(intentActivity.task.intent)) { 1561 // In this case we are launching the root activity 1562 // of the task, but with a different intent. We 1563 // should start a new instance on top. 1564 addingToTask = true; 1565 sourceRecord = intentActivity; 1566 } 1567 } else if ((launchFlags&Intent.FLAG_ACTIVITY_RESET_TASK_IF_NEEDED) == 0) { 1568 // In this case an activity is being launched in to an 1569 // existing task, without resetting that task. This 1570 // is typically the situation of launching an activity 1571 // from a notification or shortcut. We want to place 1572 // the new activity on top of the current task. 1573 addingToTask = true; 1574 sourceRecord = intentActivity; 1575 } else if (!intentActivity.task.rootWasReset) { 1576 // In this case we are launching in to an existing task 1577 // that has not yet been started from its front door. 1578 // The current task has been brought to the front. 1579 // Ideally, we'd probably like to place this new task 1580 // at the bottom of its stack, but that's a little hard 1581 // to do with the current organization of the code so 1582 // for now we'll just drop it. 1583 intentActivity.task.setIntent(r.intent, r.info); 1584 } 1585 if (!addingToTask && reuseTask == null) { 1586 // We didn't do anything... but it was needed (a.k.a., client 1587 // don't use that intent!) And for paranoia, make 1588 // sure we have correctly resumed the top activity. 1589 if (doResume) { 1590 targetStack.resumeTopActivityLocked(null, options); 1591 } else { 1592 ActivityOptions.abort(options); 1593 } 1594 if (r.task == null) Slog.v(TAG, 1595 "startActivityUncheckedLocked: task left null", 1596 new RuntimeException("here").fillInStackTrace()); 1597 return ActivityManager.START_TASK_TO_FRONT; 1598 } 1599 } 1600 } 1601 } 1602 1603 //String uri = r.intent.toURI(); 1604 //Intent intent2 = new Intent(uri); 1605 //Slog.i(TAG, "Given intent: " + r.intent); 1606 //Slog.i(TAG, "URI is: " + uri); 1607 //Slog.i(TAG, "To intent: " + intent2); 1608 1609 if (r.packageName != null) { 1610 // If the activity being launched is the same as the one currently 1611 // at the top, then we need to check if it should only be launched 1612 // once. 1613 ActivityStack topStack = getFocusedStack(); 1614 ActivityRecord top = topStack.topRunningNonDelayedActivityLocked(notTop); 1615 if (top != null && r.resultTo == null) { 1616 if (top.realActivity.equals(r.realActivity) && top.userId == r.userId) { 1617 if (top.app != null && top.app.thread != null) { 1618 if ((launchFlags&Intent.FLAG_ACTIVITY_SINGLE_TOP) != 0 1619 || r.launchMode == ActivityInfo.LAUNCH_SINGLE_TOP 1620 || r.launchMode == ActivityInfo.LAUNCH_SINGLE_TASK) { 1621 ActivityStack.logStartActivity(EventLogTags.AM_NEW_INTENT, top, 1622 top.task); 1623 // For paranoia, make sure we have correctly 1624 // resumed the top activity. 1625 topStack.mLastPausedActivity = null; 1626 if (doResume) { 1627 resumeTopActivitiesLocked(); 1628 } 1629 ActivityOptions.abort(options); 1630 if ((startFlags&ActivityManager.START_FLAG_ONLY_IF_NEEDED) != 0) { 1631 // We don't need to start a new activity, and 1632 // the client said not to do anything if that 1633 // is the case, so this is it! 1634 if (r.task == null) Slog.v(TAG, 1635 "startActivityUncheckedLocked: task left null", 1636 new RuntimeException("here").fillInStackTrace()); 1637 return ActivityManager.START_RETURN_INTENT_TO_CALLER; 1638 } 1639 top.deliverNewIntentLocked(callingUid, r.intent); 1640 if (r.task == null) Slog.v(TAG, 1641 "startActivityUncheckedLocked: task left null", 1642 new RuntimeException("here").fillInStackTrace()); 1643 return ActivityManager.START_DELIVERED_TO_TOP; 1644 } 1645 } 1646 } 1647 } 1648 1649 } else { 1650 if (r.resultTo != null) { 1651 r.resultTo.task.stack.sendActivityResultLocked(-1, r.resultTo, r.resultWho, 1652 r.requestCode, Activity.RESULT_CANCELED, null); 1653 } 1654 ActivityOptions.abort(options); 1655 if (r.task == null) Slog.v(TAG, 1656 "startActivityUncheckedLocked: task left null", 1657 new RuntimeException("here").fillInStackTrace()); 1658 return ActivityManager.START_CLASS_NOT_FOUND; 1659 } 1660 1661 boolean newTask = false; 1662 boolean keepCurTransition = false; 1663 1664 // Should this be considered a new task? 1665 if (r.resultTo == null && !addingToTask 1666 && (launchFlags&Intent.FLAG_ACTIVITY_NEW_TASK) != 0) { 1667 targetStack = adjustStackFocus(r); 1668 moveHomeStack(targetStack.isHomeStack()); 1669 if (reuseTask == null) { 1670 r.setTask(targetStack.createTaskRecord(getNextTaskId(), r.info, intent, true), 1671 null, true); 1672 if (DEBUG_TASKS) Slog.v(TAG, "Starting new activity " + r + " in new task " + 1673 r.task); 1674 } else { 1675 r.setTask(reuseTask, reuseTask, true); 1676 } 1677 newTask = true; 1678 if (!movedHome) { 1679 if ((launchFlags & 1680 (Intent.FLAG_ACTIVITY_NEW_TASK|Intent.FLAG_ACTIVITY_TASK_ON_HOME)) 1681 == (Intent.FLAG_ACTIVITY_NEW_TASK|Intent.FLAG_ACTIVITY_TASK_ON_HOME)) { 1682 // Caller wants to appear on home activity, so before starting 1683 // their own activity we will bring home to the front. 1684 r.task.mOnTopOfHome = true; 1685 } 1686 } 1687 } else if (sourceRecord != null) { 1688 TaskRecord sourceTask = sourceRecord.task; 1689 targetStack = sourceTask.stack; 1690 moveHomeStack(targetStack.isHomeStack()); 1691 if (!addingToTask && 1692 (launchFlags&Intent.FLAG_ACTIVITY_CLEAR_TOP) != 0) { 1693 // In this case, we are adding the activity to an existing 1694 // task, but the caller has asked to clear that task if the 1695 // activity is already running. 1696 ActivityRecord top = sourceTask.performClearTaskLocked(r, launchFlags); 1697 keepCurTransition = true; 1698 if (top != null) { 1699 ActivityStack.logStartActivity(EventLogTags.AM_NEW_INTENT, r, top.task); 1700 top.deliverNewIntentLocked(callingUid, r.intent); 1701 // For paranoia, make sure we have correctly 1702 // resumed the top activity. 1703 targetStack.mLastPausedActivity = null; 1704 if (doResume) { 1705 targetStack.resumeTopActivityLocked(null); 1706 } 1707 ActivityOptions.abort(options); 1708 if (r.task == null) Slog.w(TAG, 1709 "startActivityUncheckedLocked: task left null", 1710 new RuntimeException("here").fillInStackTrace()); 1711 return ActivityManager.START_DELIVERED_TO_TOP; 1712 } 1713 } else if (!addingToTask && 1714 (launchFlags&Intent.FLAG_ACTIVITY_REORDER_TO_FRONT) != 0) { 1715 // In this case, we are launching an activity in our own task 1716 // that may already be running somewhere in the history, and 1717 // we want to shuffle it to the front of the stack if so. 1718 final ActivityRecord top = sourceTask.findActivityInHistoryLocked(r); 1719 if (top != null) { 1720 final TaskRecord task = top.task; 1721 task.moveActivityToFrontLocked(top); 1722 ActivityStack.logStartActivity(EventLogTags.AM_NEW_INTENT, r, task); 1723 top.updateOptionsLocked(options); 1724 top.deliverNewIntentLocked(callingUid, r.intent); 1725 targetStack.mLastPausedActivity = null; 1726 if (doResume) { 1727 targetStack.resumeTopActivityLocked(null); 1728 } 1729 return ActivityManager.START_DELIVERED_TO_TOP; 1730 } 1731 } 1732 // An existing activity is starting this new activity, so we want 1733 // to keep the new one in the same task as the one that is starting 1734 // it. 1735 r.setTask(sourceTask, sourceRecord.thumbHolder, false); 1736 if (DEBUG_TASKS) Slog.v(TAG, "Starting new activity " + r 1737 + " in existing task " + r.task + " from source " + sourceRecord); 1738 1739 } else { 1740 // This not being started from an existing activity, and not part 1741 // of a new task... just put it in the top task, though these days 1742 // this case should never happen. 1743 targetStack = adjustStackFocus(r); 1744 moveHomeStack(targetStack.isHomeStack()); 1745 ActivityRecord prev = targetStack.topActivity(); 1746 r.setTask(prev != null ? prev.task 1747 : targetStack.createTaskRecord(getNextTaskId(), r.info, intent, true), 1748 null, true); 1749 if (DEBUG_TASKS) Slog.v(TAG, "Starting new activity " + r 1750 + " in new guessed " + r.task); 1751 } 1752 1753 mService.grantUriPermissionFromIntentLocked(callingUid, r.packageName, 1754 intent, r.getUriPermissionsLocked()); 1755 1756 if (newTask) { 1757 EventLog.writeEvent(EventLogTags.AM_CREATE_TASK, r.userId, r.task.taskId); 1758 } 1759 ActivityStack.logStartActivity(EventLogTags.AM_CREATE_ACTIVITY, r, r.task); 1760 targetStack.mLastPausedActivity = null; 1761 targetStack.startActivityLocked(r, newTask, doResume, keepCurTransition, options); 1762 mService.setFocusedActivityLocked(r); 1763 return ActivityManager.START_SUCCESS; 1764 } 1765 1766 void acquireLaunchWakelock() { 1767 if (VALIDATE_WAKE_LOCK_CALLER && Binder.getCallingUid() != Process.myUid()) { 1768 throw new IllegalStateException("Calling must be system uid"); 1769 } 1770 mLaunchingActivity.acquire(); 1771 if (!mHandler.hasMessages(LAUNCH_TIMEOUT_MSG)) { 1772 // To be safe, don't allow the wake lock to be held for too long. 1773 mHandler.sendEmptyMessageDelayed(LAUNCH_TIMEOUT_MSG, LAUNCH_TIMEOUT); 1774 } 1775 } 1776 1777 // Checked. 1778 final ActivityRecord activityIdleInternalLocked(final IBinder token, boolean fromTimeout, 1779 Configuration config) { 1780 if (localLOGV) Slog.v(TAG, "Activity idle: " + token); 1781 1782 ArrayList<ActivityRecord> stops = null; 1783 ArrayList<ActivityRecord> finishes = null; 1784 ArrayList<UserStartedState> startingUsers = null; 1785 int NS = 0; 1786 int NF = 0; 1787 IApplicationThread sendThumbnail = null; 1788 boolean booting = false; 1789 boolean enableScreen = false; 1790 boolean activityRemoved = false; 1791 1792 ActivityRecord r = ActivityRecord.forToken(token); 1793 if (r != null) { 1794 if (DEBUG_IDLE) Slog.d(TAG, "activityIdleInternalLocked: Callers=" + 1795 Debug.getCallers(4)); 1796 mHandler.removeMessages(IDLE_TIMEOUT_MSG, r); 1797 r.finishLaunchTickingLocked(); 1798 if (fromTimeout) { 1799 reportActivityLaunchedLocked(fromTimeout, r, -1, -1); 1800 } 1801 1802 // This is a hack to semi-deal with a race condition 1803 // in the client where it can be constructed with a 1804 // newer configuration from when we asked it to launch. 1805 // We'll update with whatever configuration it now says 1806 // it used to launch. 1807 if (config != null) { 1808 r.configuration = config; 1809 } 1810 1811 // We are now idle. If someone is waiting for a thumbnail from 1812 // us, we can now deliver. 1813 r.idle = true; 1814 1815 if (r.thumbnailNeeded && r.app != null && r.app.thread != null) { 1816 sendThumbnail = r.app.thread; 1817 r.thumbnailNeeded = false; 1818 } 1819 1820 //Slog.i(TAG, "IDLE: mBooted=" + mBooted + ", fromTimeout=" + fromTimeout); 1821 if (!mService.mBooted && isFrontStack(r.task.stack)) { 1822 mService.mBooted = true; 1823 enableScreen = true; 1824 } 1825 } 1826 1827 if (allResumedActivitiesIdle()) { 1828 if (r != null) { 1829 mService.scheduleAppGcsLocked(); 1830 } 1831 1832 if (mLaunchingActivity.isHeld()) { 1833 mHandler.removeMessages(LAUNCH_TIMEOUT_MSG); 1834 if (VALIDATE_WAKE_LOCK_CALLER && 1835 Binder.getCallingUid() != Process.myUid()) { 1836 throw new IllegalStateException("Calling must be system uid"); 1837 } 1838 mLaunchingActivity.release(); 1839 } 1840 ensureActivitiesVisibleLocked(null, 0); 1841 } 1842 1843 // Atomically retrieve all of the other things to do. 1844 stops = processStoppingActivitiesLocked(true); 1845 NS = stops != null ? stops.size() : 0; 1846 if ((NF=mFinishingActivities.size()) > 0) { 1847 finishes = new ArrayList<ActivityRecord>(mFinishingActivities); 1848 mFinishingActivities.clear(); 1849 } 1850 1851 final ArrayList<ActivityRecord> thumbnails; 1852 final int NT = mCancelledThumbnails.size(); 1853 if (NT > 0) { 1854 thumbnails = new ArrayList<ActivityRecord>(mCancelledThumbnails); 1855 mCancelledThumbnails.clear(); 1856 } else { 1857 thumbnails = null; 1858 } 1859 1860 if (isFrontStack(mHomeStack)) { 1861 booting = mService.mBooting; 1862 mService.mBooting = false; 1863 } 1864 1865 if (mStartingUsers.size() > 0) { 1866 startingUsers = new ArrayList<UserStartedState>(mStartingUsers); 1867 mStartingUsers.clear(); 1868 } 1869 1870 // Perform the following actions from unsynchronized state. 1871 final IApplicationThread thumbnailThread = sendThumbnail; 1872 mHandler.post(new Runnable() { 1873 @Override 1874 public void run() { 1875 if (thumbnailThread != null) { 1876 try { 1877 thumbnailThread.requestThumbnail(token); 1878 } catch (Exception e) { 1879 Slog.w(TAG, "Exception thrown when requesting thumbnail", e); 1880 mService.sendPendingThumbnail(null, token, null, null, true); 1881 } 1882 } 1883 1884 // Report back to any thumbnail receivers. 1885 for (int i = 0; i < NT; i++) { 1886 ActivityRecord r = thumbnails.get(i); 1887 mService.sendPendingThumbnail(r, null, null, null, true); 1888 } 1889 } 1890 }); 1891 1892 // Stop any activities that are scheduled to do so but have been 1893 // waiting for the next one to start. 1894 for (int i = 0; i < NS; i++) { 1895 r = stops.get(i); 1896 final ActivityStack stack = r.task.stack; 1897 if (r.finishing) { 1898 stack.finishCurrentActivityLocked(r, ActivityStack.FINISH_IMMEDIATELY, false); 1899 } else { 1900 stack.stopActivityLocked(r); 1901 } 1902 } 1903 1904 // Finish any activities that are scheduled to do so but have been 1905 // waiting for the next one to start. 1906 for (int i = 0; i < NF; i++) { 1907 r = finishes.get(i); 1908 activityRemoved |= r.task.stack.destroyActivityLocked(r, true, false, "finish-idle"); 1909 } 1910 1911 if (booting) { 1912 mService.finishBooting(); 1913 } else if (startingUsers != null) { 1914 for (int i = 0; i < startingUsers.size(); i++) { 1915 mService.finishUserSwitch(startingUsers.get(i)); 1916 } 1917 } 1918 1919 mService.trimApplications(); 1920 //dump(); 1921 //mWindowManager.dump(); 1922 1923 if (enableScreen) { 1924 mService.enableScreenAfterBoot(); 1925 } 1926 1927 if (activityRemoved) { 1928 resumeTopActivitiesLocked(); 1929 } 1930 1931 return r; 1932 } 1933 1934 boolean handleAppDiedLocked(ProcessRecord app) { 1935 boolean hasVisibleActivities = false; 1936 for (int stackNdx = mStacks.size() - 1; stackNdx >= 0; --stackNdx) { 1937 hasVisibleActivities |= mStacks.get(stackNdx).handleAppDiedLocked(app); 1938 } 1939 return hasVisibleActivities; 1940 } 1941 1942 void closeSystemDialogsLocked() { 1943 final int numStacks = mStacks.size(); 1944 for (int stackNdx = 0; stackNdx < numStacks; ++stackNdx) { 1945 final ActivityStack stack = mStacks.get(stackNdx); 1946 stack.closeSystemDialogsLocked(); 1947 } 1948 } 1949 1950 void removeUserLocked(int userId) { 1951 mUserStackInFront.delete(userId); 1952 } 1953 1954 /** 1955 * @return true if some activity was finished (or would have finished if doit were true). 1956 */ 1957 boolean forceStopPackageLocked(String name, boolean doit, boolean evenPersistent, int userId) { 1958 boolean didSomething = false; 1959 final int numStacks = mStacks.size(); 1960 for (int stackNdx = 0; stackNdx < numStacks; ++stackNdx) { 1961 final ActivityStack stack = mStacks.get(stackNdx); 1962 if (stack.forceStopPackageLocked(name, doit, evenPersistent, userId)) { 1963 didSomething = true; 1964 } 1965 } 1966 return didSomething; 1967 } 1968 1969 void updatePreviousProcessLocked(ActivityRecord r) { 1970 // Now that this process has stopped, we may want to consider 1971 // it to be the previous app to try to keep around in case 1972 // the user wants to return to it. 1973 1974 // First, found out what is currently the foreground app, so that 1975 // we don't blow away the previous app if this activity is being 1976 // hosted by the process that is actually still the foreground. 1977 ProcessRecord fgApp = null; 1978 for (int stackNdx = mStacks.size() - 1; stackNdx >= 0; --stackNdx) { 1979 final ActivityStack stack = mStacks.get(stackNdx); 1980 if (isFrontStack(stack)) { 1981 if (stack.mResumedActivity != null) { 1982 fgApp = stack.mResumedActivity.app; 1983 } else if (stack.mPausingActivity != null) { 1984 fgApp = stack.mPausingActivity.app; 1985 } 1986 break; 1987 } 1988 } 1989 1990 // Now set this one as the previous process, only if that really 1991 // makes sense to. 1992 if (r.app != null && fgApp != null && r.app != fgApp 1993 && r.lastVisibleTime > mService.mPreviousProcessVisibleTime 1994 && r.app != mService.mHomeProcess) { 1995 mService.mPreviousProcess = r.app; 1996 mService.mPreviousProcessVisibleTime = r.lastVisibleTime; 1997 } 1998 } 1999 2000 boolean resumeTopActivitiesLocked() { 2001 return resumeTopActivitiesLocked(null, null, null); 2002 } 2003 2004 boolean resumeTopActivitiesLocked(ActivityStack targetStack, ActivityRecord target, 2005 Bundle targetOptions) { 2006 if (targetStack == null) { 2007 targetStack = getFocusedStack(); 2008 } 2009 boolean result = false; 2010 for (int stackNdx = mStacks.size() - 1; stackNdx >= 0; --stackNdx) { 2011 final ActivityStack stack = mStacks.get(stackNdx); 2012 if (isFrontStack(stack)) { 2013 if (stack == targetStack) { 2014 result = stack.resumeTopActivityLocked(target, targetOptions); 2015 } else { 2016 stack.resumeTopActivityLocked(null); 2017 } 2018 } 2019 } 2020 return result; 2021 } 2022 2023 void finishTopRunningActivityLocked(ProcessRecord app) { 2024 final int numStacks = mStacks.size(); 2025 for (int stackNdx = 0; stackNdx < numStacks; ++stackNdx) { 2026 final ActivityStack stack = mStacks.get(stackNdx); 2027 stack.finishTopRunningActivityLocked(app); 2028 } 2029 } 2030 2031 void findTaskToMoveToFrontLocked(int taskId, int flags, Bundle options) { 2032 for (int stackNdx = mStacks.size() - 1; stackNdx >= 0; --stackNdx) { 2033 if (mStacks.get(stackNdx).findTaskToMoveToFrontLocked(taskId, flags, options)) { 2034 if (DEBUG_STACK) Slog.d(TAG, "findTaskToMoveToFront: moved to front of stack=" + 2035 mStacks.get(stackNdx)); 2036 return; 2037 } 2038 } 2039 } 2040 2041 ActivityStack getStack(int stackId) { 2042 for (int stackNdx = mStacks.size() - 1; stackNdx >= 0; --stackNdx) { 2043 final ActivityStack stack = mStacks.get(stackNdx); 2044 if (stack.getStackId() == stackId) { 2045 return stack; 2046 } 2047 } 2048 return null; 2049 } 2050 2051 ArrayList<ActivityStack> getStacks() { 2052 return new ArrayList<ActivityStack>(mStacks); 2053 } 2054 2055 int createStack() { 2056 while (true) { 2057 if (++mLastStackId <= HOME_STACK_ID) { 2058 mLastStackId = HOME_STACK_ID + 1; 2059 } 2060 if (getStack(mLastStackId) == null) { 2061 break; 2062 } 2063 } 2064 mStacks.add(new ActivityStack(mService, mContext, mLooper, mLastStackId)); 2065 return mLastStackId; 2066 } 2067 2068 void moveTaskToStack(int taskId, int stackId, boolean toTop) { 2069 final TaskRecord task = anyTaskForIdLocked(taskId); 2070 if (task == null) { 2071 return; 2072 } 2073 final ActivityStack stack = getStack(stackId); 2074 if (stack == null) { 2075 Slog.w(TAG, "moveTaskToStack: no stack for id=" + stackId); 2076 return; 2077 } 2078 removeTask(task); 2079 stack.addTask(task, toTop); 2080 mWindowManager.addTask(taskId, stackId, toTop); 2081 resumeTopActivitiesLocked(); 2082 } 2083 2084 ActivityRecord findTaskLocked(ActivityRecord r) { 2085 if (DEBUG_TASKS) Slog.d(TAG, "Looking for task of " + r); 2086 for (int stackNdx = mStacks.size() - 1; stackNdx >= 0; --stackNdx) { 2087 final ActivityStack stack = mStacks.get(stackNdx); 2088 if (!r.isApplicationActivity() && !stack.isHomeStack()) { 2089 if (DEBUG_TASKS) Slog.d(TAG, "Skipping stack: " + stack); 2090 continue; 2091 } 2092 final ActivityRecord ar = stack.findTaskLocked(r); 2093 if (ar != null) { 2094 return ar; 2095 } 2096 } 2097 if (DEBUG_TASKS) Slog.d(TAG, "No task found"); 2098 return null; 2099 } 2100 2101 ActivityRecord findActivityLocked(Intent intent, ActivityInfo info) { 2102 for (int stackNdx = mStacks.size() - 1; stackNdx >= 0; --stackNdx) { 2103 final ActivityRecord ar = mStacks.get(stackNdx).findActivityLocked(intent, info); 2104 if (ar != null) { 2105 return ar; 2106 } 2107 } 2108 return null; 2109 } 2110 2111 void goingToSleepLocked() { 2112 scheduleSleepTimeout(); 2113 if (!mGoingToSleep.isHeld()) { 2114 mGoingToSleep.acquire(); 2115 if (mLaunchingActivity.isHeld()) { 2116 if (VALIDATE_WAKE_LOCK_CALLER && Binder.getCallingUid() != Process.myUid()) { 2117 throw new IllegalStateException("Calling must be system uid"); 2118 } 2119 mLaunchingActivity.release(); 2120 mService.mHandler.removeMessages(LAUNCH_TIMEOUT_MSG); 2121 } 2122 } 2123 checkReadyForSleepLocked(); 2124 } 2125 2126 boolean shutdownLocked(int timeout) { 2127 boolean timedout = false; 2128 goingToSleepLocked(); 2129 2130 final long endTime = System.currentTimeMillis() + timeout; 2131 while (true) { 2132 boolean cantShutdown = false; 2133 for (int stackNdx = mStacks.size() - 1; stackNdx >= 0; --stackNdx) { 2134 cantShutdown |= mStacks.get(stackNdx).checkReadyForSleepLocked(); 2135 } 2136 if (cantShutdown) { 2137 long timeRemaining = endTime - System.currentTimeMillis(); 2138 if (timeRemaining > 0) { 2139 try { 2140 mService.wait(timeRemaining); 2141 } catch (InterruptedException e) { 2142 } 2143 } else { 2144 Slog.w(TAG, "Activity manager shutdown timed out"); 2145 timedout = true; 2146 break; 2147 } 2148 } else { 2149 break; 2150 } 2151 } 2152 2153 // Force checkReadyForSleep to complete. 2154 mSleepTimeout = true; 2155 checkReadyForSleepLocked(); 2156 2157 return timedout; 2158 } 2159 2160 void comeOutOfSleepIfNeededLocked() { 2161 removeSleepTimeouts(); 2162 if (mGoingToSleep.isHeld()) { 2163 mGoingToSleep.release(); 2164 } 2165 for (int stackNdx = mStacks.size() - 1; stackNdx >= 0; --stackNdx) { 2166 final ActivityStack stack = mStacks.get(stackNdx); 2167 stack.awakeFromSleepingLocked(); 2168 if (isFrontStack(stack)) { 2169 resumeTopActivitiesLocked(); 2170 } 2171 } 2172 mGoingToSleepActivities.clear(); 2173 } 2174 2175 void activitySleptLocked(ActivityRecord r) { 2176 mGoingToSleepActivities.remove(r); 2177 checkReadyForSleepLocked(); 2178 } 2179 2180 void checkReadyForSleepLocked() { 2181 if (!mService.isSleepingOrShuttingDown()) { 2182 // Do not care. 2183 return; 2184 } 2185 2186 if (!mSleepTimeout) { 2187 boolean dontSleep = false; 2188 for (int stackNdx = mStacks.size() - 1; stackNdx >= 0; --stackNdx) { 2189 dontSleep |= mStacks.get(stackNdx).checkReadyForSleepLocked(); 2190 } 2191 2192 if (mStoppingActivities.size() > 0) { 2193 // Still need to tell some activities to stop; can't sleep yet. 2194 if (DEBUG_PAUSE) Slog.v(TAG, "Sleep still need to stop " 2195 + mStoppingActivities.size() + " activities"); 2196 scheduleIdleLocked(); 2197 dontSleep = true; 2198 } 2199 2200 if (mGoingToSleepActivities.size() > 0) { 2201 // Still need to tell some activities to sleep; can't sleep yet. 2202 if (DEBUG_PAUSE) Slog.v(TAG, "Sleep still need to sleep " 2203 + mGoingToSleepActivities.size() + " activities"); 2204 dontSleep = true; 2205 } 2206 2207 if (dontSleep) { 2208 return; 2209 } 2210 } 2211 2212 for (int stackNdx = mStacks.size() - 1; stackNdx >= 0; --stackNdx) { 2213 mStacks.get(stackNdx).goToSleep(); 2214 } 2215 2216 removeSleepTimeouts(); 2217 2218 if (mGoingToSleep.isHeld()) { 2219 mGoingToSleep.release(); 2220 } 2221 if (mService.mShuttingDown) { 2222 mService.notifyAll(); 2223 } 2224 } 2225 2226 boolean reportResumedActivityLocked(ActivityRecord r) { 2227 final ActivityStack stack = r.task.stack; 2228 if (isFrontStack(stack)) { 2229 mService.updateUsageStats(r, true); 2230 } 2231 if (allResumedActivitiesComplete()) { 2232 ensureActivitiesVisibleLocked(null, 0); 2233 mWindowManager.executeAppTransition(); 2234 return true; 2235 } 2236 return false; 2237 } 2238 2239 void handleAppCrashLocked(ProcessRecord app) { 2240 final int numStacks = mStacks.size(); 2241 for (int stackNdx = 0; stackNdx < numStacks; ++stackNdx) { 2242 final ActivityStack stack = mStacks.get(stackNdx); 2243 stack.handleAppCrashLocked(app); 2244 } 2245 } 2246 2247 void ensureActivitiesVisibleLocked(ActivityRecord starting, int configChanges) { 2248 // First the front stacks. In case any are not fullscreen and are in front of home. 2249 boolean showHomeBehindStack = false; 2250 for (int stackNdx = mStacks.size() - 1; stackNdx >= 0; --stackNdx) { 2251 final ActivityStack stack = mStacks.get(stackNdx); 2252 if (isFrontStack(stack)) { 2253 showHomeBehindStack = 2254 stack.ensureActivitiesVisibleLocked(starting, configChanges); 2255 } 2256 } 2257 // Now do back stacks. 2258 for (int stackNdx = mStacks.size() - 1; stackNdx >= 0; --stackNdx) { 2259 final ActivityStack stack = mStacks.get(stackNdx); 2260 if (!isFrontStack(stack)) { 2261 stack.ensureActivitiesVisibleLocked(starting, configChanges, showHomeBehindStack); 2262 } 2263 } 2264 } 2265 2266 void scheduleDestroyAllActivities(ProcessRecord app, String reason) { 2267 final int numStacks = mStacks.size(); 2268 for (int stackNdx = 0; stackNdx < numStacks; ++stackNdx) { 2269 final ActivityStack stack = mStacks.get(stackNdx); 2270 stack.scheduleDestroyActivities(app, false, reason); 2271 } 2272 } 2273 2274 boolean switchUserLocked(int userId, UserStartedState uss) { 2275 mUserStackInFront.put(mCurrentUser, getFocusedStack().getStackId()); 2276 final int restoreStackId = mUserStackInFront.get(userId, HOME_STACK_ID); 2277 mCurrentUser = userId; 2278 2279 mStartingUsers.add(uss); 2280 for (int stackNdx = mStacks.size() - 1; stackNdx >= 0; --stackNdx) { 2281 mStacks.get(stackNdx).switchUserLocked(userId); 2282 } 2283 2284 ActivityStack stack = getStack(restoreStackId); 2285 if (stack == null) { 2286 stack = mHomeStack; 2287 } 2288 final boolean homeInFront = stack.isHomeStack(); 2289 moveHomeStack(homeInFront); 2290 mWindowManager.moveTaskToTop(stack.topTask().taskId); 2291 return homeInFront; 2292 } 2293 2294 final ArrayList<ActivityRecord> processStoppingActivitiesLocked(boolean remove) { 2295 int N = mStoppingActivities.size(); 2296 if (N <= 0) return null; 2297 2298 ArrayList<ActivityRecord> stops = null; 2299 2300 final boolean nowVisible = allResumedActivitiesVisible(); 2301 for (int i=0; i<N; i++) { 2302 ActivityRecord s = mStoppingActivities.get(i); 2303 if (localLOGV) Slog.v(TAG, "Stopping " + s + ": nowVisible=" 2304 + nowVisible + " waitingVisible=" + s.waitingVisible 2305 + " finishing=" + s.finishing); 2306 if (s.waitingVisible && nowVisible) { 2307 mWaitingVisibleActivities.remove(s); 2308 s.waitingVisible = false; 2309 if (s.finishing) { 2310 // If this activity is finishing, it is sitting on top of 2311 // everyone else but we now know it is no longer needed... 2312 // so get rid of it. Otherwise, we need to go through the 2313 // normal flow and hide it once we determine that it is 2314 // hidden by the activities in front of it. 2315 if (localLOGV) Slog.v(TAG, "Before stopping, can hide: " + s); 2316 mWindowManager.setAppVisibility(s.appToken, false); 2317 } 2318 } 2319 if ((!s.waitingVisible || mService.isSleepingOrShuttingDown()) && remove) { 2320 if (localLOGV) Slog.v(TAG, "Ready to stop: " + s); 2321 if (stops == null) { 2322 stops = new ArrayList<ActivityRecord>(); 2323 } 2324 stops.add(s); 2325 mStoppingActivities.remove(i); 2326 N--; 2327 i--; 2328 } 2329 } 2330 2331 return stops; 2332 } 2333 2334 void validateTopActivitiesLocked() { 2335 for (int stackNdx = mStacks.size() - 1; stackNdx >= 0; --stackNdx) { 2336 final ActivityStack stack = mStacks.get(stackNdx); 2337 final ActivityRecord r = stack.topRunningActivityLocked(null); 2338 final ActivityState state = r == null ? ActivityState.DESTROYED : r.state; 2339 if (isFrontStack(stack)) { 2340 if (r == null) { 2341 Slog.e(TAG, "validateTop...: null top activity, stack=" + stack); 2342 } else { 2343 final ActivityRecord pausing = stack.mPausingActivity; 2344 if (pausing != null && pausing == r) { 2345 Slog.e(TAG, "validateTop...: top stack has pausing activity r=" + r + 2346 " state=" + state); 2347 } 2348 if (state != ActivityState.INITIALIZING && state != ActivityState.RESUMED) { 2349 Slog.e(TAG, "validateTop...: activity in front not resumed r=" + r + 2350 " state=" + state); 2351 } 2352 } 2353 } else { 2354 final ActivityRecord resumed = stack.mResumedActivity; 2355 if (resumed != null && resumed == r) { 2356 Slog.e(TAG, "validateTop...: back stack has resumed activity r=" + r + 2357 " state=" + state); 2358 } 2359 if (r != null && (state == ActivityState.INITIALIZING 2360 || state == ActivityState.RESUMED)) { 2361 Slog.e(TAG, "validateTop...: activity in back resumed r=" + r + 2362 " state=" + state); 2363 } 2364 } 2365 } 2366 } 2367 2368 private static String stackStateToString(int stackState) { 2369 switch (stackState) { 2370 case STACK_STATE_HOME_IN_FRONT: return "STACK_STATE_HOME_IN_FRONT"; 2371 case STACK_STATE_HOME_TO_BACK: return "STACK_STATE_HOME_TO_BACK"; 2372 case STACK_STATE_HOME_IN_BACK: return "STACK_STATE_HOME_IN_BACK"; 2373 case STACK_STATE_HOME_TO_FRONT: return "STACK_STATE_HOME_TO_FRONT"; 2374 default: return "Unknown stackState=" + stackState; 2375 } 2376 } 2377 2378 public void dump(PrintWriter pw, String prefix) { 2379 pw.print(prefix); pw.print("mDismissKeyguardOnNextActivity="); 2380 pw.println(mDismissKeyguardOnNextActivity); 2381 pw.print(prefix); pw.print("mFocusedStack=" + mFocusedStack); 2382 pw.print(" mStackState="); pw.println(stackStateToString(mStackState)); 2383 pw.print(prefix); pw.println("mSleepTimeout=" + mSleepTimeout); 2384 pw.print(prefix); pw.println("mCurTaskId=" + mCurTaskId); 2385 pw.print(prefix); pw.println("mUserStackInFront=" + mUserStackInFront); 2386 } 2387 2388 ArrayList<ActivityRecord> getDumpActivitiesLocked(String name) { 2389 return getFocusedStack().getDumpActivitiesLocked(name); 2390 } 2391 2392 static boolean printThisActivity(PrintWriter pw, ActivityRecord activity, String dumpPackage, 2393 boolean needSep, String prefix) { 2394 if (activity != null) { 2395 if (dumpPackage == null || dumpPackage.equals(activity.packageName)) { 2396 if (needSep) { 2397 pw.println(); 2398 } 2399 pw.print(prefix); 2400 pw.println(activity); 2401 return true; 2402 } 2403 } 2404 return false; 2405 } 2406 2407 boolean dumpActivitiesLocked(FileDescriptor fd, PrintWriter pw, boolean dumpAll, 2408 boolean dumpClient, String dumpPackage) { 2409 boolean printed = false; 2410 boolean needSep = false; 2411 final int numStacks = mStacks.size(); 2412 for (int stackNdx = 0; stackNdx < numStacks; ++stackNdx) { 2413 final ActivityStack stack = mStacks.get(stackNdx); 2414 StringBuilder stackHeader = new StringBuilder(128); 2415 stackHeader.append(" Stack #"); 2416 stackHeader.append(mStacks.indexOf(stack)); 2417 stackHeader.append(":"); 2418 printed |= stack.dumpActivitiesLocked(fd, pw, dumpAll, dumpClient, dumpPackage, needSep, 2419 stackHeader.toString()); 2420 printed |= dumpHistoryList(fd, pw, stack.mLRUActivities, " ", "Run", false, !dumpAll, 2421 false, dumpPackage, true, " Running activities (most recent first):", null); 2422 2423 needSep = printed; 2424 boolean pr = printThisActivity(pw, stack.mPausingActivity, dumpPackage, needSep, 2425 " mPausingActivity: "); 2426 if (pr) { 2427 printed = true; 2428 needSep = false; 2429 } 2430 pr = printThisActivity(pw, stack.mResumedActivity, dumpPackage, needSep, 2431 " mResumedActivity: "); 2432 if (pr) { 2433 printed = true; 2434 needSep = false; 2435 } 2436 if (dumpAll) { 2437 pr = printThisActivity(pw, stack.mLastPausedActivity, dumpPackage, needSep, 2438 " mLastPausedActivity: "); 2439 if (pr) { 2440 printed = true; 2441 needSep = true; 2442 } 2443 printed |= printThisActivity(pw, stack.mLastNoHistoryActivity, dumpPackage, 2444 needSep, " mLastNoHistoryActivity: "); 2445 } 2446 needSep = printed; 2447 } 2448 2449 printed |= dumpHistoryList(fd, pw, mFinishingActivities, " ", "Fin", false, !dumpAll, 2450 false, dumpPackage, true, " Activities waiting to finish:", null); 2451 printed |= dumpHistoryList(fd, pw, mStoppingActivities, " ", "Stop", false, !dumpAll, 2452 false, dumpPackage, true, " Activities waiting to stop:", null); 2453 printed |= dumpHistoryList(fd, pw, mWaitingVisibleActivities, " ", "Wait", false, !dumpAll, 2454 false, dumpPackage, true, " Activities waiting for another to become visible:", 2455 null); 2456 printed |= dumpHistoryList(fd, pw, mGoingToSleepActivities, " ", "Sleep", false, !dumpAll, 2457 false, dumpPackage, true, " Activities waiting to sleep:", null); 2458 printed |= dumpHistoryList(fd, pw, mGoingToSleepActivities, " ", "Sleep", false, !dumpAll, 2459 false, dumpPackage, true, " Activities waiting to sleep:", null); 2460 2461 return printed; 2462 } 2463 2464 static boolean dumpHistoryList(FileDescriptor fd, PrintWriter pw, List<ActivityRecord> list, 2465 String prefix, String label, boolean complete, boolean brief, boolean client, 2466 String dumpPackage, boolean needNL, String header1, String header2) { 2467 TaskRecord lastTask = null; 2468 String innerPrefix = null; 2469 String[] args = null; 2470 boolean printed = false; 2471 for (int i=list.size()-1; i>=0; i--) { 2472 final ActivityRecord r = list.get(i); 2473 if (dumpPackage != null && !dumpPackage.equals(r.packageName)) { 2474 continue; 2475 } 2476 if (innerPrefix == null) { 2477 innerPrefix = prefix + " "; 2478 args = new String[0]; 2479 } 2480 printed = true; 2481 final boolean full = !brief && (complete || !r.isInHistory()); 2482 if (needNL) { 2483 pw.println(""); 2484 needNL = false; 2485 } 2486 if (header1 != null) { 2487 pw.println(header1); 2488 header1 = null; 2489 } 2490 if (header2 != null) { 2491 pw.println(header2); 2492 header2 = null; 2493 } 2494 if (lastTask != r.task) { 2495 lastTask = r.task; 2496 pw.print(prefix); 2497 pw.print(full ? "* " : " "); 2498 pw.println(lastTask); 2499 if (full) { 2500 lastTask.dump(pw, prefix + " "); 2501 } else if (complete) { 2502 // Complete + brief == give a summary. Isn't that obvious?!? 2503 if (lastTask.intent != null) { 2504 pw.print(prefix); pw.print(" "); 2505 pw.println(lastTask.intent.toInsecureStringWithClip()); 2506 } 2507 } 2508 } 2509 pw.print(prefix); pw.print(full ? " * " : " "); pw.print(label); 2510 pw.print(" #"); pw.print(i); pw.print(": "); 2511 pw.println(r); 2512 if (full) { 2513 r.dump(pw, innerPrefix); 2514 } else if (complete) { 2515 // Complete + brief == give a summary. Isn't that obvious?!? 2516 pw.print(innerPrefix); pw.println(r.intent.toInsecureString()); 2517 if (r.app != null) { 2518 pw.print(innerPrefix); pw.println(r.app); 2519 } 2520 } 2521 if (client && r.app != null && r.app.thread != null) { 2522 // flush anything that is already in the PrintWriter since the thread is going 2523 // to write to the file descriptor directly 2524 pw.flush(); 2525 try { 2526 TransferPipe tp = new TransferPipe(); 2527 try { 2528 r.app.thread.dumpActivity(tp.getWriteFd().getFileDescriptor(), 2529 r.appToken, innerPrefix, args); 2530 // Short timeout, since blocking here can 2531 // deadlock with the application. 2532 tp.go(fd, 2000); 2533 } finally { 2534 tp.kill(); 2535 } 2536 } catch (IOException e) { 2537 pw.println(innerPrefix + "Failure while dumping the activity: " + e); 2538 } catch (RemoteException e) { 2539 pw.println(innerPrefix + "Got a RemoteException while dumping the activity"); 2540 } 2541 needNL = true; 2542 } 2543 } 2544 return printed; 2545 } 2546 2547 void scheduleIdleTimeoutLocked(ActivityRecord next) { 2548 if (DEBUG_IDLE) Slog.d(TAG, "scheduleIdleTimeoutLocked: Callers=" + Debug.getCallers(4)); 2549 Message msg = mHandler.obtainMessage(IDLE_TIMEOUT_MSG, next); 2550 mHandler.sendMessageDelayed(msg, IDLE_TIMEOUT); 2551 } 2552 2553 final void scheduleIdleLocked() { 2554 mHandler.sendEmptyMessage(IDLE_NOW_MSG); 2555 } 2556 2557 void removeTimeoutsForActivityLocked(ActivityRecord r) { 2558 if (DEBUG_IDLE) Slog.d(TAG, "removeTimeoutsForActivity: Callers=" + Debug.getCallers(4)); 2559 mHandler.removeMessages(IDLE_TIMEOUT_MSG, r); 2560 } 2561 2562 final void scheduleResumeTopActivities() { 2563 mHandler.sendEmptyMessage(RESUME_TOP_ACTIVITY_MSG); 2564 } 2565 2566 void removeSleepTimeouts() { 2567 mSleepTimeout = false; 2568 mHandler.removeMessages(SLEEP_TIMEOUT_MSG); 2569 } 2570 2571 final void scheduleSleepTimeout() { 2572 removeSleepTimeouts(); 2573 mHandler.sendEmptyMessageDelayed(SLEEP_TIMEOUT_MSG, SLEEP_TIMEOUT); 2574 } 2575 2576 private final class ActivityStackSupervisorHandler extends Handler { 2577 2578 public ActivityStackSupervisorHandler(Looper looper) { 2579 super(looper); 2580 } 2581 2582 void activityIdleInternal(ActivityRecord r) { 2583 synchronized (mService) { 2584 activityIdleInternalLocked(r != null ? r.appToken : null, true, null); 2585 } 2586 } 2587 2588 @Override 2589 public void handleMessage(Message msg) { 2590 switch (msg.what) { 2591 case IDLE_TIMEOUT_MSG: { 2592 if (DEBUG_IDLE) Slog.d(TAG, "handleMessage: IDLE_TIMEOUT_MSG: r=" + msg.obj); 2593 if (mService.mDidDexOpt) { 2594 mService.mDidDexOpt = false; 2595 Message nmsg = mHandler.obtainMessage(IDLE_TIMEOUT_MSG); 2596 nmsg.obj = msg.obj; 2597 mHandler.sendMessageDelayed(nmsg, IDLE_TIMEOUT); 2598 return; 2599 } 2600 // We don't at this point know if the activity is fullscreen, 2601 // so we need to be conservative and assume it isn't. 2602 activityIdleInternal((ActivityRecord)msg.obj); 2603 } break; 2604 case IDLE_NOW_MSG: { 2605 if (DEBUG_IDLE) Slog.d(TAG, "handleMessage: IDLE_NOW_MSG: r=" + msg.obj); 2606 activityIdleInternal((ActivityRecord)msg.obj); 2607 } break; 2608 case RESUME_TOP_ACTIVITY_MSG: { 2609 synchronized (mService) { 2610 resumeTopActivitiesLocked(); 2611 } 2612 } break; 2613 case SLEEP_TIMEOUT_MSG: { 2614 synchronized (mService) { 2615 if (mService.isSleepingOrShuttingDown()) { 2616 Slog.w(TAG, "Sleep timeout! Sleeping now."); 2617 mSleepTimeout = true; 2618 checkReadyForSleepLocked(); 2619 } 2620 } 2621 } break; 2622 case LAUNCH_TIMEOUT_MSG: { 2623 if (mService.mDidDexOpt) { 2624 mService.mDidDexOpt = false; 2625 mHandler.sendEmptyMessageDelayed(LAUNCH_TIMEOUT_MSG, LAUNCH_TIMEOUT); 2626 return; 2627 } 2628 synchronized (mService) { 2629 if (mLaunchingActivity.isHeld()) { 2630 Slog.w(TAG, "Launch timeout has expired, giving up wake lock!"); 2631 if (VALIDATE_WAKE_LOCK_CALLER 2632 && Binder.getCallingUid() != Process.myUid()) { 2633 throw new IllegalStateException("Calling must be system uid"); 2634 } 2635 mLaunchingActivity.release(); 2636 } 2637 } 2638 } break; 2639 } 2640 } 2641 } 2642} 2643