嵌入式Linux使用Busybox init进程启动过程分析

news/2024/11/20 4:29:26/
转自: http://blog.csdn.net/shanzhizi/article/details/39082495
一、Busybox
Busybo是一个遵循GPLv2协议的开源项目。 Busybox将众多的Linux命令集合进一个很小的可执行程序中,可以用来替换GNU fileutils shellutils等工具集。Busybox中各种命令与相应的GNU工具相比,所能提供的选项较少,但是能够满足一般应用。 Busybox为各种小型 的或者嵌入式系统提供了一个比较完完全的工具集。
Busybox在编写过程中对文件大小进行了优化,并考虑了系统资源有限的情况。与一般的GNU 工具集动辄几MB的体积相比,动态连接的Busybox只有几百KB,即使静态连接也只有1MB左右。有人将Busybox比喻成Linux工具中的瑞士 军刀,简单的说就是好像是Linux的一个大的工具集,包括了Linux中的大部分命令和工具。嵌入式根目录下的bin,sbin和usr目录以及 linuxc通常就是Busybox。Busybox会根据配置的不同自动的生成一些文件,但是有些根文件系统下的文件还是需要用户自己来建立。
二、Busybox启动流程分析
init进程是由内核启动的第一个也是惟一的一个用户进程,它根据配置文件决定启动哪些程序,比如执行某些脚本,启动shell,运行用户指定的程序等。 init进程是后续所有进程的发起者,比如init进程启动/bin/sh程序后,才能够在控制台上输入各种命令。
   init进程的执行程序通常是sbin/init,上面讲述的init进程的作用只不过是/sbin/init这个程序的功能。在嵌入式领域,通常使用 Busybox集成的init程序.嵌入式根目录下的bin,sbin和usr目录以及linuxc通常就是Busybox。
1、在kernel/init/main.c的init函数中有如下代码:
 if(execute_command)
 execve(execute_command,argv_init,envp_init);
 execve("/sbin/init",argv_init,envp_init);
bootloader会传给内核的main函数 init=/linuxrc这个参数,于是就会执行下面的这句
execute_command = "linuxrc",busybox中_install目录下的linuxrc是Busybox的一个软链接,指向/bin/busybox,而 /sbin/init也是/bin/busybox的符号链接,因此这个linxrc基本没有实际的意义只是一个连接作用。我们可以重写linuxrc, 添加自己的一些初始化的东西。这样就可以把Linux内核中的init程序和Busybox中的init程序结合起来了。
2、Busybox init进程启动流程
Busybox是目标板系统上执行的第一个应用程序,当调用Busybox它会执行Busybox自身的init进程。
 Busybox initt 程序对应的代码在init/init.c文件中。其对应的流程图如下:
busybox初始化流程图
其中与构建根文件系统关系密切的是控制台的初始化,对inittab文件的解释及执行。从图中我们可以 看出, Busybox init启动的第一个函数是int init_main(int argc UNUSED_PARAM, char **argv),在这里可以设置信号的处理函数,初始化控制台,最重要的是解析inittab中内容。
在init_main()函数中会调用parse_inittab(void)函数,parse_inittab(void)函数可以使用一些默认的配置,当/etc/inittab没有配置时。
static void parse_inittab(void)
{
#if ENABLE_FEATURE_USE_INITTAB
    char *token[4];
    parser_t *parser = config_open2("/etc/inittab", fopen_for_read);

    if (parser == NULL)
#endif
    {
        /* No inittab file -- set up some default behavior */
        /* Reboot on Ctrl-Alt-Del */
        new_init_action(CTRLALTDEL, "reboot", "");
        /* Umount all filesystems on halt/reboot */
        new_init_action(SHUTDOWN, "umount -a -r", "");
        /* Swapoff on halt/reboot */
        if (ENABLE_SWAPONOFF)
            new_init_action(SHUTDOWN, "swapoff -a", "");
        /* Prepare to restart init when a QUIT is received */
        new_init_action(RESTART, "init", "");
        /* Askfirst shell on tty1-4 */
        new_init_action(ASKFIRST, bb_default_login_shell, "");
//TODO: VC_1 instead of ""? "" is console -> ctty problems -> angry users

        new_init_action(ASKFIRST, bb_default_login_shell, VC_2);
        new_init_action(ASKFIRST, bb_default_login_shell, VC_3);
        new_init_action(ASKFIRST, bb_default_login_shell, VC_4);
        /* sysinit */
        new_init_action(SYSINIT, INIT_SCRIPT, "");
        return;
 }
..............   
}

    其中最重要的一个是其中,最重要的一个,就是 new_init_action(SYSINIT, INIT_SCRIPT, ""),也就决定了接下去初始化的脚本是INIT_SCRIPT所定义的值。这个宏的默认值是"/etc/init.d/rcS".

 
