Init是鸿蒙OS的第一个用户态进程,相似于如今Linux发行版中的systemd。Init进程的代码在base\startup\services\init_lite实现。shell
main函数数组
本函数的注解很是清晰,总共4步,app
- 打印系统信息
- 注册信号处理函数
- 读取系统配置文件并进行相关处理
- 进入循环等待信号处理
下面分别解读一下1-3步的相关代码ide
PrintSysInfo函数函数
本函数主要功能就是打印系统信息。post
详细的看GetVersionId函数,因为代码比较长,咱们主要看核心处理的部分:ui
主要功能就是获取设备的相关类型,厂商,品牌,型号等信息。具体看一个函数GetProductType:spa
咱们能够看到,只是调用了硬件抽象层的函数HalGetProcutType,而这个函数依据不一样的硬件有不一样的实现,所以咱们就不继续往下深刻了。操作系统
SignalInitModule函数3d
从信号处理函数来看,init进程主要助理两个信号,SIGCHLD和SIGTERM。
先说简单的SIGTERM信号,这时候init会经过StopAllService函数结束全部的系统服务。若是是收到某个服务终止的SIGCHLD信号,则要视服务的重要性进行处理,有可能重启系统。具体服务包括哪些则经过配置文件进行定义,后续详细说明。
InitReadCfg函数
InitReadCfg这个函数,感受名称不是很合适,由于不光是读了配置文件,实际还经过DoJob函数,执行了不少启动前,中和后的操做。
配置文件的地址以下:
#define INIT_CONFIGURATION_FILE "/etc/init.cfg"
看一下具体init.cfg的一个例子,来自于HiSpark AI Camera套件
vendor\huawei\camera\init_configs\init_liteos_a_3516dv300.cfg
这里面定义了init先后中须要执行的jobs以及init启动完成以后启动的服务。
{ "jobs" : [{ "name" : "pre-init", "cmds" : [ "mkdir /storage/data/log", "chmod 0755 /storage/data/log", "chown 4 4 /storage/data/log", "mkdir /storage/data/softbus", "chmod 0700 /storage/data/softbus", "chown 7 7 /storage/data/softbus", "mkdir /sdcard", "chmod 0777 /sdcard", "mount vfat /dev/mmcblk0 /sdcard rw,umask=000", "mount vfat /dev/mmcblk1 /sdcard rw,umask=000" ] }, { "name" : "init", "cmds" : [ "start shell", "start apphilogcat", "start foundation", "start bundle_daemon", "start appspawn", "start media_server", "start wms_server" ] }, { "name" : "post-init", "cmds" : [ "chown 0 99 /dev/dev_mgr", "chown 0 99 /dev/hdfwifi", "chown 0 99 /dev/gpio", "chown 0 99 /dev/i2c-0", "chown 0 99 /dev/i2c-1", "chown 0 99 /dev/i2c-2", "chown 0 99 /dev/i2c-3", "chown 0 99 /dev/i2c-4", "chown 0 99 /dev/i2c-5", "chown 0 99 /dev/i2c-6", "chown 0 99 /dev/i2c-7", "chown 0 99 /dev/uartdev-0", "chown 0 99 /dev/uartdev-1", "chown 0 99 /dev/uartdev-2", "chown 0 99 /dev/uartdev-3", "chown 0 99 /dev/spidev0.0", "chown 0 99 /dev/spidev1.0", "chown 0 99 /dev/spidev2.0", "chown 0 99 /dev/spidev2.1" ] } ], "services" : [{ "name" : "foundation", "path" : "/bin/foundation", "uid" : 7, "gid" : 7, "once" : 0, "importance" : 1, "caps" : [10, 11, 12, 13] }, { "name" : "shell", "path" : "/bin/shell", "uid" : 2, "gid" : 2, "once" : 0, "importance" : 0, "caps" : [4294967295] }, { "name" : "appspawn", "path" : "/bin/appspawn", "uid" : 1, "gid" : 1, "once" : 0, "importance" : 0, "caps" : [2, 6, 7, 8, 23] }, { "name" : "apphilogcat", "path" : "/bin/apphilogcat", "uid" : 4, "gid" : 4, "once" : 1, "importance" : 0, "caps" : [] }, { "name" : "media_server", "path" : "/bin/media_server", "uid" : 5, "gid" : 5, "once" : 1, "importance" : 0, "caps" : [] }, { "name" : "wms_server", "path" : "/bin/wms_server", "uid" : 0, "gid" : 0, "once" : 1, "importance" : 0, "caps" : [] }, { "name" : "bundle_daemon", "path" : "/bin/bundle_daemon", "uid" : 8, "gid" : 8, "once" : 0, "importance" : 0, "caps" : [0, 1] } ] }
鸿蒙OS的Service
鸿蒙OS的init进程启动后,如上面的例子所示init进程接下来会启动不少服务,对于这些服务,鸿蒙OS有一个统一管理,全部的服务都被注册到以下的动态数组当中。
Service的定义
从定义中不难看出,对于每一个Service,除了基本的名字,可执行文件路径,进程id,还记录了这个Service的crash次数和第一次crash的时间,另外还定义了Service的属性和权限。
对于属性,参考以下常量定义,主要是在该Service奔溃以后是否须要重启。
// service attributes #define SERVICE_ATTR_INVALID 0x001 // option invalid #define SERVICE_ATTR_ONCE 0x002 // do not restart when it exits #define SERVICE_ATTR_NEED_RESTART 0x004 // will restart in the near future #define SERVICE_ATTR_NEED_STOP 0x008 // will stop in reap #define SERVICE_ATTR_IMPORTANT 0x010 // will reboot if it crash
对于Perms,则依据操做系统的定义而不一样。
对于Service,都有启动,中止和重启三个动做。
对于Service Manager,则提供了如下动做:
void RegisterServices(Service* services, int servicesCnt); void StartServiceByName(const char* serviceName); void StopAllServices(); void ReapServiceByPID(int pid);