Android init.rc详解3

发布于:2025-08-18 ⋅ 阅读:(16) ⋅ 点赞:(0)

关于Android Init的详解,关于Action,Service,Trigger的请参考Android init.rc详解1,关于Options的请参考Android init.rc详解2,本章将介绍常见的Commands、Imports、Properties。

1 Commands

  • bootchart [start|stop]

  1. 启动或停止bootcharting(系统启动性能分析),bootcharting只有在文件/data/bootchart/enabled 存在时才会激活,斗则将不执行任何操作。
  2. bootchart是一个收集和分析Android系统启动过程性能数据的工具,通过采样CPU、I/O、进程活动等信息,生成可视化的启动时序图(.png.svg),帮助开发者优化开机时间。
  3. bootchart start:在启动早期(如 on init 阶段)调用,启动数据采集。
  4. bootchart stop:在启动后期(如 on property:sys.boot_completed=1)调用,停止采集并生成日志。
  5. init.rc中使用该command的举例:
    on post-fs-data
        # Start bootcharting as soon as possible after the data partition is
        # mounted to collect more data.
        mkdir /data/bootchart 0755 shell shell encryption=Require
        bootchart start
    
    on property:sys.boot_completed=1
        bootchart stop
        # Setup per_boot directory so other .rc could start to use it on boot_completed
        exec - system system -- /bin/rm -rf /data/per_boot
        mkdir /data/per_boot 0700 system system encryption=Require key=per_boot_ref
        setprop ro.vendor.qti.per_boot_created 1

Android 系统的关键启动时间指标(如 bootanimation 显示、sys.boot_completed=1)主要取决于:

  • class_start main
  • class_start late_start
  • 关键服务(如 zygotesystem_server)的启动速度。
  • chmod <octal-mode> <path>

  1. 更改指定文件或者目录的访问权限(读/写/执行),使用8进制表示法。
  2. 使用举例:
# set system-background to 0775 so SurfaceFlinger can touch it
chmod 0775 /dev/cpuset/system-background

chmod 0664 /dev/cpuset/foreground/tasks
chmod 0664 /dev/cpuset/background/tasks
chmod 0664 /dev/cpuset/system-background/tasks
chmod 0664 /dev/cpuset/top-app/tasks
  • chown <owner> <group> <path>

  1. 改变文件的所有者和用户组。
  2. 使用举例
 # change permissions for all cpusets we'll touch at runtime
chown system system /dev/cpuset
chown system system /dev/cpuset/foreground
chown system system /dev/cpuset/background
chown system system /dev/cpuset/system-background

✅ 总结

指令 作用 典型用途 注意事项
bootchart [start|stop] 控制启动性能分析 优化开机时间 需手动创建 /data/bootchart/enabled 启用
chmod <mode> <path> 修改文件权限 设置可执行、保护敏感文件 使用八进制权限,最小权限原则
chown <owner> <group> <path> 修改文件所有者和组 确保服务能访问资源 与 chmod 配合使用
  • class _start <serviceclass>

  1. 启动指定类别(service class)的所有服务,前提是这些服务尚未运行。将同一类别的service集中管理,便于延迟启动或者统一控制。
  2. 他是一个批量启动服务的指令,常见的service class由
service class 值 含义
main

系统运行所必需的核心服务:zygote, bluetoothbd, storaged, 

core 核心服务,servicemanager, console,ueventd, bootanim
late_start 非关键、耗时或可延迟的服务(优化启动时间的关键,可以缩短sys.boot_completed时间)
early_hal 需要在main之前启动的服务
hal 指Android HAL层的服务,用于与底层通信。
charger 和充电有关的service,例如charger,hw-health-service,在on charger触发的services
  • class_stop <serviceclass>

  1. 关闭指定类型的services。
  2. 使用举例
# Healthd can trigger a full boot from charger mode by signaling this
# property when the power button is held.
on property:sys.boot_from_charger_mode=1
    class_stop charger
    trigger late-init
  • class_restart [ --only--enabled ] <serviceclass>

  1. 重启指定类别的所有services。
  2. 如果指定了--only--enabled,则跳过被禁用的服务(即disabled修饰的service)。
  3. 如果没有指定该选项,则会尝试重启该类别下的所有服务(包括disabled和oneshort修饰的service),如果服务正在运行,则先stop,然后再start;如果服务没运行,直接start。

✅ 总结