#define INITTAB "/etc/inittab"    /* inittab file location */
#ifndef INIT_SCRIPT
#define INIT_SCRIPT "/etc/init.d/rcS"    /* Default sysinit script. */
#endif

  1)下面是分析文件系统中/etc/init.d/rcS的内容,这是我的rcS文件中的内容。这个文件会在inittab中使用。在inittab后启动rcS.

#!/bin/sh 
PATH=/sbin:/bin:/usr/sbin:/usr/bin 
runlevel=S 
prevlevel=N 
umask 022 
export PATH runlevel prevlevel  //上面几句为启动环境设置必要的环境变量
echo "----------munt all----------------" 
mount -a  //加载文件/etc/fstab文件中的选项,
echo /sbin/mdev>/proc/sys/kernel/hotplug 
mdev -s  //在/dev 目录下建立必要的设备节点;
echo "***********************************************" 
echo "****************Studying ARM Embedded *********************
echo "Kernel version:linux-2.6.32.1" 
echo "Author frank" 
echo "Date:2010.4.19" 
echo "***********************************************
/bin/hostname -F /etc/sysconfig/HOSTNAME  //设置主机的名字

 

//下面这一句是设置内核的hotplug handler 为 mdev, 即当设备热插拔时,由 mdev 接收来自内核的消息并作出相应的回应, 比如挂载U盘。
echo /sbin/mdev>/proc/sys/kernel/hotplug

2)下面是inittab文件的分析:如果存在/etc/inittab文件,Busybox init程序解析它,然后按照它的指示各种子进程,否则使用默认的配置创建子进程

#etc/inittab
::sysinit:/etc/init.d/rcS    //作为系统初始化文件.
s3c2410_serial0::askfirst:-/bin/sh  在串口启动一个登录会话
::ctrlaltdel:/sbin/reboot  //作为init重启执行程序.
::shutdown:/bin/umount -a –r
   //告诉init在关机时运行umount命令卸载所有的文件系统,如果卸载失败,试图以只读方式重新挂载。

/etc/inittab 文件中每个条目用来定义一个子进程,并确定它的启动方法,格式如下 :
<id>:<runlevels>:<action>:<process>
例如:
ttySAC0:askfirst:-/bin/sh
(1)<id>:表示这个进程要使用的控制台(即标准输入、标准输出、标准错误设备)。如果省略,则使用与init进程一样的控制台。
(2)<runlevels>:对于Busybox init程序,这个字段滑意义,可以省略。
(3)<action>:表示init程序如何控制这个子进程,
(4)<process>: 要执行的程序,它可以是可执行程序,也可以是脚本
如果<process>:字段有"-"字符,表示这个程序被称为“交互的”。在/etc/inittab/文件的控制下,init进程的行为总结如下:
(1)在系统启动前期,init进程首先启动<action>为sysinit wait once的3类子进程。
(2)在系统正常运行期间,init程序首先启动,<action>为respawn askfirst的两类子进程,并监视它们,发现某个子进程退出时重新启动它。
(3) 在系统退出时,执行<action> 为shutdown restart ctrlaltdel的3类子进程之一或全部。
如果根文件系统中没有/etc/initab文件,Busybox init程序将使用如下默认的inittab条目。

             /etc/inittab文件中<action>字段的意义

Action 名称

执行条件

说明

Sysinit

系统启动后最先执行

只执行一次, init 进程等待它结束才继续执行其它动作

Wait

系统执行完 sysinit 进程后

只执行一次, init 进程等待它结束才继续执行其它动作

Once

系统执行完 wait 进程后

只执行一次 ,init 进程不等待它结束

Respawn

启动完 once 进程后

Init 进程监测发现子进程退出时,重新启动它

Askfirst

启动完 respawn 进程后

与 respawn 类似,不过 init 进程先输出“ Please press Enter to actvie this console ”,等用户输入驾车键之后才启动子进程

Shutdown

当系统关机时

即重启关闭系统命令时

Restart

Busybox 中配置了CONFIG_FEATURE_USE_INITTAB,并且 init 进程接收到 SIGHUP 信号时

先重新读取,解析 /etc/initab 文件,再执行 restart 程序

Ctrlatldel

按下 Ctr+Alt+del 组合键时

 

