Android底層有一定的認識,研究過相關的Android源碼


一、系統架構:

一)、系統分層:(由下向上)【如圖】

1、安卓系統分為四層,分別是Linux內核層、Libraries層、FrameWork層,以及Applications層;

其中Linux內核層包含了Linux內核和各種驅動;

Libraries層包含各種類庫(動態庫(也叫共享庫)、android運行時庫、Dalvik虛擬機),編程語言主要為C或C++

FrameWork層大部分使用java語言編寫,是android平台上Java世界的基石

Applications層是應用層,我們在這一層進行開發,使用java語音編寫

2、Dalvik VM和傳統JVM的區別:

傳統的JVM:編寫.java文件 à 編譯為.class文件 à 打包成.jar文件

Dalvik VM:  編寫.java文件 à 編譯為.class文件 à 打包成.dex文件 à 打包成.apk文件(通過dx工具)

       將所有的類整合到一個文件中,提高了效率。更適合在手機上運行

 

1、Linux內核層[LINUX KERNEL]:

包含Linux內核和驅動模塊(比如USB、Camera、藍牙等)。

Android2.2(代號Froyo)基於Linux內核2.6版本。

2、Libraries層[LIBRARIES]:

這一層提供動態庫(也叫共享庫)、android運行時庫、Dalvik虛擬機等。

編程語言主要為C或C++,所以可以簡單的看成Native層。

3、FrameWork層[APPLICATION FRAMEWORK]:

這一層大部分用java語言編寫,它是android平台上Java世界的基石。

4、Applications層[APPLICATION]:應用層

 

如圖所示:

系統分層的圖整體簡化為下面的一張圖,對應如下:

FrameWork層       --------à        Java世界

Libraries層           --------à        Native世界

Linux內核層         --------à        Linux OS

 

Java世界和Native世界間的通信是通過JNI層

JNI層和Native世界都可以直接調用系統底層

 

二)、系統編譯:

1、主要步驟:系統環境的准備,下載源碼、編譯源碼、輸出結果:

目前系統的編譯環境只支持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層全部開啟起來

 

一)安卓系統的總體啟動順序:

1、通過LINUX內核,將init進程啟動起來(是Linux系統中用戶空間的第一個進程)

2、將ANDROID RUNTIME這一塊的內容啟動完畢

3、分為兩步分別啟動LIBRARIES(即Native世界)和APPLICATION FRAMEWORK(即java世界)

1)先啟動LIBRARIES(即Native世界)

2)后啟動APPLICATION FRAMEWORK(即java世界)【ActivityManager,WindowManager,電源管理等等】

二)具體啟動流程

一)、啟動流程:

1、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的參數】

3、app_main:——開啟孵化器

       app_main中,調用AppRuntime的start方法,將Native層的右上角有一塊區域,即ANDROID RUNTIME啟動起來

其中的start方法實際是其父類AndroidRuntime的start方法

【此時VM虛擬機被開啟起來了,通過start方法開啟,在AndroidRuntime中並設置了默認的內存大小16M】

【注冊JNI,並啟動孵化器Zygote】

4、ZygoteInit開啟

       AppRuntime被啟動后,會調用ZygoteInit的main方法,啟動ZygoteInit;

       然后,整個的APPLICATION 和FRAMEWORK都會由ZygoteInit帶起來的

5、SystemServer啟動:

       ZygoteInit調用SystemServer這個類,在SystemServer的main方法中啟動init1()方法,將system_init.cpp開啟起來

       在init1()方法中,將整個Native世界開啟起來了

6、ServerThread啟動(開啟framework層)

調用SystemServer的init2()方法開啟ServerThread,通過ServerThread將framework層開啟起來(所有的就全部開啟起來了)

       此時ActivityManager,WindowManager,PackageManager(最主要,所有的清單文件及apk都有它管理)等等framework層全部開啟起來

 

二)、具體介紹:

1、啟動入口: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)無限循環階段,等待一些事情發生

 

2、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世界的入口

 

3、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啟動

 

三、開機時的時間消耗:

1、ZygoteInit.main()中會預加載類

目錄:framework/base/preload-class

ZygoteInit.main()會加載很多的類,將近1800多個(安卓2.3的)

2、開機時會對系統所有的apk進行掃描

       需要將所有的應用展現給用戶,就需要對apk進行掃描,掃描所有的包

       data目錄下有個apk的包

       system目錄下有個apk的包

       framework目錄下也有相關的包

3、SystemServer創建的那些Service

 

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM