鸿蒙OS开源代码精要解读之——init 原创 精华

阿拉神农
发布于 2021-5-8 10:48
浏览
1收藏

作者介绍:

中科创达OpenHarmony研究组

 

说明:

  中科创达OpenHarmony研究组第一时间对https://gitee.com/openharmony上开源的代码进行了详尽的代码研读和学习。为此,我们打算编写一系列篇幅中等,内容精炼的源码分析文章来引领大家更进一步的走进鸿蒙OS。随着对代码的了解,广大开发者想亲自动手参与的意愿和信心也会随之增强——这也是鸿蒙OS开源的意义所在。

 

本篇内容摘要:

本篇以OpenHarmony中ipcamera_hi3518ev300为编译目标,介绍init进程的相关代码。


写在前面的话

我们对OpenHarmony的代码进行了一个简单粗略的统计。除去所有的third_party代码(即OpenHarmony使用的第三方开源库),其他剩余的代码中,以.c、.h文件为统计入口,总有效代码行数(不含注释、空行等,统计工具为tSourceCounter)为325627行。其中,归属kernel目录下的总有效代码行数为74150行。整个OpenHarmony中,kernel部分占比为22.8%左右,代码量上占大头的还在于kernel之上的、我们称之为Framework的部分。根据我们在Android系统上多年的摸索和经验,Framework恰恰是Android OS的精髓。所以,以OpenHarmony目前才20多万行的Framework代码量来看,感兴趣的开发者在这块参与共建、献策献力的机会非常大。

 

1.  OpenHarmony源码的下载和编译

先介绍代码的下载和编译。我们研究组用得是ubuntu 19.10的主机环境。

 

1.1  源码下载

见附件,我们使用的是第四种方式“获取方式4:从代码仓库获取”。执行这一节中的几个命令,即可得到整个源码仓库。

 

1.2  编译源码

我们选择的编译目标是“Hi3518解决方案”,其编译后的输出目录名为ipcamera_hi3518ev300。ipcamera_hi3518ev300是一个基于海思的ip摄像头设备。相关的介绍文档:见附件

 

注意,编译不同的解决方案需要建立对应的编译环境。对hi3518来说,开发者需要按照上述链接里的“搭建环境”来下载和配置。

 

一切就绪后,在源码根目录下执行 python build.py。如果不带参数的话,它会提醒你指定编译目标,截图如下:

鸿蒙OS开源代码精要解读之——init-鸿蒙开发者社区

图1  python build.py不带参数的执行结果

 

这次,我们通过python build.py ipcamera_hi3518ev300即可编译“Hi3518解决方案”。编译耗时10几分钟。

 

注意,编译过程中可能出现找不到<valgrind/valgrind.h>的错误。这是因为目前我们下载的代码中没有包含valgrind的头文件。开发者可以手动将/usr/include/valgrind目录拷贝到prebuilts/lite/sysroot/usr/include下即可(仅限Ubuntu平台,需提前安装好valgrind工具)。

 

1.3  OpenHarmony编译相关小知识介绍

OpenHarmony源码编译系统使用了google开发的gn工具以及ninjia。这二者结合起来比传统的makefile编译系要高效,尤其适合大系统的并行编译。对开发者而言,如果要参与OpenHarmony的开发,需要对gn的语法有些了解。

 

本文仅做一些最基本的介绍:

  1. 使用gn工具的话,开发者将编译规则写在名为BUILD.gn文件中。和Makefile一样,gn文件有自己的语法规则,属于领域语言(Domain Specific Language,DSL)。gn语法不难,但编译规则本身有很多内容,所以一下子要掌握全部内容也不容易。
  2. gn支持自定义模板函数,可放在名为.gni的文件中。OpenHarmony中最常见到的gn模板文件为./build/lite/config/component/lite_component.gni。.gn文件中通过import可导入gni模板文件。OpenHarmony定义了lite_component、lite_library等模板函数。
  3. gn中,可执行文件的编译函数入口为exectuable("文件名"),共享库的编译规则函数为shared_library("文件名")。所以,如果要搜索某个文件对应的编译规则,可以先搜索所有的BUILD.gn文件,然后grep executable。以下是我们grep所有的executable的结果截图。

鸿蒙OS开源代码精要解读之——init-鸿蒙开发者社区

图2  grep BUILD.gn中executable的结果示意

通过这种方式,我们能很快定位到比如init对应的代码在什么地方。

 