3)下面是etc/fstab文件内容,表示执行完“mount -a”命令后将挂载proc tmpfs等系统
#device mount-point type option dump fsck order
proc /proc proc defaults 0 0
temps /tmp rpoc defaults 0 0
none /tmp ramfs defaults 0 0
sysfs /sys sysfs defaults 0 0
mdev /dev ramfs defaults 0 0

4)/etc/profile文件 

这个文件是 sh 用的,当用户获得一个 shell 后, sh 就会根据这个文件配置用户的登陆环境,下面是我的profile 文件。

# Ash profile
# vim: syntax= sh
# No core file by defaults
# ulimit - S - c 0> / dev/ null 2> & 1
USER= "id -un" 
LOGNAME= $ USER
PS1= '[/u@/h=W]#' 
PATH= $ PATH
HOSTNAME= '/bin/hostname' 
export USER LOGNAME PS1 PATH

    其中PATH环境变量指定当用户键入一个命令时,sh寻找这个命令的路径。PS1指定sh提示符的格式。其它的 export 命令, alias 命令, busybox 里面的 ash 和 bash 非常相似 

这样, Busybox所需的基本的配置文件就完成了。这也是Busybox最基本的文件,当然还可以配置更多的文件,增强Busybox的功能。

http://www.ppmy.cn/news/650997.html

相关文章

猿题库 iOS 客户端架构设计

转载自&#xff1a; 蓝晨钰的博客 序 猿题库是一个拥有数千万用户的创业公司&#xff0c;从2013年题库项目起步到2015年&#xff0c;团队保持了极高的生产效率&#xff0c;使我们的产品完成了五个大版本和数十个小版本的高速迭代。在如此快速的开发过程中&#xff0c;如何保证…

智能mp5 android系统,新Android智能MP5 蓝晨BM790改版上市

新Android智能MP5 蓝晨BM790改版上市 2011年03月02日 05:01作者&#xff1a;厂商投稿编辑&#xff1a;范源媛文章出处&#xff1a;泡泡网原创 分享 泡泡网MP3频道3月2日 当平板电脑袭卷全球&#xff0c;Android智能平台成为目前MID平板应用系统的第一大派系。蓝晨数码在2011年度…

大像素全景,如何让自己的VR全景变得具有高级感?

一个成功的VR全景作品&#xff0c;如果想要在商业领域上获得一定影响力&#xff0c;那么VR全景本身的质量就是关键&#xff0c;如何让自己的VR全景变得具有高级感呢&#xff1f; 从艺术表达手法上&#xff0c;航拍是对VR全景很好的诠释&#xff0c;通过VR全景航拍&#xff0c;人…

Axure教程—上传文件

本文介绍用Axure制作文件上传效果 预览 预览地址&#xff1a;https://6q4of2.axshare.com 功能 1、点击”文件上传“按钮&#xff0c;显示上传的文件 2、点击”删除“图片&#xff0c;显示提示”是否要删除“&#xff0c;点击”是“&#xff0c;删除数据&#xff0c;点击”否…

当产品进化遇见亿元福利,华帝携手人民日报为消费复苏添了一把火

这个五一黄金周&#xff0c;消费复苏的热火彻底被点燃。统计数据显示&#xff0c;2023年“五一”假期累计超过2.74亿人次出游&#xff0c;消费市场恢复到2019年同期水平。久违的“人间烟火气”再度回归。 除了旅游市场的火爆&#xff0c;同样助燃消费市场的还有全民“厨房焕新…

区块链生态发展

文章目录 前言以太坊的到来什么是图灵完备&#xff1f;什么是智能合约&#xff1f; 以太坊的应用去中心化应用 DApp代币发行 公有链&联盟链区块链应用总结 前言 前面的区块链文章有介绍区块链的诞生以及底层运行原理&#xff0c; 本文主要介绍一下区块链应用的发展&#x…

[Unity][疑难杂症]Mac电脑打开工程unity attempt to write a readonly database

报错的根本原因&#xff1a; 你Unity项目所在的硬盘&#xff0c;格式不是MacOS或者APFS格式&#xff0c;我的是ExFAT所以报这个错。 可能出现的问题&#xff1a; 1、删除unity项目中的c#之类的文件就会报错&#xff0c;并且强制退出 2、新项目压根打不开&#xff0c;在生成资源…

如何取消锁定计算机,如何取消解除计算机锁定窗口

方法1&#xff1a;方法/步骤&#xff1a;1&#xff0c;右击“桌面”&#xff0c;在弹出的右键菜单中选择“属性”项。2&#xff0c;在打开的“属性”窗口中&#xff0c;切换至“屏幕保护程序”选项卡&#xff0c;取消勾选“在恢复时使用保护密码”选项。3&#xff0c;接着点击“…