Android系统 init.rc文件详解

简介: Android系统 init.rc文件详解

在这篇博客中,深入探讨了Android系统中的init.rc文件,这是Android系统启动和运行的关键部分。详细解析了init.rc文件中的命令和动作,包括内置命令,外部命令,属性触发器和事件触发器,并且详细介绍了它们的使用和定义。还讨论了Android 11++中init.rc文件的执行顺序,以及如何根据系统属性和事件来定义和触发动作。这篇博客对于理解和控制Android系统的启动和运行过程非常有帮助。

系列文章

Android系统 init.rc 第一次开机创建文件节点实现和原理分析

Android系统 init.rc开机执行shell脚本

Android系统 init.rc sys/class系统节点写不进解决方案和原理分析

Android系统 init.rc文件详解

Android系统 自定义动态修改init.custom.rc

Android USB系统初始化init.usb.configfs.rc

Android USB系统初始化init.usb.rc

1. init.rc文件概述

1.1 init.rc文件的定义与作用
  • init.rc文件是一个配置文件,由Android初始化语言编写的脚本,主要包含五种类型语句:Action、Command、Service、Option、Import。
  • init.rc文件由Android系统第一个启动的init程序解析,此文件由语句组成,主要包含了四种类型的语句:Action, Commands,Services, Options.
  • init.rc文件是Android系统启动时执行的脚本文件,它负责系统的初始设置,如挂载文件系统,创建目录,设置属性,启动服务等。
1.2 Android启动流程中init.rc的角色
  • Android启动流程可以分为三个主要阶段:第一阶段初始化(first_stage_init),SELinux设置(selinux_setup),第二阶段初始化(second_stage_init)。
  • 第一阶段初始化负责设置最低限度的基本需求用以加载系统其余部分,具体来说,包括“/dev”,“/proc”的挂载,挂载“early mount”分区 (这包括所有包含系统代码的分区,例如system和vendor)。对于有ramdisk的设备,将system.img挂载到“/”。对于没有ramdisk的设备,将system.img挂载到“/system_root”。
  • SELinux设置阶段可选地编译并加载SELinux到系统中,这个阶段主要是加载初始化selinux相关的东西,如sepolicy、seapp_contexts等。
  • 第二阶段初始化是init的主要阶段,将运行并通过init继续引导init.rc脚本。在这个阶段中,init会解析init.rc文件和其他相关的rc文件,并根据其中定义的命令和服务来完成系统启动。例如,init会导入init.super.rc文件 (我在rk3568没看到这个文件),用于挂载super分区和动态分区;导入init.hardware.rc文件,用于启动硬件相关的服务;导入init.zygote64_32.rc文件,用于启动Zygote进程和应用程序框架等。

2. init.rc文件结构和语法

2.1 init.rc文件的基本结构
  • init.rc文件由多个部分组成,每个部分以一个关键字开头,并用花括号括起来。例如:
service <name> <pathname> [ <argument> ]*
{
    <option>
    <option>
    ...
}
  • 关键字有以下几种:service, action, onrestart, import, writepid。
  • service表示定义一个服务,action表示定义一个动作,onrestart表示定义一个服务重启时执行的命令,import表示导入其他rc文件,writepid表示将服务进程的PID写入到指定文件。
2.2 init.rc文件的语法规则
  • init.rc文件中的每一行都是一个语句或者一个注释。注释以#开头,并且只能单独占一行。
  • 语句的格式为:关键字 参数1 参数2 … 参数n
  • 参数之间用空格或者制表符分隔,不能用逗号或者其他符号。
  • 参数可以是字符串,数字,变量或者表达式。字符串必须用双引号括起来,数字可以是十进制或者十六进制(以0x开头)。变量以$开头,可以是系统属性或者环境变量。表达式可以是比较运算符(==, !=, <, >, <=, >=)或者逻辑运算符(&&, ||, !)组合的布尔值。
  • 语句可以跨越多行,但是必须在每行的末尾加上反斜杠(\)表示续行。

3. init.rc文件中的命令和动作

3.1 常用命令详解

命令是init.rc文件中的基本元素,它们用于执行一些具体的操作,如挂载文件系统,设置属性,启动服务等。命令有以下几种类型:

内置命令

这些命令是init进程直接实现的,它们通常用于执行一些基本的系统操作,如挂载文件系统,设置系统属性,启动和停止服务等。这些命令是Android系统启动和运行的基础,它们在系统的整个生命周期中都可能被使用。

命令 示例 说明 参数
setprop setprop ro.debuggable 1 设置一个系统属性的值 是属性名,是属性值
getprop getprop ro.bootmode 获取一个系统属性的值 是属性名
start start surfaceflinger 启动一个服务进程 是服务名
stop stop surfaceflinger 停止一个服务进程 是服务名
restart restart media 重启一个服务进程 是服务名
class_start class_start core 启动一类服务进程 是服务类别
class_stop class_stop core 停止一类服务进程 是服务类别
class_reset class_reset core 重置一类服务进程的状态 是服务类别
trigger trigger init 触发一个触发器段落的执行 <trigger_name>是触发器名
write write /sys/class/leds/lcd-backlight/brightness 255 向一个文件写入一个值 是文件路径,是写入值
copy copy /system/etc/init/hw/init.{ro.hardware}.rc /data/misc/wifi/wpa_supplicant.conf 复制一个文件到另一个文件 <src_path>是源文件路径,<dst_path>是目标文件路径
symlink symlink /system/bin/linker /system/bin/linker64 创建一个软链接到另一个文件 <target_path>是目标文件路径,<link_path>是软链接路径
chmod chmod 0660 /data/misc/wifi/wpa_supplicant.conf 修改一个或多个文件的权限模式 是八进制数表示的权限位,<path…>是文件路径列表
chown chown system system /data/misc/wifi/wpa_supplicant.conf 改变文件或目录的所有者和组 .是所有者和组,是文件或目录路径
mount mount ext4 /dev/block/mmcblk0p1 /system 挂载文件系统 文件系统类型,设备,挂载点
umount umount /system 卸载文件系统 挂载点
外部命令

这些命令是由系统提供的可执行文件实现的,它们通常用于执行一些更复杂的操作,如创建和删除目录,修改文件权限等。这些命令通常在系统启动时被执行,用于设置系统的初始状态。

命令 示例 说明 参数
mkdir mkdir /data/misc/wifi 0770 wifi wifi 创建目录 路径,权限,所有者,组
rmdir rmdir /data/misc/wifi 删除目录 路径
rm rm /data/misc/wifi/wpa_supplicant.conf 删除文件 文件路径
exec exec – /system/bin/sh -c “mkdir /data/app-private” 执行一个命令,通常用于执行一些复杂的shell命令 命令行
属性触发器

这些命令是由系统属性的变化触发的,它们通常用于响应系统状态的变化,如电池电量低,网络连接变化等。这些命令可以让我们在系统属性变化时执行一些特定的操作,以适应新的系统状态。

命令 示例 说明 参数
on property:= on property:ro.bootmode=charger 当属性的值变为时,执行后面的命令 是属性名,是属性值
事件触发器

这些命令是由系统事件触发的,它们通常用于响应系统的一些特定事件,如系统启动,设备插入等。这些命令可以让我们在特定的系统事件发生时执行一些特定的操作,以响应这些事件。

命令 示例 说明 参数
on on boot 当事件发生时,执行后面的命令 是事件名

以上是一些常见的命令,但并不是全部,Android init语言的完整语法可以在Android源代码的system/core/init/README.md文件中找到。

3.2 常用动作详解
  • 动作是由一组命令组成的,它们在满足某个触发条件时执行。动作的格式为:
on <trigger>
    <command>
    <command>
    ...
  • 触发条件可以是系统属性或者系统事件。系统属性的格式为:property:<name>=<value>,表示当属性<name>的值变为<value>时触发。系统事件的格式为:<event>,表示当<event>事件发生时触发。常用的系统事件有以下几种:
顺序 阶段 描述
1 on early-init 在系统启动的早期阶段,此时只有根文件系统是可写的,其他如/system/data等都是只读的。
2 on init 在系统初始化阶段,此时还不能访问/system/data等目录。
3 on early-fs 在文件系统准备好之后的早期阶段,此时可以访问/system等目录,但/data等目录可能还是只读的。
4 on fs 在文件系统准备好之后,此时可以访问/system等目录,但/data等目录可能还是只读的。
5 on post-fs 在文件系统挂载之后,此时可以访问大部分目录,但/data等目录可能还是只读的。
6 on post-fs-data /data等目录准备好之后,此时可以访问所有目录。
7 on early-boot 在系统启动的早期阶段,此时可以访问所有目录,并且所有服务都已经启动。
8 on boot 在系统启动完成之后,此时可以访问所有目录,并且所有服务都已经启动。
9 on post-boot 在系统启动完成后的后期阶段,此时可以访问所有目录,并且所有服务都已经启动,通常用于启动一些非关键服务。
10 on property:<name>=<value> 当系统属性<name>的值变为<value>时,执行后面的命令。
11 on <event> <event>事件发生时,执行后面的命令。常见的事件有boot(系统启动完成)、fs(文件系统已经挂载)、post-fs-data/data分区挂载后执行)、charger(充电模式启动)等。
  • 动作中的命令可以是内置命令,外部命令,或者其他动作的触发器。例如:
on boot
    # Start the low-level logging daemon
    start logd
    # Start the kernel logging daemon
    start klogd
    # Trigger late init
    trigger late-init

  • 动作可以嵌套定义,即一个动作中可以包含另一个动作的定义。例如:
on property:sys.boot_completed=1
    # Action to run upon boot completion.
    on boot_complete
        trigger boot_complete

4. init.rc文件编写

4.1. 编写自己的init.rc文件

算了 尝试了几种方法都加不成功 , 后面再补充…


希望对你有所帮助。如果你有任何问题或建议,欢迎留言讨论。谢谢!

相关文章
|
15天前
|
存储 数据库 Android开发
安卓Jetpack Compose+Kotlin,支持从本地添加音频文件到播放列表,支持删除,使用ExoPlayer播放音乐
为了在UI界面添加用于添加和删除本地音乐文件的按钮,以及相关的播放功能,你需要实现以下几个步骤: 1. **集成用户选择本地音乐**:允许用户从设备中选择音乐文件。 2. **创建UI按钮**:在界面中创建添加和删除按钮。 3. **数据库功能**:使用Room数据库来存储音频文件信息。 4. **更新ViewModel**:处理添加、删除和播放音频文件的逻辑。 5. **UI实现**:在UI层支持添加、删除音乐以及播放功能。
|
11天前
|
存储 监控 调度
Android系统服务:WMS、AMS相关知识
参考文献 Android窗口管理服务WindowManagerService计算Activity窗口大小的过程分析 Android窗口管理服务WindowManagerService显示Activity组件的启动窗口(Starting Window)的过程分析 Android窗口管理服务WindowManagerService对输入法窗口(Input Method Window)的管理分析 Android窗口管理服务WindowManagerService显示窗口动画的原理分析
|
16天前
|
缓存 Android开发 Kotlin
【安卓app开发】kotlin Jetpack Compose框架 | 先用OKhttp下载远程音频文件再使用ExoPlayer播放
使用 Kotlin 的 Jetpack Compose 开发安卓应用时,可以结合 OkHttp 下载远程音频文件和 ExoPlayer 进行播放。在 `build.gradle` 添加相关依赖后,示例代码展示了如何下载音频并用 ExoPlayer 播放。代码包括添加依赖、下载文件、播放文件及简单的 Compose UI。注意,示例未包含完整错误处理和资源释放,实际应用需补充这些内容。
|
15天前
|
Java Linux Android开发
Android面试题之说说系统的启动流程(总结)
这篇文章概述了Android系统的启动流程,从Boot Rom到Zygote进程和SystemServer的启动。init进程作为用户级别的第一个进程,负责创建文件目录、初始化服务并启动Zygote。Zygote通过预加载资源和创建Socket服务,使用fork函数生成SystemServer进程。fork过程中,子进程继承父进程大部分信息但具有独立的进程ID。Zygote预加载资源以减少后续进程的启动时间,而SystemServer启动众多服务并最终开启Launcher应用。文中还讨论了为何从Zygote而非init或SystemServer fork新进程的原因。
22 2
|
1天前
|
Java 开发工具 Android开发
详细解读Android开发DNK开发将.c文件打包成os
详细解读Android开发DNK开发将.c文件打包成os
|
3天前
|
安全 搜索推荐 Android开发
探索安卓和iOS系统的优劣与特点
在移动操作系统领域,安卓和iOS一直是最热门的两个选择。本文将探讨安卓和iOS系统的优劣与特点,帮助读者更好地了解这两个操作系统,并为选择合适的移动设备提供参考。
11 0
|
6天前
|
Android开发
Android Gradle开发—脚本实现自动打包后复制一份APK文件,并修改APK名称,到指定目录作备份
Android Gradle开发—脚本实现自动打包后复制一份APK文件,并修改APK名称,到指定目录作备份
18 0
|
6天前
|
缓存 大数据 Android开发
Android 巧用putBinder方法传递大文件
Android 巧用putBinder方法传递大文件
14 0
|
6天前
|
开发工具 Android开发
Android 代码自定义drawble文件实现View圆角背景
Android 代码自定义drawble文件实现View圆角背景
15 0
|
14天前
|
JavaScript Java 测试技术
基于SpringBoot+Vue+uniapp的安卓的微博客系统的详细设计和实现
基于SpringBoot+Vue+uniapp的安卓的微博客系统的详细设计和实现
11 0