指令 作用 是否阻塞 典型触发时机
class_start <class> 启动指定类别中尚未运行的服务 否(异步) on booton property:
class_stop <class> 停止指定类别中正在运行的所有服务 否(异步) 用户切换、省电模式、调试
class_restart [--only-enabled] <class> 先停止,再重新启动该类所有服务 否(异步) 错误恢复、配置重载、调试
  • start <service>

如果指定的服务尚未运行,则启动该服务。如果该服务已运行,start不会重复启动。

  • stop <service>

停止运行指定的service。

  • restart [ --only-if-running ] <service>

  1. 停止并重启一个正在运行的service。
  2. 如果该service处于重启过程中,则不执行任何操作
  3. 如果该服务未运行,则直接启动该服务(相当于start <service>);
  4. 如果指定了--only-if-running选项,则仅当服务正在运行时才执行重启。如果服务未运行,则不做任何操作。

exec_start <service>

  1. 启动指定的服务,并暂停后续init指令,知道该service执行完成并返回。
  2. 他是惟一能阻塞init进程的同步指令,允许在关键启动中精确控制执行顺序,确保某些service必须启动完成。
  3. 使用举例:
on zygote-start && property:ro.crypto.state=unencrypted
    # wait OTA signature verifcation 
    wait_for_prop odsign.verification.done 1
    # A/B update verifier that marks a successful boot.
    exec_start update_verifier_nonencrypted
    start statsd
    start netd
    start zygote
    start zygote_secondary
  • A/B update:又称无缝更新,设备上由两套系统分区:A和B,当前系统允许在分区A,分区B可以后台静默更新,更新完成后,下次重启就切换到B分区。 
  • 首次启动B系统,则必须标记本次启动成功,如果启动成功,则B被永久标注为“新系统”,如果启动失败,下次自动切换A分区。
  • A/B update verifier:检查当前系统是否时首次从新系统启动,如果是则将successful标志置为1
  • enable <servicename>

  1. 将一个disabled的service转化成enable,即激活service。
  2. enable本身不启动服务,他只是激活service,当service的启动条件满足时才会被启动,即使他是disabled。

✅ 总结

指令 作用 是否阻塞 init 典型使用场景 注意事项
start <servic> 启动一个已定义的服务

 否

(异步)

正常启动服务,如 start zygote 若服务已在运行,不会重复启动
stop <servic> 停止一个正在运行的服务

(异步)

关机、切换模式时停止服务 服务进程退出后不再自动重启(除非有 respawning)
restart <servic> 先 stop,再 start 服务

(异步)

配置变更后重载服务,如 restart adbd 等价于 stop + start,服务会短暂中断
exec_start <servic> 同步执行一个 oneshot 服务,并等待其完成

(同步)

关键初始化任务,如标记 OTA 成功、运行配置脚本 仅适用于 oneshot 服务;init 会等待其退出后再执行后续命令
enable <service> 激活一个被 disabled 的服务,使其可被 start 或自动启动

(异步)

根据属性动态启用服务,如 enable watchdogd when ro.boot.quiescent=1 服务必须先定义为 disabledenable 后若满足条件(如属于 main class 且已 class_start),会立即启动
  • exec [ <seclabel> [ <user> [ <group> *] ] ] -- <command> [ <argument> *]

fork一个子进程并在指定的上下文(SELinux权限以及user/group)下执行。

该指令是一个同步的,会阻塞init进程。在该指令执行完成前,init将暂停后续所有指令。

参数解释 说明
<seclabel>

SELinux 安全上下文,如 u:r:init:s0

用 - 表示默认

<user> 执行用户,如 rootsystemshell
<group>* 零个或多个补充组,如 inetlogsystem
-- 分隔符,表示前面是执行上下文,后面是命令
<command> 要执行的可执行文件路径
[argument]* 命令参数,支持属性展开 ${prop}
  • exec_backgroud [ <seclabel> [ <user> [ <group> *] ] ] -- <command> [ <argument> *]

  1. 与exec类似,fork一个子进程并在指定的上下文(SELinux权限以及user/group)下执行。
  2. 该指令是异步的,不会阻塞init,会继续执行后续指令。

✅ 总结

