Openwrt启动之preinit流程分析
2015-06-05 22:42
369 查看
首先上代码 /etc/preinit文件
在/etc/preinit中首先初始化一些参数,这些参数其实是供hook链上函数调用的,这里不多解释。重要的是五个hook链(名字分别见代码),使用boot_hook_init进行初始化,需要用到/lib/function/boot.sh中的函数,代码如下:
这个函数中主要用到了export -n命令, export –n含义是删除指定的环境变量,但并非真正删除,只是在环境变量表中去除了,不能传递给子环境,变量本身还在,在本shell的其他函数中还可调用,相当于要本环境中声明了全局变量。
初始化后去/lib/preinit/目录下依次执行每一个文件,文件太多,且格式相同,我就以标准格式举例,如下:
前面可以写一个或多个函数,后面使用boot_hook_add加入到对应的hook链中,hook_name是链名,function_name是前面定义的函数。若有多个函数可使用多行boot_hook_add。下面上代码:
将所有函数挂到对应的hook链上后,使用boot_run_hook运行指定链上所有函数。
boot_hook_run中一个重要的函数如下:
下面是各个hook链及挂在上面的函数:
preinit_main_hook define_default_set_state do_ar71xx preinit_enable_reset_button preinit_set_mac_address set_preinit_iface init_tuxera_fs preinit_ip pi_indicate_preinit failsafe_wait run_failsafe_hook indicate_regular_preinit init_hotplug initramfs_test do_mount_root do_load_ath10k_board_bin restore_config load_qos_modules run_init
preinit_mount_root_hook check_for_mtd check_for_jffs2 do_mount_jffs2 do_mount_ubifs merge_overlay_hooks determine_external_root determine_extroot_sysupgrade external_root_pivot rootfs_pivot_jffs2 rootfs_pivot_ubifs do_mount_no_jffs2 do_make_flash_dev do_mount_no_mtd
failsafe_hook indicate_failsafe failsafe_netlogin failsafe_shell
preinit_essential_hook do_mount_procfs do_mount_sysfs do_mount_tmpfs choose_device_fs init_device_fs init_shm init_devpts do_mount_devpts choose_console init_console
preinit_mount_root_hook check_for_mtd check_for_jffs2 do_mount_jffs2 do_mount_ubifs merge_overlay_hooks determine_external_root determine_extroot_sysupgrade external_root_pivot rootfs_pivot_jffs2 rootfs_pivot_ubifs do_mount_no_jffs2
后面讲一下执行的最后一个函数,脚本如下:
run_init函数处于preinit_main_hook链上,这个函数的功能就是当完成preinit后执行/sbin/init,开始openwrt启动的下一流程。
#!/bin/sh # Copyright (C) 2006 OpenWrt.org # Copyright (C) 2010 Vertical Communications export PATH=/bin:/sbin:/usr/bin:/usr/sbin pi_ifname= pi_ip=192.168.1.1 pi_broadcast=192.168.1.255 pi_netmask=255.255.255.0 fs_failsafe_ifname= fs_failsafe_ip=192.168.1.1 fs_failsafe_broadcast=192.168.1.255 fs_failsafe_netmask=255.255.255.0 fs_failsafe_wait_timeout=2 pi_suppress_stderr="y" pi_init_suppress_stderr="y" pi_init_path="/bin:/sbin:/usr/bin:/usr/sbin" pi_init_cmd="/sbin/init" . /lib/functions.sh . /lib/functions/boot.sh boot_hook_init preinit_essential boot_hook_init preinit_main boot_hook_init failsafe boot_hook_init initramfs boot_hook_init preinit_mount_root for pi_source_file in /lib/preinit/*; do . $pi_source_file done boot_run_hook preinit_essential pi_mount_skip_next=false pi_jffs2_mount_success=false pi_failsafe_net_message=false boot_run_hook preinit_main
在/etc/preinit中首先初始化一些参数,这些参数其实是供hook链上函数调用的,这里不多解释。重要的是五个hook链(名字分别见代码),使用boot_hook_init进行初始化,需要用到/lib/function/boot.sh中的函数,代码如下:
boot_hook_init() { local hook="${1}_hook" #将链名后带hook后缀 export -n "PI_STACK_LIST=${PI_STACK_LIST:+$PI_STACK_LIST }$hook" export -n "$hook=" }
这个函数中主要用到了export -n命令, export –n含义是删除指定的环境变量,但并非真正删除,只是在环境变量表中去除了,不能传递给子环境,变量本身还在,在本shell的其他函数中还可调用,相当于要本环境中声明了全局变量。
初始化后去/lib/preinit/目录下依次执行每一个文件,文件太多,且格式相同,我就以标准格式举例,如下:
function_name() { #TODO } boot_hook_add hook_name function_name
前面可以写一个或多个函数,后面使用boot_hook_add加入到对应的hook链中,hook_name是链名,function_name是前面定义的函数。若有多个函数可使用多行boot_hook_add。下面上代码:
boot_hook_add() { local hook="${1}_hook${PI_HOOK_SPLICE:+_splice}" local func="${2}" [ -n "$func" ] && { local v; eval "v=\$$hook" export -n "$hook=${v:+$v }$func" #将每个func挂到各自的链上 } }
将所有函数挂到对应的hook链上后,使用boot_run_hook运行指定链上所有函数。
boot_run_hook() { local hook="$1" local func #下面调用boot_hook_shift,作用是依次执行链上的每一个函数,直到链末。不到链末时一直return 0,即true,当到链末时return 1,即false,while循环结束。 while boot_hook_shift "$hook" func; do local ran; eval "ran=\$PI_RAN_$func" [ -n "$ran" ] || { export -n "PI_RAN_$func=1" $func "$1" "$2" #执行函数 } done }
boot_hook_run中一个重要的函数如下:
boot_hook_shift() { local hook="${1}_hook" local rvar="${2}" local v; eval "v=\$$hook" #$hook指的是preinit_main_hook(例),而$$hook指的是preinit_main_hook链,其上包含了一串func函数 [ -n "$v" ] && { local first="${v%% *}" #每次取出链上的第一个函数 [ "$v" != "${v#* }" ] && \ export -n "$hook=${v#* }" || \ export -n "$hook=" export -n "$rvar=$first" #将第一个函数通过export –n传出,供调用它的函数使用 return 0 #这里很迷惑人,其实shell中函数最后会返回上一个执行命令的返回值(可使用echo $?),也可用return num指定(return只能出现在函数体内),返回值0表示真,即true,非0表示假,即false。 } return 1 }
下面是各个hook链及挂在上面的函数:
preinit_main_hook define_default_set_state do_ar71xx preinit_enable_reset_button preinit_set_mac_address set_preinit_iface init_tuxera_fs preinit_ip pi_indicate_preinit failsafe_wait run_failsafe_hook indicate_regular_preinit init_hotplug initramfs_test do_mount_root do_load_ath10k_board_bin restore_config load_qos_modules run_init
preinit_mount_root_hook check_for_mtd check_for_jffs2 do_mount_jffs2 do_mount_ubifs merge_overlay_hooks determine_external_root determine_extroot_sysupgrade external_root_pivot rootfs_pivot_jffs2 rootfs_pivot_ubifs do_mount_no_jffs2 do_make_flash_dev do_mount_no_mtd
failsafe_hook indicate_failsafe failsafe_netlogin failsafe_shell
preinit_essential_hook do_mount_procfs do_mount_sysfs do_mount_tmpfs choose_device_fs init_device_fs init_shm init_devpts do_mount_devpts choose_console init_console
preinit_mount_root_hook check_for_mtd check_for_jffs2 do_mount_jffs2 do_mount_ubifs merge_overlay_hooks determine_external_root determine_extroot_sysupgrade external_root_pivot rootfs_pivot_jffs2 rootfs_pivot_ubifs do_mount_no_jffs2
后面讲一下执行的最后一个函数,脚本如下:
#!/bin/sh # Copyright (C) 2006 OpenWrt.org # Copyright (C) 2010 Vertical Communications run_init() { preinit_echo "- init -" preinit_ip_deconfig if [ "$pi_init_suppress_stderr" = "y" ]; then exec env - PATH=$pi_init_path $pi_init_env $pi_init_cmd 2>&0 #$pi_init_cmd为/sbin/init else exec env - PATH=$pi_init_path $pi_init_env $pi_init_cmd fi } boot_hook_add preinit_main run_init
run_init函数处于preinit_main_hook链上,这个函数的功能就是当完成preinit后执行/sbin/init,开始openwrt启动的下一流程。
相关文章推荐
- UVa 242 Stamps and Envelope Size
- Centos 6x安装sys-log
- 『初学opencv』——求灰度图像灰度直方图
- linux yum命令详解以及查询当前哪些包需要更新,与更新命令。
- Linux常用命令-文件处理命令-链接命令
- Tomcat使用
- Linux用户管理(1)
- Linux最常用的20条命令
- linux内存管理源码分析 - 概述
- OpenSessionInViewFilter的配置
- 设置linux静态IP
- Linux 压缩与解压缩相关
- MacOS copy图标shell脚本
- Linux Page Cache机制
- Hadoop文件解压缩
- Linux终端下的命令
- [GUI] Linux中的图形管理
- CentOS 创建svn服务器
- Tomcat服务器自动加载监听程序(转载)
- Win7+CentOS 7双系统启动顺序修改方法.