1、系統架構:java
一)、系統分層:(由下向上)【如圖】android
一、安卓系統分爲四層,分別是Linux內核層、Libraries層、FrameWork層,以及Applications層;git
其中Linux內核層包含了Linux內核和各類驅動;編程
Libraries層包含各類類庫(動態庫(也叫共享庫)、android運行時庫、Dalvik虛擬機),編程語言主要爲C或C++架構
FrameWork層大部分使用java語言編寫,是android平臺上Java世界的基石app
Applications層是應用層,咱們在這一層進行開發,使用java語音編寫curl
二、Dalvik VM和傳統JVM的區別:編程語言
傳統的JVM:編寫.java文件 à 編譯爲.class文件 à 打包成.jar文件函數
Dalvik VM: 編寫.java文件 à 編譯爲.class文件 à 打包成.dex文件 à 打包成.apk文件(經過dx工具)工具
將全部的類整合到一個文件中,提升了效率。更適合在手機上運行
一、Linux內核層[LINUX KERNEL]:
包含Linux內核和驅動模塊(好比USB、Camera、藍牙等)。
Android2.2(代號Froyo)基於Linux內核2.6版本。
二、Libraries層[LIBRARIES]:
這一層提供動態庫(也叫共享庫)、android運行時庫、Dalvik虛擬機等。
編程語言主要爲C或C++,因此能夠簡單的當作Native層。
三、FrameWork層[APPLICATION FRAMEWORK]:
這一層大部分用java語言編寫,它是android平臺上Java世界的基石。
四、Applications層[APPLICATION]:應用層
如圖所示:
系統分層的圖總體簡化爲下面的一張圖,對應以下:
FrameWork層 --------à Java世界
Libraries層 --------à Native世界
Linux內核層 --------à Linux OS
Java世界和Native世界間的通訊是經過JNI層
JNI層和Native世界均可以直接調用系統底層
二)、系統編譯:
一、主要步驟:系統環境的準備,下載源碼、編譯源碼、輸出結果:
目前系統的編譯環境只支持Ubuntu 以及 Mac OS 兩種操做系統,磁盤的控件要足夠大
在下載源碼的時候,因爲Android源碼使用Git進行管理,須要下載一些工具,如apt-get install git-core curl
源碼下載好後,進行編譯:首先搭建環境,部署JDK(不一樣的源碼編譯時須要的JDK版本不一樣,如2.2須要JDK5,2.3須要1.6),
而後設置編譯環境:使用. build/envsetup.sh腳本;選擇編譯目標(能夠根據本身須要的版本進行不一樣的搭配)
最後經過make –j4的命令進行編譯。(make是編譯的函數即命令,j4指的是cpu處理器的核數:單核的是j4 x i;雙核的是j8)
最後將編譯好的結果進行輸出:全部的編譯產物都位於 /out 目錄下
二、編譯流程圖
2、系統的啓動:
經過Linux內核將Linux系統中用戶空間的第一個進程init啓動起來,這是安卓世界第一個被啓動的進程;
而後在init中會加載init.rc的配置文件,並開啓系統的守護進程(守護media(多媒體的裝載)和孵化器zygote(Java世界的開啓)),其實此時調試橋的守護進程也被開啓起來了;
而後會處理一些動做執行,在app_main.cpp中會將Zygote孵化器(Zygote是整個java世界的基礎,整個安卓世界中(包括framework和app等apk)都是由孵化器啓動的)啓動起來:
在app_main中,會調用AppRuntime的start方法開啓AppRuntime,其實開啓的是其父類AndroidRuntime的start方法被調用,zygote由此就被調用了,此時Native層的右上角有一塊區域即ANDROID RUNTIME就啓動起來了;
與此同時,AppRuntime會調用ZygoteInit的main方法啓動ZygoteInit(整個的APPLICATION 和FRAMEWORK都會由ZygoteInit帶起來的,JNI也被啓動起來):
在ZygoteInit中會調用SystemServer這個類,在SystemServer的main方法中啓動init1()方法,將system_init.cpp開啓起來,在init1()方法中,將整個Native世界(即LIBRARIES層)開啓起來了
而後在system_init.cpp會調用SystemServer的init2()方法開啓ServerThread,經過ServerThread將framework層開啓起來(全部的就所有開啓起來了),即java世界(APPLICATION FRAMEWORK)就被啓動了;此時ActivityManager,WindowManager,PackageManager(最主要,全部的清單文件及apk都有它管理)等等framework層所有開啓起來
一)安卓系統的整體啓動順序:
一、經過LINUX內核,將init進程啓動起來(是Linux系統中用戶空間的第一個進程)
二、將ANDROID RUNTIME這一塊的內容啓動完畢
三、分爲兩步分別啓動LIBRARIES(即Native世界)和APPLICATION FRAMEWORK(即java世界)
1)先啓動LIBRARIES(即Native世界)
2)後啓動APPLICATION FRAMEWORK(即java世界)【ActivityManager,WindowManager,電源管理等等】
二)具體啓動流程
一)、啓動流程:
一、init進程:——安卓世界第一個被啓動的進程
加載一堆配置文件,核心加載的init.rc配置文件,其中包含了孵化器和守護進程都被開啓了
1)、啓動服務:開啓ServerManager
守護進程啓動(Daemon Process):/system/bin/servicemanager
守護的是:
①、Java世界的開啓:onrestart restart zygote
②、多媒體的裝載:onrestart restart media
@、adbd的守護也被開啓起來了,即調試橋的守護進程也被開啓起來了
2)、啓動孵化器Zygote
在app_main中啓動孵化器Zygote,整個安卓世界中(包括framework和app等apk)都是由孵化器啓動的
【此時虛擬機還沒開啓起來,只是配置了一些vm的參數】
三、app_main:——開啓孵化器
app_main中,調用AppRuntime的start方法,將Native層的右上角有一塊區域,即ANDROID RUNTIME啓動起來
其中的start方法實際是其父類AndroidRuntime的start方法
【此時VM虛擬機被開啓起來了,經過start方法開啓,在AndroidRuntime中並設置了默認的內存大小16M】
【註冊JNI,並啓動孵化器Zygote】
四、ZygoteInit開啓
AppRuntime被啓動後,會調用ZygoteInit的main方法,啓動ZygoteInit;
而後,整個的APPLICATION 和FRAMEWORK都會由ZygoteInit帶起來的
五、SystemServer啓動:
ZygoteInit調用SystemServer這個類,在SystemServer的main方法中啓動init1()方法,將system_init.cpp開啓起來
在init1()方法中,將整個Native世界開啓起來了
六、ServerThread啓動(開啓framework層)
調用SystemServer的init2()方法開啓ServerThread,經過ServerThread將framework層開啓起來(全部的就所有開啓起來了)
此時ActivityManager,WindowManager,PackageManager(最主要,全部的清單文件及apk都有它管理)等等framework層所有開啓起來
二)、具體介紹:
一、啓動入口:init進程
@、源碼位置:/system/core/init/init.c
@、進程入口:main方法
1)建立文件夾,掛載設備【經過mkdir的命令建立,掛載一些系統設備後】
2)重定向輸入輸出,如錯誤信息輸出【設置了一些輸入輸出的處理】
3)設置日誌輸出【一些系統的日誌】
4)init.rc系統啓動的配置文件【加載了相關的信息,不一樣版本的手機所特有的配置信息】
①、文件位置:/system/core/rootdir
②、守護進程啓動(Daemon Process):/system/bin/servicemanager
守護的是
Java世界的開啓:onrestart restart zygote
多媒體的裝載:onrestart restart media
adbd守護也被開啓起來了,即調試橋(adb[Android Debug Bridge])的守護進程(adbd[Android Debug Bridge Daemon])也被開啓起來了
③、啓動Zygote——app_main.cpp【Zygote是整個java世界的基礎】
當編譯以後,在system/bin/app_process下會有孵化器的啓動Xzygote
守護進程被開啓以後,緊接着Zygote也被啓動起來了
5)解析和當前設備相關的配置信息(/init.%s.rc)
Tips:
當解析完init.rc和設備配置信息後會獲取到一系列Action
Init將動做的執行劃分爲四個階段(優先級由大到小):
early-init :初期
Init :初始化階段
early-boot :系統啓動的初期
boot :系統啓動
6)處理動做執行:這個階段Zygote將被啓動
7)無限循環階段,等待一些事情發生
二、Zygote簡介:
@、Zygote啓動:app_main.cpp
1)Zygote簡介:
①、自己爲Native的應用程序
②、由init進程經過init.rc加載
2)功能分析:
①、Main方法中AppRuntime.start(),工做由父類AndroidRuntime來完成
②、在AndroidRuntime中開啓了以下內容:
@startVM——開啓虛擬機(查看堆內存設置):默認16M【】
@註冊JNI函數【此時還在Native層,須要將鏈接java和c的橋(即JNI)搭建好】
@啓動「com.android.internal.os.ZygoteInit」的main方法
【系統級別的包(由runtime的start方法開啓的這個包)】
start方法實際是其父類AndroidRuntime的
@進入java世界的入口
三、ServiceThread的簡介:(java世界所作的事情)
1)preloadClasses();:預加載class
讀取一個preloaded-classes的配置文件
此文件的內容很是多,這就是安卓系統啓動慢的緣由之一
此時會有一個垃圾回收的操做gc(),將無用的回收掉
2)ZygoteInit在main方法中利用JNI開啓com.android.server.SystemServer
3)啓動system_init.cpp處理Native層的服務
4)而後調用SystemServer的init2()
5)啓動ServiceThread,啓動android服務
6)Launcher啓動
3、開機時的時間消耗:
一、ZygoteInit.main()中會預加載類
目錄:framework/base/preload-class
ZygoteInit.main()會加載不少的類,將近1800多個(安卓2.3的)
二、開機時會對系統全部的apk進行掃描
須要將全部的應用展示給用戶,就須要對apk進行掃描,掃描全部的包
data目錄下有個apk的包
system目錄下有個apk的包
framework目錄下也有相關的包
三、SystemServer建立的那些Service