指令 是否阻塞 init 用途
exec ✅ 是(同步) 执行关键初始化任务,必须完成才能继续
exec_background ❌ 否(异步) 执行非关键、后台任务,不阻塞启动流程
  • setprop <name> <value>

  1. 给指定的系统属性赋值。

  2. 它是触发属性值为条件(on property:)的event,eg:
    on property:sys.boot_completed=1
        bootchart stop
        # Setup per_boot directory so other .rc could start to use it on boot_completed
        exec - system system -- /bin/rm -rf /data/per_boot
        mkdir /data/per_boot 0700 system system encryption=Require key=per_boot_ref
        setprop ro.vendor.qti.per_boot_created 1
  3. 常见的系统属性分类:
    前缀 说明 是否可写
    ro.* 只读属性(Read-Only) ❌ 仅在 init 阶段可设,之后不可改
    sys.* 系统属性,可被 init 和系统服务修改 ✅ 可修改
    persist.* 持久化属性,写入 /data/property/ ✅ 可修改,重启后保留
    ctl.* 控制属性(如 ctl.startctl.stop ✅ 触发服务控制
    debug.* 调试属性 ✅ 开发者可设symlink <target> <path>
  • trigger <event>

触发一个事件,用于从一个Action执行完成后,主动触发另一个Action。

  • symlink <target> <path>

在指定path创建一个指向target的符号链接(相当于软连接,即ln -s <target> <path>)。

  • wait_for_prop <name> <value>

  1. 等待指定系统属性的值变成指定value,如果该属性值等于value,则立即执行后续命令。

  2. 他是init中用于同步控制的关键指令,setprop会触发该指令往后执行。

2 Imports 

  • import <path>

  1. 导入一个init配置文件(或者目录下所有文件)。如果path是文件,则解析该文件;如果path是目录,则解析该目录下所有文件(不递归子目录)。
  2. import是Android init系统实现模块化、分层话配置管理的核心机制。它允许:
    将庞大的初始化配置拆分为多个 .rc 文件;
    按硬件、供应商、产品维度组织配置;
    实现系统组件的解耦与可维护性;
    支持动态加载 /vendor/odm 等分区的配置。

  3. 使用举例,init.rc中
import /init.environ.rc
import /system/etc/init/hw/init.usb.rc
import /init.${ro.hardware}.rc
import /vendor/etc/init/hw/init.${ro.hardware}.rc
import /system/etc/init/hw/init.usb.configfs.rc
import /system/etc/init/hw/init.${ro.zygote}.rc

    3 Properties

    • init.svc.<name>

    1. 查询指定Service name的状态。name是.rc文件中定义的Service名称。
    2. 当每个Service的状态发生便后时,init都会更新对应的init.svc.<name>的属性值。
      eg: 查询某个Service的状态:adb shell getprop init.svc.zygote
    3. 服务的状态值类型有:
    状态值 说明
    running 服务正在运行(主进程已启动且未崩溃)
    stopped 服务已停止(未运行,且不是因为崩溃)
    restarting 服务正在重启(通常因崩溃后由 init 重启)
    stopping 服务正在停止过程中(收到 SIGTERM,但进程尚未退出)
    disabled 服务被禁用(通过 setprop init.svc.<name> disabled
    invalid 服务未定义或路径无效(如可执行文件不存在)
    • ctl. [ <target>_ ] <command> <value>

    1. 该类属性是Android init用于远程控制Service生命周期和行为的“控制通道”。它允许系统其他组件通过设置属性来间接执行start/stop等。
    2. <target>是可选的,指定匹配的Service(当前只支持target取值Interface),注意“_”不要缺失;
    3. <command>是要执行的指令,前边1 Command部分介绍的指令集,常见的有start/stop 
    4. <value>可以是Servicename,如果是Interface,对于AIDL,则value是aidl/instance;对于HIDL,则value是package::Interface/instance。
    5. 使用举例:
    setprop ctl.restart vendor.power-hal-aidl
    setprop ctl.interface_restart android.hardware.power@1.0::IPower/default

    4 Boot Timing

    init进程在启动过程中会精确记录关键结算的时间戳和耗时,并将其写入只读属性ro.boottime.*中。

    属性 含义 单位 说明
    ro.boottime.init 第一阶段 init 启动的时间点 ns 从 CLOCK_BOOTTIME 开始到 init 进程开始执行的时间
    ro.boottime.init.first_stage 第一阶段 init 执行耗时 ns 通常指 ramdisk 中的 init 执行时间(如设备树解析、挂载 /dev 等)
    ro.boottime.init.selinux SELinux 策略加载与转换耗时 ns 包括 load_policyrestorecon 等操作
    ro.boottime.init.modules 内核模块加载耗时 ms init 执行 insmod 或 modprobe 加载 .ko 文件的总时间
    ro.boottime.init.cold_boot_wait 等待 ueventd 完成冷启动设备发现的耗时 ns init 等待 ueventd 发出 coldboot_done 事件的时间


    网站公告

    今日签到

    点亮在社区的每一天
    去签到