Android應(yīng)用啟動流程分析

關(guān)鍵類說明

整個啟動流程因為會涉及到多次Binder通信,這里先簡要說明一下幾個類的用途量窘,方便大家理解整個交互流程:

  • ActivityManagerService :AMS是Android中最核心的服務(wù)之一墙牌,主要負(fù)責(zé)系統(tǒng)中四大組件的啟動、切換、調(diào)度及應(yīng)用進(jìn)程的管理和調(diào)度等工作埠况,其職責(zé)與操作系統(tǒng)中的進(jìn)程管理和調(diào)度模塊相類似筷凤,因此它在Android中非常重要昭殉,它本身也是一個Binder的實現(xiàn)類。
  • Instrumentation :顧名思義藐守,它用來監(jiān)控應(yīng)用程序和系統(tǒng)的交互挪丢。
  • ActivityThread :應(yīng)用的入口類,系統(tǒng)通過調(diào)用main函數(shù)卢厂,開啟消息循環(huán)隊列乾蓬。ActivityThread所在線程被稱為應(yīng)用的主線程(UI線程)。
  • ApplicationThread :ApplicationThread提供Binder通訊接口慎恒,AMS則通過代理調(diào)用此App進(jìn)程的本地方法任内。
  • ActivityManagerProxy :AMS服務(wù)在當(dāng)前進(jìn)程的代理類撵渡,負(fù)責(zé)與AMS通信。
  • ApplicationThreadProxy :ApplicationThread在AMS服務(wù)中的代理類死嗦,負(fù)責(zé)與ApplicationThread通信趋距。

流程分析

1、Launcher響應(yīng)用戶點擊越除,通知AMS

Launcher做為應(yīng)用的入口节腐,通過starActicity輾轉(zhuǎn)調(diào)用到Activity:startActivityForResult而后則調(diào)用至Instrumentation:execStartActivity。在Instrumentation:execStartActivity方法中摘盆,這里的 ActivityManagerNative.getDefault 返回ActivityManagerService的遠(yuǎn)程接口翼雀,即 ActivityManagerProxy 接口,通過Binder驅(qū)動程序孩擂, ActivityManagerProxy 與AMS服務(wù)通信锅纺,則實現(xiàn)了跨進(jìn)程到System進(jìn)程。

2肋殴、AMS響應(yīng)Launcher進(jìn)程請求

從上面的流程我們知道囤锉,此時AMS應(yīng)該處理Launcher進(jìn)程發(fā)來的請求,請參看時序圖及源碼护锤,此時我們調(diào)用到ActivityStackSupervisor:startActivityUncheckedLocked方法官地。在這個方法中函數(shù)經(jīng)過intent的標(biāo)志值設(shè)置,通過findTaskLocked函數(shù)來查找存不存這樣的Task烙懦,這里返回的結(jié)果是null驱入,即intentActivity為null,因此氯析,需要創(chuàng)建一個新的Task來啟動這個Activity】鹘希現(xiàn)在處理堆棧頂端的Activity是Launcher,與我們即將要啟動的MainActivity不是同一個Activity掩缓,創(chuàng)建了一個新的Task里面來啟動這個Activity雪情。經(jīng)過棧頂檢測,則需要將Launcher推入Paused狀態(tài)你辣,才可以啟動新的Activity巡通。后續(xù)則調(diào)用至ActivityStack:startPausingLocked,在這個函數(shù)中的prev.app.thread是一個ApplicationThread對象的遠(yuǎn)程接口舍哄,通過調(diào)用這個遠(yuǎn)程接口的schedulePauseActivity來通知Launcher進(jìn)入Paused狀態(tài)宴凉。至此,AMS對Launcher的請求已經(jīng)響應(yīng)表悬,這是我們發(fā)現(xiàn)又通過Binder通信回調(diào)至Launcher進(jìn)程弥锄。

3、Launcher進(jìn)程掛起Launcher,再次通知AMS

這個流程相對會簡單一些籽暇,我們來看Launcher中的ActivityThread温治,這部分Launcher的ActivityThread處理頁面Paused并且再次通過ActivityManagerProxy通知AMS。

4图仓、AMS創(chuàng)建新的進(jìn)程

