Android系統啓動過程

Android框架架構圖

這裏寫圖片描述

Linux內核啓動之後就到Android Init進程,進而啓動Android相關的服務和應用。

啓動的過程如下圖所示
這裏寫圖片描述

下面將從Android4.0源碼中,和網絡達人對此的總結中,對此過程加以學習瞭解和總結,

以下學習過程中代碼片段中均有省略不完整,請參照源碼

一 Init進程的啓動

  init進程,它是一個由內核啓動的用戶級進程。內核自行啓動(已經被載入內存,開始運行,

並已初始化所有的設備驅動程序和數據結構等)之後,就通過啓動一個用戶級程序init的方式,完成引導進程。init始終是第一個進程。

  啓動過程就是代碼init.c中main函數執行過程:system\core\init\init.c

在函數中執行了:文件夾建立,掛載,rc文件解析,屬性設置,啓動服務,執行動作,socket監聽……

下面看兩個重要的過程:rc文件解析和服務啓動。

1 rc文件解析

  .rc文件是Android使用的初始化腳本文件 (System/Core/Init/readme.txt中有描述:

four broad classes of statements which are Actions, Commands, Services, and Options.)

  其中Command 就是系統支持的一系列命令,如:export,hostname,mkdir,mount,等等,其中一部分是 linux 命令,

還有一些是 android 添加的,如:class_start : 啓動服務,class_stop :關閉服務,等等。

  其中Options是針對 Service 的選項的。

系統初始化要觸發的動作和要啓動的服務及其各自屬性都在rc腳本文件中定義。 具體看一下啓動腳本:\system\core\rootdir\init.rc

   在解析rc腳本文件時,將相應的類型放入各自的List中:

  \system\core\init\Init_parser.c :init_parse_config_file( )存入到

  action_queue、 action_list、 service_list中,解析過程可以看一下parse_config函數,類似狀態機形式挺有意思。

  這其中包含了服務:adbd、servicemanager、vold、ril-daemon、debuggerd、surfaceflinger、zygote、media……

2 服務啓動

   文件解析完成之後將service放入到service_list中。

文件解析完成之後將service放入到service_list中。

  \system\core\init\builtins.c

   Service的啓動是在do_class_start函數中完成:
int do_class_start(int nargs, char **args)
{
    service_for_each_class(args[1], service_start_if_not_disabled);
    return 0;
}

遍歷所有名稱爲classname,狀態不爲SVC_DISABLED的Service啓動

void service_for_each_class(const char *classname,
                            void (*func)(struct service *svc))
{
       ……
}

static void service_start_if_not_disabled(struct service *svc)
{
    if (!(svc->flags & SVC_DISABLED)) {
        service_start(svc, NULL);
    }
}

do_class_start對應的命令:

  KEYWORD(class_start, COMMAND, 1, do_class_start)

init.rc文件中搜索class_start:class_start main 、class_start core、……

  main、core即爲do_class_start參數classname

init.rc文件中Service class名稱都是main:

   service drm /system/bin/drmserver

    class main

  service surfaceflinger /system/bin/surfaceflinger

   class main

於是就能夠通過main名稱遍歷到所有的Service,將其啓動。

do_class_start調用:

   init.rc中

    on boot  //action

      class_start core    //執行command 對應 do_class_start

      class_start main

Init進程main函數中:

system/core/init/init.c中:

int main(){
     //掛在文件

       //解析配置文件:init.rc……

       //初始化化action queue

     ……
       for(;;){

              execute_one_command();

              restart_processes();

              for (i = 0; i < fd_count; i++) {

            if (ufds[i].revents == POLLIN) {

                if (ufds[i].fd == get_property_set_fd())

                    handle_property_set_fd();

                else if (ufds[i].fd == get_keychord_fd())

                    handle_keychord();

                else if (ufds[i].fd == get_signal_fd())

                    handle_signal();
            }
        }

       }
}

循環調用service_start,將狀態SVC_RESTARTING啓動, 將啓動後的service狀態設置爲SVC_RUNNING。

  pid=fork();

  execve();

  在消息循環中:Init進程執行了Android的Command,啓動了Android的NativeService,監聽Service的變化需求,Signal處理。

Init進程是作爲屬性服務(Property service),維護這些NativeService。

二 ServiceManager啓動

   在.rc腳本文件中zygote的描述:
service servicemanager /system/bin/servicemanager
  class core
  user system
  group system
  critical
  onrestart restart zygote
  onrestart restart media
  onrestart restart surfaceflinger
  onrestart restart drm

ServiceManager用來管理系統中所有的binder service,不管是本地的c++實現的還是java語言實現的都需要

這個進程來統一管理,最主要的管理就是,註冊添加服務,獲取服務。所有的Service使用前都必須先在servicemanager中進行註冊。

  do_find_service( )

  do_add_service( )

  svcmgr_handler( )

  代碼位置:frameworks\base\cmds\servicemanager\Service_manager.c

三 Zygote進程的啓動

  Zygote這個進程是非常重要的一個進程,Zygote進程的建立是真正的Android運行空間,初始化建立的Service都是Navtive service.

(1) 在.rc腳本文件中zygote的描述:

service zygote /system/bin/app_process -Xzygote /system/bin --zygote --start-system-server
  class main
  socket zygote stream 666
  onrestart write /sys/android_power/request_state wake
  onrestart write /sys/power/state on
  onrestart restart media
  onrestart restart netd

參數:--zygote --start-system-server

代碼位置:frameworks/base/cmds/app_process/app_main.cpp

   上面的參數在這裏就會用上,決定是否要啓動和啓動那些進程。
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章