最后,我们再简单介绍下OpenHarmony编译系统中和底层OS有关的一个条件编译控制变量ohos_kernel_type。目前,该变量有四个取值,分别为"liteos_a"、"liteos_m"、"liteos_riscv"和"linux":

  1. "liteos_a"和"linux"经常做为一组进行判断。liteos_a实际对应的是Cortex-A系列,其性能相对较高,可以跑Linux系统。
  2. "liteos_m"和"liteos_riscv"往往是一组的。liteos_m对应的是Cortex-M系列,liteos_riscv是Riscv芯片的表示,二者可能都是针对性能一般,功耗较低的设备。

 

ohos_kernel_type的取值由build/lite/product/解决方案名.json文件中的product字段决定。例如,我们选择的ipcamera_hi3518ev300的配置文件内容截图如下,它的kernel字段值为"liteos_a"。

鸿蒙OS开源代码精要解读之——init-鸿蒙开发者社区

图3  build/lite/product/ ipcamera_hi3518ev300.json配置文件示意图

 编译完成后,所有编译生成物都在out/ipcamera_hi3518ev300目录下。

 

2 init源码精要解析

init是Linux系统上的第一个应用进程,是其它进程的源头。对ipcamera_hi3518ev300来说,它的编译产物中也有一个init进程。

 

在上面提到的out/ipcamera_hi3518ev300目录下,有一个rootfs.tar文件。这个文件里就是设备上根文件系统的内容。打开其中的/rootfs/bin目录,可以看到此次编译的可执行程序如下截图所示:

鸿蒙OS开源代码精要解读之——init-鸿蒙开发者社区

图4  out/ipcamera_hi3518ev300/rootfs.tar/bin内容示意

 

借助图2里提到的办法,我们可以定位到init对应的代码路径为base/startup/services/init_lite/。其内容如下图所示:

鸿蒙OS开源代码精要解读之——init-鸿蒙开发者社区

图5  init_lite源码文件示意图

 

main.c是整个init的入口。我们简单看一下它的代码,如下所示。

鸿蒙OS开源代码精要解读之——init-鸿蒙开发者社区

图6  init_lite/main.c

 

init main函数非常精简,非常符合"lite"轻量简便的风格。当然,也不排除未来init的代码会越来越复杂。我们在AOSP上观察到的情况就是一个例子——AOSP里现在的init的相关代码非常复杂)。

 

我们对InitReadCfg比较感兴趣,这个函数内部将读取/etc/init.cfg文件。这个文件在图4中提到的rootfs.tar中可以找到,下图是其内容的示意:

鸿蒙OS开源代码精要解读之——init-鸿蒙开发者社区

图7  rootfs.tar/etc/init.cfg

 

init.cfg本质上是一个json格式的文件。它包括一个名为"jobs"的数组和一个名为"services"的数组。

  1. 对"jobs"来说:内部分别包含"pre-init"、"init"和"post-init"三个元素。从上面的截图中可以看出,这三个元素对应的就是设置挂载一些设备、设置好路径,启动服务等工作。
  2. 对"services"来说:它包含一组服务的定义。所谓的服务,就是系统里的关键进程。可以猜测到,init将根据service的配置来启动对应的服务程序,并设置它的uid、gid、进程优先级和权限等。

 

如果开发者对Android系统有一定了解的话,会发现OpenHarmony和AOSP在init的工作流程上有着相似的设计思路。不过,对OpenHarmony目标设备来说,使用json格式无疑是比较简单且方便的。

 

最后,我们再看一下init的另外一个重要职能——服务进程状况监控。init.cfg中的那些服务属于系统关键进程。运行过程中如果它们出现异常导致进程退出,需要有个办法将它们重新启动以保证业务连续性。

 

这个功能的实现就是利用Linux系统的SIGCHILD信号。init在SignalInitModule中监听了该信号并设置了对应的信号处理函数——SigHandler。SigHandler函数的具体处理过程则比此处说得要更复杂一点。现在,这部分内容就留给读者们自行探索了!!

©著作权归作者所有,如需转载,请注明出处,否则将追究法律责任
分类
get-code_源码获取.md 19.05K 27次下载
quick-start_搭建环境-2.md 20.03K 17次下载
已于2021-5-8 11:32:55修改
3
收藏 1
回复
举报
3条回复
按时间正序
/
按时间倒序
红叶亦知秋
红叶亦知秋

可以,讲解的很详细。

回复
2021-5-8 13:39:40
flyingsmiling
flyingsmiling

附件好评~下载方便

回复
2021-5-8 15:18:55
鸿蒙张荣超
鸿蒙张荣超

赞赞赞!

回复
2021-5-9 22:54:42
回复
    相关推荐