創(chuàng)建新進(jìn)程的時候罐盔,AMS會保存一個ProcessRecord信息,如果應(yīng)用程序中的AndroidManifest.xml配置文件中救崔,我們沒有指定Application標(biāo)簽的process屬性惶看,系統(tǒng)就會默認(rèn)使用package的名稱。每一個應(yīng)用程序都有自己的uid六孵,因此纬黎,這里uid + process的組合就可以為每一個應(yīng)用程序創(chuàng)建一個ProcessRecord。這里主要是調(diào)用Process:start接口來創(chuàng)建一個新的進(jìn)程劫窒,新的進(jìn)程會導(dǎo)入android.app.ActivityThread類本今,并且執(zhí)行它的main函數(shù),這就是每一個應(yīng)用程序都有一個ActivityThread實例來對應(yīng)的原因主巍。

5冠息、應(yīng)用進(jìn)程初始化

我們來看Activity的main函數(shù),這里綁定了主線程的Looper孕索,并進(jìn)入消息循環(huán)逛艰,大家應(yīng)該知道,整個Android系統(tǒng)是消息驅(qū)動的搞旭,這也是為什么主線程默認(rèn)綁定Looper的原因散怖。attach函數(shù)最終調(diào)用了ActivityManagerService的遠(yuǎn)程接口ActivityManagerProxy的attachApplication函數(shù),傳入的參數(shù)是mAppThread肄渗,這是一個ApplicationThread類型的Binder對象镇眷,它的作用是AMS與應(yīng)用進(jìn)程進(jìn)行進(jìn)程間通信的。

6翎嫡、在AMS中注冊應(yīng)用進(jìn)程欠动,啟動啟動棧頂頁面

前面我們提到了AMS負(fù)責(zé)系統(tǒng)中四大組件的啟動、切換钝的、調(diào)度及應(yīng)用進(jìn)程的管理和調(diào)度等工作翁垂,通過上一個流程我們知道應(yīng)用進(jìn)程創(chuàng)建后通過Binder驅(qū)動與AMS產(chǎn)生交互,此時AMS則將應(yīng)用進(jìn)程創(chuàng)建后的信息進(jìn)行了一次 注冊 硝桩,如果拿Windows系統(tǒng)程序注冊到的注冊表來理解這個過程,可能會更形象一些枚荣。mMainStack.topRunningActivityLocked(null)從堆棧頂端取出要啟動的Activity碗脊,并在realStartActivityLockedhan函數(shù)中通過ApplicationThreadProxy調(diào)回App進(jìn)程啟動頁面。此時在App進(jìn)程,我們可以看到衙伶,經(jīng)過一些列的調(diào)用鏈最終調(diào)用至MainActivity:onCreate函數(shù)祈坠,之后會調(diào)用至onResume,而后會通知AMS該MainActivity已經(jīng)處于resume狀態(tài)矢劲。至此赦拘,整個啟動流程告一段落。

應(yīng)用啟動流程時序圖.png

詳細(xì)的啟動流程分析

以被啟動應(yīng)用的角度看整個流程

詳細(xì)分析(個人感覺沒有時序來的容易理解)

以應(yīng)用啟動的角度看整個過程.jpg

補充知識 APP啟動方式

通常來說芬沉,APP中啟動方式分為兩種:冷啟動和熱啟動躺同。
  • 冷啟動:當(dāng)啟動應(yīng)用時,后臺沒有該應(yīng)用的進(jìn)程丸逸,這時系統(tǒng)會重新創(chuàng)建一個新的進(jìn)程分配給該應(yīng)用蹋艺,這個啟動方式就是冷啟動。
  • 熱啟動:當(dāng)啟動應(yīng)用時黄刚,后臺已有該應(yīng)用的進(jìn)程(例:按back鍵/home鍵捎谨,應(yīng)用雖然會退出,但是該應(yīng)用的進(jìn)程是依然會保留在后臺憔维,可進(jìn)入任務(wù)列表查看)涛救,所以在已有進(jìn)程的情況下,這種啟動會從已有的進(jìn)程中來啟動應(yīng)用业扒,這個方式叫熱啟動检吆。

