Android源碼版本9.0
應(yīng)用程序的啟動
從手機屏幕點擊APP圖標(biāo)起熟嫩,APP的啟動就已經(jīng)開始了
首先:
執(zhí)行java首次啟動都要執(zhí)行的main方法開始
Android main方法存在于ActivityThread中,也就是說啟動應(yīng)用都要從ActivityThread的main方法開始
##ActivityThread
public static void main(String[] args) {
...
Looper.prepareMainLooper(); //1
long startSeq = 0;
if (args != null) {
for (int i = args.length - 1; i >= 0; --i) {
if (args[i] != null && args[i].startsWith(PROC_START_SEQ_IDENT)) {
startSeq = Long.parseLong(
args[i].substring(PROC_START_SEQ_IDENT.length()));
}
}
}
ActivityThread thread = new ActivityThread(); //2
thread.attach(false, startSeq); //3
...
Looper.loop();
throw new RuntimeException("Main thread loop unexpectedly exited");
}
說一下幾個比較重要的方法 ->
- 注釋1 -> Looper.prepareMainLooper() -> 用于應(yīng)用啟動創(chuàng)建進程唯一的UI線程
- 注釋2 -> 把ActivityThread創(chuàng)建出來并調(diào)用attach連接
- 注釋3 -> 啟動Looper的消息隊列
接下來看一下具體連接了什么
##ActivityThread
private void attach(boolean system, long startSeq) {
...
if (!system) {
...
final IActivityManager mgr = ActivityManager.getService(); //1
try {
mgr.attachApplication(mAppThread, startSeq); //2
} catch (RemoteException ex) {
throw ex.rethrowFromSystemServer();
}
...
} else {
...
}
...
}
- 注釋1 -> 通過ActivityManager獲取IActivityManager机错,這個是系統(tǒng)的本地代理對象爬范,作用是應(yīng)用進程請求系統(tǒng)進程接口,為了實現(xiàn)進程間通信弱匪,這里用到的是AIDL青瀑。具體用法不再此處說明,只需要知道這能夠?qū)崿F(xiàn)進程間交互萧诫。
- 注釋2 -> 調(diào)用attachApplication方法斥难,調(diào)用系統(tǒng)進程接口,用于連接Application
IActivityManager具體執(zhí)行方法是在ActivityManagerService帘饶,這里讓Application去和AMS連接是為了APP和系統(tǒng)綁定哑诊,更好的方便管理當(dāng)前APP。
##ActivityManagerService
public final void attachApplication(IApplicationThread thread, long startSeq) {
synchronized (this) {
//獲取pid
int callingPid = Binder.getCallingPid(); //1
//獲取uid
final int callingUid = Binder.getCallingUid(); //2
final long origId = Binder.clearCallingIdentity();
//連接Application
attachApplicationLocked(thread, callingPid, callingUid, startSeq); //3
Binder.restoreCallingIdentity(origId);
}
}
attachApplication是AMS中的一個方法及刻。
- 注釋1和2 -> 分別獲取到pid和uid(由系統(tǒng)創(chuàng)建搭儒,并分配穷当,并且是處以沒有進程使用)。
- 注釋3 -> 可以看到pid和uid傳入到了attachApplicationLocked這個方法中淹禾。
##ActivityManagerService
private final boolean attachApplicationLocked(IApplicationThread thread,
int pid, int callingUid, long startSeq) {
ProcessRecord app; //1
long startTime = SystemClock.uptimeMillis();
if (pid != MY_PID && pid >= 0) {
synchronized (mPidsSelfLocked) {
app = mPidsSelfLocked.get(pid); //2
}
}
...
if (app.instr != null) { //當(dāng)前進程是否正在活動
thread.bindApplication(processName, appInfo, providers, app.instr.mClass,
profilerInfo, app.instr.mArguments, app.instr.mWatcher, app.instr.mUiAutomationConnection,
testMode, mBinderTransactionTrackingEnabled, enableTrackAllocation,
isRestrictedBackupMode || !normalMode, app.persistent, new Configuration(getGlobalConfiguration()),
app.compat, getCommonServicesLocked(app.isolated), mCoreSettingsObserver.getCoreSettingsLocked(),
buildSerial, isAutofillCompatEnabled); //3
} else {
//Application 綁定到當(dāng)前線程
thread.bindApplication(processName, appInfo, providers, null, profilerInfo,
null, null, null, testMode, mBinderTransactionTrackingEnabled,
enableTrackAllocation, isRestrictedBackupMode || !normalMode, app.persistent,
new Configuration(getGlobalConfiguration()), app.compat, getCommonServicesLocked(app.isolated),
mCoreSettingsObserver.getCoreSettingsLocked(), buildSerial, isAutofillCompatEnabled); //4
}
...
//檢測最可見的Activity是否在運行進程中等待,如果再則創(chuàng)建Activity
if (mStackSupervisor.attachApplicationLocked(app)) { //5
didSomething = true;
}
...
}
- 注釋1 -> rocessRecord是個進程記錄類茴扁,可以看作是一個javabean铃岔,用來保存當(dāng)前進程先關(guān)的一些信息(如pid、uip峭火、ApplicationInfo等)
- 注釋2 -> 根據(jù)pid獲取到了這個類,其實也就是獲得當(dāng)前進程的相關(guān)屬性毁习。
- 注釋3、注釋4 -> 綁定Application到當(dāng)前進程卖丸,thread也就是IApplicationThread纺且,它是一個AIDL的接口,作用是系統(tǒng)進程請求應(yīng)用進程的接口稍浆。實現(xiàn)類是ActivityThread中的內(nèi)部類ApplicationThread载碌。
- 注釋5 -> 開始創(chuàng)建Activity
總結(jié):App的啟動從應(yīng)用圖標(biāo)被點擊開始,首先執(zhí)行的是ActivityThread中的main方法衅枫。
1嫁艇、創(chuàng)建出進程唯一的UI線程,并啟動它的消息隊列弦撩。
2步咪、獲取IActivityManager也就是ActivityManagerService請求系統(tǒng)進程接口,通過AIDL實現(xiàn)進程間通信益楼,作用是APP連接系統(tǒng)進程猾漫,方便管理當(dāng)前APP。這樣就完成了系統(tǒng)和應(yīng)用進程的綁定感凤。
綁定Application
##ActivityThread.ApplicationThread
public final void bindApplication(String processName...boolean autofillCompatibilityEnabled) {
...
setCoreSettings(coreSettings);
AppBindData data = new AppBindData();
data.processName = processName; //當(dāng)前進程名字
data.appInfo = appInfo; //app信息
data.providers = providers; //providers
...
//最后使用Handler發(fā)送消息悯周,并攜帶AppBindData數(shù)據(jù)
sendMessage(H.BIND_APPLICATION, data);
}
在bindApplication中,會把傳入的一系列參數(shù)封裝成一個AppBindData對象俊扭,然后通過Handler把這個對象發(fā)送出去队橙。H是ActivityThread中的內(nèi)部類,是Handler的子類萨惑。
##ActivityThread.H
public void handleMessage(Message msg) {
if (DEBUG_MESSAGES) Slog.v(TAG, ">>> handling: " + codeToString(msg.what));
switch (msg.what) {
case BIND_APPLICATION:
Trace.traceBegin(Trace.TRACE_TAG_ACTIVITY_MANAGER, "bindApplication");
AppBindData data = (AppBindData) msg.obj;
handleBindApplication(data);
Trace.traceEnd(Trace.TRACE_TAG_ACTIVITY_MANAGER);
break;
...
}
...
}
handleMessage方法是H中的方法捐康,主要是用來處理消息。
##ActivityThread
private void handleBindApplication(AppBindData data) {
...
final ContextImpl appContext = ContextImpl.createAppContext(this, data.info); //1
...
Application app;
...
//創(chuàng)建Application
app = data.info.makeApplication(data.restrictedBackupMode, null); //2
...
//調(diào)用Application中的onCreate方法
mInstrumentation.callApplicationOnCreate(app); //3
...
}
##LoadedApk
public Application makeApplication(boolean forceDefaultAppClass,
Instrumentation instrumentation) {
...
try {
java.lang.ClassLoader cl = getClassLoader();
...
ContextImpl appContext = ContextImpl.createAppContext(mActivityThread, this);
app = mActivityThread.mInstrumentation.newApplication(
cl, appClass, appContext);//2
appContext.setOuterContext(app);
} catch (Exception e) {
if (!mActivityThread.mInstrumentation.onException(app, e)) {
Trace.traceEnd(Trace.TRACE_TAG_ACTIVITY_MANAGER);
throw new RuntimeException(
"Unable to instantiate application " + appClass
+ ": " + e.toString(), e);
}
}
...
}
##Instrumentation
public Application newApplication(ClassLoader cl, String className, Context context)
throws InstantiationException, IllegalAccessException,
ClassNotFoundException {
Application app = getFactory(context.getPackageName())
.instantiateApplication(cl, className);
app.attach(context);//2
return app;
}
public void callApplicationOnCreate(Application app) {
app.onCreate();//3
}
- 注釋1 -> 創(chuàng)建App的上下文環(huán)境,ContextImpl是Context的子類庸蔼,getApplicationContext()中獲取到的Context其實就是ContextImpl解总。
- 注釋2 -> 一路往下調(diào)用,發(fā)現(xiàn)Application是通過類加載器和反射創(chuàng)建的姐仅,并把Context綁定到Application花枫。
- 注釋3 -> Application中的onCreate方法調(diào)用
總結(jié):創(chuàng)建Application步驟
1刻盐、獲取系統(tǒng)分配的pid和uid。
2劳翰、通過IApplicationThread請求當(dāng)前進程敦锌。
3、發(fā)送消息把創(chuàng)建邏輯切換到UI線程中佳簸,如果現(xiàn)在可能是在其他線程的話乙墙。
4、通過類加載器和反射創(chuàng)建Application并綁定一個上下文環(huán)境生均。
5听想、最后執(zhí)行Application中的onCreate方法完成整個Application的創(chuàng)建并初始化。
創(chuàng)建Activity
##ActivityStackSupervisor
boolean attachApplicationLocked(ProcessRecord app) throws RemoteException {
...
if (realStartActivityLocked(activity, app,
top == activity /* andResume */, true /* checkConfig */)) {
didSomething = true;
}
...
}
realStartActivityLocked马胧,真正開始Activity的創(chuàng)建汉买。
##ActivityStackSupervisor
final boolean realStartActivityLocked(ActivityRecord r, ProcessRecord app,
boolean andResume, boolean checkConfig) throws RemoteException {
...
// 創(chuàng)建啟動Activity
final ClientTransaction clientTransaction = ClientTransaction.obtain(app.thread,
r.appToken);
clientTransaction.addCallback(LaunchActivityItem.obtain(new Intent(r.intent),
System.identityHashCode(r), r.info,
mergedConfiguration.getGlobalConfiguration(),
mergedConfiguration.getOverrideConfiguration(), r.compat,
r.launchedFromPackage, task.voiceInteractor, app.repProcState, r.icicle,
r.persistentState, results, newIntents, mService.isNextTransitionForward(),
profilerInfo)); //添加LaunchActivityItem的回調(diào)
// Set desired final state.
final ActivityLifecycleItem lifecycleItem;
if (andResume) {
lifecycleItem = ResumeActivityItem.obtain(mService.isNextTransitionForward());
} else {
lifecycleItem = PauseActivityItem.obtain();
}
clientTransaction.setLifecycleStateRequest(lifecycleItem);
// 通過生命周期管理對象ClientLifecycleManager,來管理Activity的生命周期狀態(tài)
mService.getLifecycleManager().scheduleTransaction(clientTransaction);
...
return true;
}
##ClientLifecycleManager
void scheduleTransaction(ClientTransaction transaction) throws RemoteException {
final IApplicationThread client = transaction.getClient();
//ClientTransaction是個javabean 實現(xiàn)了Parcelable 序列化佩脊。
//schedule()方法內(nèi)部蛙粘,會回調(diào)到ActivityThread.ApplicationThread的scheduleTransaction()方法
transaction.schedule();
if (!(client instanceof Binder)) {
// If client is not an instance of Binder - it's a remote call and at this point it is
// safe to recycle the object. All objects used for local calls will be recycled after
// the transaction is executed on client in ActivityThread.
transaction.recycle();
}
}
##ActivityThread.ApplicationTread
public void scheduleTransaction(ClientTransaction transaction) throws RemoteException {
//ActivityThread.this 指的是父類ClientTransactionHandler
ActivityThread.this.scheduleTransaction(transaction);
}
##ClientTransactionHandler
void scheduleTransaction(ClientTransaction transaction) {
transaction.preExecute(this);
//發(fā)送Handler消息
sendMessage(ActivityThread.H.EXECUTE_TRANSACTION, transaction);
}
執(zhí)行這一系列的方法后,會發(fā)送一條消息邻吞,在ActivithThread中處理组题。
##ActivityThread.H
public void handleMessage(Message msg) {
if (DEBUG_MESSAGES) Slog.v(TAG, ">>> handling: " + codeToString(msg.what));
switch (msg.what) {
...
case EXECUTE_TRANSACTION:
final ClientTransaction transaction = (ClientTransaction) msg.obj;
//開始執(zhí)行
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();
}
// TODO(lifecycler): Recycle locally scheduled transactions.
break;
...
}
...
}
##TransactionExecutor
public void execute(ClientTransaction transaction) {
final IBinder token = transaction.getActivityToken();
log("Start resolving transaction for client: " + mTransactionHandler + ", token: " + token);
executeCallbacks(transaction); //1
executeLifecycleState(transaction); //5
mPendingActions.clear();
log("End resolving transaction");
}
public void executeCallbacks(ClientTransaction transaction) {
final List<ClientTransactionItem> callbacks = transaction.getCallbacks(); //2
...
for (int i = 0; i < size; ++i) {
final ClientTransactionItem item = callbacks.get(i); //3
...
item.execute(mTransactionHandler, token, mPendingActions); //4
...
}
}
##LaunchActivityItem
@Override
public void execute(ClientTransactionHandler client, IBinder token,
PendingTransactionActions pendingActions) {
...
client.handleLaunchActivity(r, pendingActions, null /* customIntent */);//5
...
}
- 注釋1 -> 執(zhí)行回調(diào)。
- 注釋2 -> 獲取到ClientTransaction中的ClientTransactionItem集合抱冷。
- 注釋3 -> 處理回調(diào),這里獲取到的ClientTransactionItem是LaunchActivityItem崔列。
- 注釋4 -> 調(diào)用LaunchActivityItem中的execute方法。
- 注釋5 -> 發(fā)送一個創(chuàng)建Activity的消息旺遮,ClientTransactionHandler其實就是ActivityThread,這是它的子類赵讯。 LaunchActivityItem可以把它理解成隊列中等待創(chuàng)建的Activity實例,說白了就是最終調(diào)用的位置是在ActivityThread的handleLaunchActivity方法中去處理耿眉。
##ActivityThread
public Activity handleLaunchActivity(ActivityClientRecord r,
PendingTransactionActions pendingActions, Intent customIntent) {
...
//開始執(zhí)行Activity的創(chuàng)建
final Activity a = performLaunchActivity(r, customIntent);
...
return a;
}
private Activity performLaunchActivity(ActivityClientRecord r, Intent customIntent) {
ActivityInfo aInfo = r.activityInfo; //1
...
ContextImpl appContext = createBaseContextForActivity(r); //2
Activity activity = null;
try {
java.lang.ClassLoader cl = appContext.getClassLoader(); //3
activity = mInstrumentation.newActivity(cl, component.getClassName(), r.intent); //4
...
} catch (Exception e) {
...
}
...
//調(diào)用Activity的OnCreate()方法
if (r.isPersistable()) {
mInstrumentation.callActivityOnCreate(activity, r.state, r.persistentState); //5
} else {
mInstrumentation.callActivityOnCreate(activity, r.state);
}
...
return activity;
}
##Instrumentation
public void callActivityOnCreate(Activity activity, Bundle icicle) {
prePerformCreate(activity);
activity.performCreate(icicle);
postPerformCreate(activity);
}
##Activity
final void performCreate(Bundle icicle) {
performCreate(icicle, null);
}
final void performCreate(Bundle icicle, PersistableBundle persistentState) {
mCanEnterPictureInPicture = true;
restoreHasCurrentPermissionRequest(icicle);
//onCreate 生命周期方法被調(diào)用
if (persistentState != null) {
onCreate(icicle, persistentState);
} else {
onCreate(icicle);
}
...
}
- 注釋1 -> 獲取Activity的信息边翼。
- 注釋2 -> 獲取Activity的上下文環(huán)境。
- 注釋3 -> 獲取類加載器鸣剪。
- 注釋4 -> 通過類加載器和反射創(chuàng)建出一個Activity组底。
- 注釋5 -> 調(diào)用Activity的onCreate方法。到這里就完成了一個Activity的創(chuàng)建筐骇。
總結(jié):Activity的創(chuàng)建
1债鸡、前期先做好Activity創(chuàng)建前的一系列相關(guān)環(huán)境配置
2、依然是通過ActivityThread的Handler把需要創(chuàng)建Activity的消息發(fā)送過去并把對應(yīng)的申請放入到ClientTransaction隊列當(dāng)中铛纬。
3厌均、最終消息會回到ActivityThread的handleLaunchActivity方法中去處理,在里面完成Activity的創(chuàng)建步驟告唆。
- 獲取Activity的信息
- 獲取Activity的上下文環(huán)境
- 獲取類加載器
- 通過類加載器和反射創(chuàng)建出一個Activity
- 調(diào)用Activity的onCreate方法棺弊。到這里就完成了一個Activity的創(chuàng)建