privatestaticfinal Singleton<IActivityManager> IActivityManagerSingleton = new Singleton<IActivityManager>() { @Override protected IActivityManager create(){ final IBinder b = ServiceManager.getService(Context.ACTIVITY_SERVICE); final IActivityManager am = IActivityManager.Stub.asInterface(b); return am; } };
// Save a copy in case ephemeral needs it final Intent ephemeralIntent = new Intent(intent); // Don't modify the client's object! intent = new Intent(intent);
ResolveInfo rInfo = mSupervisor.resolveIntent(intent, resolvedType, userId, 0/* matchFlags */, computeResolveFilterUid( callingUid, realCallingUid, mRequest.filterCallingUid)); if (rInfo == null) { rInfo = mSupervisor.resolveIntent(intent, resolvedType, userId, PackageManager.MATCH_DIRECT_BOOT_AWARE | PackageManager.MATCH_DIRECT_BOOT_UNAWARE, computeResolveFilterUid( callingUid, realCallingUid, mRequest.filterCallingUid)); } // Collect information about the target of the Intent. ActivityInfo aInfo = mSupervisor.resolveActivity(intent, rInfo, startFlags, profilerInfo);
synchronized (mService) { final ActivityStack stack = mSupervisor.mFocusedStack;
final ActivityRecord r = mFocusedStack.topRunningActivityLocked(); if (r == null || !r.isState(RESUMED)) { mFocusedStack.resumeTopActivityUncheckedLocked(null, null); } elseif (r.isState(RESUMED)) { // Kick off any lingering app transitions form the MoveTaskToFront operation. mFocusedStack.executeAppTransition(targetOptions); }
case EXECUTE_TRANSACTION: final ClientTransaction transaction = (ClientTransaction) msg.obj; mTransactionExecutor.execute(transaction); if (isSystem()) { // Client transactions inside system process are recycled on the client side // instead of ClientLifecycleManager to avoid being cleared before this // message is handled. transaction.recycle(); } break;
privatevoidexecuteLifecycleState(ClientTransaction transaction){ final ActivityLifecycleItem lifecycleItem = transaction.getLifecycleStateRequest(); if (lifecycleItem == null) { return; }
final IBinder token = transaction.getActivityToken(); final ActivityClientRecord r = mTransactionHandler.getActivityClient(token);
if (r == null) { return; }
// Cycle to the state right before the final requested state. cycleToPath(r, lifecycleItem.getTargetState(), true/* excludeLastState */);
// Execute the final transition with proper parameters. lifecycleItem.execute(mTransactionHandler, token, mPendingActions); lifecycleItem.postExecute(mTransactionHandler, token, mPendingActions); }
finalvoiddeliverNewIntentLocked(int callingUid, Intent intent, String referrer){ // The activity now gets access to the data associated with this Intent. service.grantUriPermissionFromIntentLocked(callingUid, packageName, intent, getUriPermissionsLocked(), userId); final ReferrerIntent rintent = new ReferrerIntent(intent, referrer); boolean unsent = true; finalboolean isTopActivityWhileSleeping = isTopRunningActivity() && isSleeping();
// We want to immediately deliver the intent to the activity if: // - It is currently resumed or paused. i.e. it is currently visible to the user and we want // the user to see the visual effects caused by the intent delivery now. // - The device is sleeping and it is the top activity behind the lock screen (b/6700897). if ((mState == RESUMED || mState == PAUSED || isTopActivityWhileSleeping) && app != null && app.thread != null) { try { ArrayList<ReferrerIntent> ar = new ArrayList<>(1); ar.add(rintent); // void scheduleTransaction(IApplicationThread client, IBinder activityToken, ClientTransactionItem callback) service.getLifecycleManager().scheduleTransaction(app.thread, appToken, NewIntentItem.obtain(ar, mState == PAUSED)); unsent = false; } catch (RemoteException e) { Slog.w(TAG, "Exception thrown sending new intent to " + this, e); } catch (NullPointerException e) { Slog.w(TAG, "Exception thrown sending new intent to " + this, e); } } if (unsent) { addNewIntentLocked(rintent); } }
voidstartSpecificActivityLocked(ActivityRecord r, boolean andResume, boolean checkConfig){ // Is this activity's application already running? ProcessRecord app = mService.getProcessRecordLocked(r.processName, r.info.applicationInfo.uid, true);
getLaunchTimeTracker().setLaunchTime(r);
if (app != null && app.thread != null) { try { if ((r.info.flags&ActivityInfo.FLAG_MULTIPROCESS) == 0 || !"android".equals(r.info.packageName)) { // Don't add this if it is a platform component that is marked // to run in multiple processes, because this is actually // part of the framework so doesn't make sense to track as a // separate apk in the process. app.addPackage(r.info.packageName, r.info.applicationInfo.longVersionCode, mService.mProcessStats); } // 真正的启动Activity realStartActivityLocked(r, app, andResume, checkConfig); return; } catch (RemoteException e) { } // If a dead object exception was thrown -- fall through to // restart the application. } // 进程不存在时创建进程 // final ActivityManagerService mService; mService.startProcessLocked(r.processName, r.info.applicationInfo, true, 0, "activity", r.intent.getComponent(), false, false, true); }
int idx = app.activities.indexOf(r); if (idx < 0) { app.activities.add(r); } try { List<ResultInfo> results = null; List<ReferrerIntent> newIntents = null; if (andResume) { // We don't need to deliver new intents and/or set results if activity is going // to pause immediately after launch. results = r.results; newIntents = r.newIntents; } if (r.isActivityTypeHome()) { // Home process is the root process of the task. mService.mHomeProcess = task.mActivities.get(0).app; }
// Create activity launch transaction. final ClientTransaction clientTransaction = ClientTransaction.obtain(app.thread, r.appToken); clientTransaction.addCallback(LaunchActivityItem.obtain(new Intent(r.intent), System.identityHashCode(r), r.info, // TODO: Have this take the merged configuration instead of separate global // and override configs. mergedConfiguration.getGlobalConfiguration(), mergedConfiguration.getOverrideConfiguration(), r.compat, r.launchedFromPackage, task.voiceInteractor, app.repProcState, r.icicle, r.persistentState, results, newIntents, mService.isNextTransitionForward(), profilerInfo));
// Set desired final state. final ActivityLifecycleItem lifecycleItem; if (andResume) { lifecycleItem = ResumeActivityItem.obtain(mService.isNextTransitionForward()); } else { lifecycleItem = PauseActivityItem.obtain(); } clientTransaction.setLifecycleStateRequest(lifecycleItem);
} catch (RemoteException e) { if (r.launchFailed) { // This is the second time we failed -- finish activity // and give up. mService.appDiedLocked(app); stack.requestFinishActivityLocked(r.appToken, Activity.RESULT_CANCELED, null, "2nd-crash", false); returnfalse; }
// This is the first time we failed -- restart process and // retry. r.launchFailed = true; app.activities.remove(r); throw e; } } finally { endDeferResume(); }
public Activity handleLaunchActivity(ActivityClientRecord r, PendingTransactionActions pendingActions, Intent customIntent){ // ... final Activity a = performLaunchActivity(r, customIntent);
if (a != null) { } else { // If there was an error, for any reason, tell the activity manager to stop us. try { ActivityManager.getService().finishActivity(r.token, Activity.RESULT_CANCELED, null, Activity.DONT_FINISH_TASK_WITH_ACTIVITY); } catch (RemoteException ex) { throw ex.rethrowFromSystemServer(); } }
final DisplayManagerGlobal dm = DisplayManagerGlobal.getInstance(); // For debugging purposes, if the activity's package name contains the value of // the "debug.use-second-display" system property as a substring, then show // its content on a secondary display if there is one. String pkgName = SystemProperties.get("debug.second-display.pkg"); if (pkgName != null && !pkgName.isEmpty() && r.packageInfo.mPackageName.contains(pkgName)) { for (int id : dm.getDisplayIds()) { if (id != Display.DEFAULT_DISPLAY) { Display display = dm.getCompatibleDisplay(id, appContext.getResources()); appContext = (ContextImpl) appContext.createDisplayContext(display); break; } } } return appContext; }
// Clamp display ID to DEFAULT_DISPLAY if it is INVALID_DISPLAY. displayId = (displayId != Display.INVALID_DISPLAY) ? displayId : Display.DEFAULT_DISPLAY;
final ResourcesManager resourcesManager = ResourcesManager.getInstance();
// Create the base resources for which all configuration contexts for this Activity // will be rebased upon. context.setResources(resourcesManager.createBaseActivityResources(activityToken, packageInfo.getResDir(), splitDirs, packageInfo.getOverlayDirs(), packageInfo.getApplicationInfo().sharedLibraryFiles, displayId, overrideConfiguration, compatInfo, classLoader)); context.mDisplay = resourcesManager.getAdjustedDisplay(displayId, context.getResources()); return context; }
if (mAutoFillResetNeeded) { // When Activity is destroyed in paused state, and relaunch activity, there will be // extra onResume and onPause event, ignore the first onResume and onPause. // see ActivityThread.handleRelaunchActivity() mAutoFillIgnoreFirstResumePause = followedByPause; if (mAutoFillIgnoreFirstResumePause && DEBUG_LIFECYCLE) { Slog.v(TAG, "autofill will ignore first pause when relaunching " + this); } }
mCalled = false; // mResumed is set by the instrumentation mInstrumentation.callActivityOnResume(this); if (!mCalled) { thrownew SuperNotCalledException( "Activity " + mComponent.toShortString() + " did not call through to super.onResume()"); }
// invisible activities must be finished before onResume() completes if (!mVisibleFromClient && !mFinished) { Log.w(TAG, "An activity without a UI must call finish() before onResume() completes"); if (getApplicationInfo().targetSdkVersion > android.os.Build.VERSION_CODES.LOLLIPOP_MR1) { thrownew IllegalStateException( "Activity " + mComponent.toShortString() + " did not call finish() prior to onResume() completing"); } }
// Now really resume, and install the current status bar and menu. mCalled = false;
onPostResume(); if (!mCalled) { thrownew SuperNotCalledException( "Activity " + mComponent.toShortString() + " did not call through to super.onPostResume()"); } }
protectedvoidonPostResume(){ final Window win = getWindow(); if (win != null) win.makeActive(); if (mActionBar != null) mActionBar.setShowHideAnimationEnabled(true); mCalled = true; }
if (mToken != null && mParent == null) { // No need to check mStopped, the roots will check if they were actually stopped. WindowManagerGlobal.getInstance().setStoppedState(mToken, false/* stopped */); }
if (mStopped) { mStopped = false;
synchronized (mManagedCursors) { finalint N = mManagedCursors.size(); for (int i=0; i<N; i++) { ManagedCursor mc = mManagedCursors.get(i); if (mc.mReleased || mc.mUpdated) { if (!mc.mCursor.requery()) { if (getApplicationInfo().targetSdkVersion >= android.os.Build.VERSION_CODES.ICE_CREAM_SANDWICH) { thrownew IllegalStateException( "trying to requery an already closed cursor " + mc.mCursor); } } mc.mReleased = false; mc.mUpdated = false; } } }
mCalled = false; mInstrumentation.callActivityOnRestart(this); writeEventLog(LOG_AM_ON_RESTART_CALLED, reason); if (!mCalled) { thrownew SuperNotCalledException( "Activity " + mComponent.toShortString() + " did not call through to super.onRestart()"); } if (start) { performStart(reason); } } }
if (!mCalled) { thrownew SuperNotCalledException( "Activity " + mComponent.toShortString() + " did not call through to super.onStart()"); } mFragments.dispatchStart(); mFragments.reportLoaderStart();
// This property is set for all non-user builds except final release boolean isDlwarningEnabled = SystemProperties.getInt("ro.bionic.ld.warning", 0) == 1;
if (isAppDebuggable || isDlwarningEnabled) { String dlwarning = getDlWarning(); if (dlwarning != null) { String appName = getApplicationInfo().loadLabel(getPackageManager()) .toString(); String warning = "Detected problems with app native libraries\n" + "(please consult log for detail):\n" + dlwarning; if (isAppDebuggable) { new AlertDialog.Builder(this). setTitle(appName). setMessage(warning). setPositiveButton(android.R.string.ok, null). setCancelable(false). show(); } else { Toast.makeText(this, appName + "\n" + warning, Toast.LENGTH_LONG).show(); } } }
// This property is set for all non-user builds except final release boolean isApiWarningEnabled = SystemProperties.getInt("ro.art.hiddenapi.warning", 0) == 1;
if (isAppDebuggable || isApiWarningEnabled) { if (!mMainThread.mHiddenApiWarningShown && VMRuntime.getRuntime().hasUsedHiddenApi()) { // Only show the warning once per process. mMainThread.mHiddenApiWarningShown = true;
String appName = getApplicationInfo().loadLabel(getPackageManager()) .toString(); String warning = "Detected problems with API compatibility\n" + "(visit g.co/dev/appcompat for more info)"; if (isAppDebuggable) { new AlertDialog.Builder(this) .setTitle(appName) .setMessage(warning) .setPositiveButton(android.R.string.ok, null) .setCancelable(false) .show(); } else { Toast.makeText(this, appName + "\n" + warning, Toast.LENGTH_LONG).show(); } } }
mActivityTransitionState.enterReady(this); }
在ReStart/Start后,再开始Resume:
1 2 3 4 5 6 7 8 9 10 11 12 13 14
publicvoidcallActivityOnResume(Activity activity){ activity.mResumed = true; activity.onResume(); if (mActivityMonitors != null) { synchronized (mSync) { finalint N = mActivityMonitors.size(); for (int i=0; i<N; i++) { final ActivityMonitor am = mActivityMonitors.get(i); am.match(activity, activity, activity.getIntent()); } } } }
private Bundle performPauseActivity(ActivityClientRecord r, boolean finished, String reason, PendingTransactionActions pendingActions){ if (r.paused) { if (r.activity.mFinished) { // If we are finishing, we won't call onResume() in certain cases. // So here we likewise don't want to call onPause() if the activity // isn't resumed. returnnull; } RuntimeException e = new RuntimeException( "Performing pause of activity that is not resumed: " + r.intent.getComponent().toShortString()); } if (finished) { r.activity.mFinished = true; }
// Pre-Honeycomb apps always save their state before pausing finalboolean shouldSaveState = !r.activity.mFinished && r.isPreHoneycomb(); if (shouldSaveState) { // OnSaveInstanceState callActivityOnSaveInstanceState(r); }
performPauseActivityIfNeeded(r, reason);
// Notify any outstanding on paused listeners ArrayList<OnActivityPausedListener> listeners; synchronized (mOnPauseListeners) { listeners = mOnPauseListeners.remove(r.activity); } int size = (listeners != null ? listeners.size() : 0); for (int i = 0; i < size; i++) { listeners.get(i).onPaused(r.activity); }
final Bundle oldState = pendingActions != null ? pendingActions.getOldState() : null; if (oldState != null) { if (r.isPreHoneycomb()) { r.state = oldState; } }
return shouldSaveState ? r.state : null; }
privatevoidperformPauseActivityIfNeeded(ActivityClientRecord r, String reason){ if (r.paused) { // You are already paused silly... return; }
try { r.activity.mCalled = false; mInstrumentation.callActivityOnPause(r.activity); if (!r.activity.mCalled) { thrownew SuperNotCalledException("Activity " + safeToComponentShortString(r.intent) + " did not call through to super.onPause()"); } } catch (SuperNotCalledException e) { throw e; } catch (Exception e) { if (!mInstrumentation.onException(r.activity, e)) { thrownew RuntimeException("Unable to pause activity " + safeToComponentShortString(r.intent) + ": " + e.toString(), e); } } r.setState(ON_PAUSE); }