請注意:上面說的啟動是點擊app的啟動圖標(biāo)來啟動的,而另外一種方式是進(jìn)入最近使用的列表界面來啟動應(yīng)用凶赁,這種不應(yīng)該叫啟動咧栗,應(yīng)該叫恢復(fù)。

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末虱肄,一起剝皮案震驚了整個濱河市致板,隨后出現(xiàn)的幾起案子,更是在濱河造成了極大的恐慌咏窿,老刑警劉巖斟或,帶你破解...
    沈念sama閱讀 222,590評論 6 517
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件,死亡現(xiàn)場離奇詭異集嵌,居然都是意外死亡萝挤,警方通過查閱死者的電腦和手機,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 95,157評論 3 399
  • 文/潘曉璐 我一進(jìn)店門根欧,熙熙樓的掌柜王于貴愁眉苦臉地迎上來怜珍,“玉大人,你說我怎么就攤上這事凤粗∷址海” “怎么了?”我有些...
    開封第一講書人閱讀 169,301評論 0 362
  • 文/不壞的土叔 我叫張陵,是天一觀的道長柔袁。 經(jīng)常有香客問我呆躲,道長,這世上最難降的妖魔是什么捶索? 我笑而不...
    開封第一講書人閱讀 60,078評論 1 300
  • 正文 為了忘掉前任插掂,我火速辦了婚禮,結(jié)果婚禮上腥例,老公的妹妹穿的比我還像新娘辅甥。我一直安慰自己,他們只是感情好院崇,可當(dāng)我...
    茶點故事閱讀 69,082評論 6 398
  • 文/花漫 我一把揭開白布肆氓。 她就那樣靜靜地躺著,像睡著了一般底瓣。 火紅的嫁衣襯著肌膚如雪谢揪。 梳的紋絲不亂的頭發(fā)上,一...
    開封第一講書人閱讀 52,682評論 1 312
  • 那天捐凭,我揣著相機與錄音拨扶,去河邊找鬼。 笑死茁肠,一個胖子當(dāng)著我的面吹牛患民,可吹牛的內(nèi)容都是我干的。 我是一名探鬼主播垦梆,決...
    沈念sama閱讀 41,155評論 3 422
  • 文/蒼蘭香墨 我猛地睜開眼匹颤,長吁一口氣:“原來是場噩夢啊……” “哼!你這毒婦竟也來了托猩?” 一聲冷哼從身側(cè)響起印蓖,我...
    開封第一講書人閱讀 40,098評論 0 277
  • 序言:老撾萬榮一對情侶失蹤,失蹤者是張志新(化名)和其女友劉穎赦肃,沒想到半個月后公浪,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體,經(jīng)...
    沈念sama閱讀 46,638評論 1 319
  • 正文 獨居荒郊野嶺守林人離奇死亡厅各,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點故事閱讀 38,701評論 3 342
  • 正文 我和宋清朗相戀三年讯检,在試婚紗的時候發(fā)現(xiàn)自己被綠了卫旱。 大學(xué)時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片。...
    茶點故事閱讀 40,852評論 1 353
  • 序言:一個原本活蹦亂跳的男人離奇死亡投放,死狀恐怖适贸,靈堂內(nèi)的尸體忽然破棺而出,到底是詐尸還是另有隱情拜姿,我是刑警寧澤,帶...
    沈念sama閱讀 36,520評論 5 351
  • 正文 年R本政府宣布谒获,位于F島的核電站批狱,受9級特大地震影響展东,放射性物質(zhì)發(fā)生泄漏。R本人自食惡果不足惜盐肃,卻給世界環(huán)境...
    茶點故事閱讀 42,181評論 3 335
  • 文/蒙蒙 一砸王、第九天 我趴在偏房一處隱蔽的房頂上張望。 院中可真熱鬧小槐,春花似錦、人聲如沸凿跳。這莊子的主人今日做“春日...
    開封第一講書人閱讀 32,674評論 0 25
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽曾掂。三九已至壁顶,卻和暖如春,著一層夾襖步出監(jiān)牢的瞬間许蓖,已是汗流浹背。 一陣腳步聲響...
    開封第一講書人閱讀 33,788評論 1 274
  • 我被黑心中介騙來泰國打工膊爪, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留米酬,地道東北人。 一個月前我還...
    沈念sama閱讀 49,279評論 3 379
  • 正文 我出身青樓赃额,卻偏偏與公主長得像爬早,于是被迫代替她去往敵國和親启妹。 傳聞我的和親對象是個殘疾皇子,可洞房花燭夜當(dāng)晚...
    茶點故事閱讀 45,851評論 2 361

推薦閱讀更多精彩內(nèi)容