SysVinit (简体中文)

From ArchWiki
The printable version is no longer supported and may have rendering errors. Please update your browser bookmarks and please use the default browser print function instead.
翻译状态:本文是 SysVinit翻译。上次翻译日期:2012-09-20。如果英文版本有所更改,则您可以帮助同步翻译。

init是Linux内核加载后执行的第一个进程。Arch的默认的 init 程序是systemd-sysvcompat提供的/sbin/init(新安装的系统已经默认使用systemd) 或 sysvinitAUR.。本文中,init指sysvinit。

inittab文件位于/etc目录,是init的启动配置文件,其中指定了一些启动脚本、程序的路径,并指定在哪些运行级别执行它们。

注意: Arch's initscripts has been officially unsupported since 2012-11-04[1].

迁移到 Systemd

2012-10-13版安装介质开始,安装程序已经默认安装systemdsystemd-sysvcompat。本部分帮助还在使用sysvinitAUR 和 initscripts 的用户迁移到 systemd.

注意: 如果是在 VPS 中使用 Arch,请先阅读:Arch Linux VPS
  • 阅读该站,了解 systemd。
  • systemd 自己有一套日志(journal)系统,用于代替 syslog
  • 虽然 systemd 可以替换 cronacpidxinetd 等的部分功能。至少目前还可以继续使用这些服务,无需立即切换。
  • 交互式 initscripts 启动脚本在 systemd 中无法工作。

安装

  1. 官方软件仓库安装 systemd 并添加内核参数init=/usr/lib/systemd/systemd
  2. 使用 systemctl enable <服务名> 启用需要的服务(大致相当于以前 DAEMONS 数组的作用,新的服务名称参见 Daemons List (简体中文))。
  3. 重启系统,执行命令 cat /proc/1/comm,如果返回systemd,表示 systemd 已经正常启动。
  4. 确认主机名已经正确设置:hostnamectl set-hostname myhostname
  5. 删除 initscripts 和 sysvinit,并安装systemd-sysvcompat.
  6. (可选)删除init=/usr/lib/systemd/systemd内核参数,现在已经不需要它了。systemd-sysvcompat 软件包提供了一个软链接,使 systemd 成为默认 init。

附加信息

  • 如果内核参数中有 quiet,建议在一开始先去掉,以便调试。
  • 使用 systemd 的时候无需将用户加入特殊用户组(如sysdisklpnetworkvideoaudioopticalstoragescannerpower等等)。加入这些组反而会有问题,例如audio组会导致程序阻塞软件混声。每个 PAM 登录都拥有一个 logind 会话,它通过POSIX ACLs,赋予本地会话以声音设备访问权限、通过udisks挂载和卸载移动设备的权限等。
  • 阅读 Network configuration (简体中文),了解如何配置网络。

init、inittab 概览

init总是Linux的1号进程,并且是一切进程的父进程。通过pstree可以形象看出init在所有进程中所处的地位。

$ pstree -Ap
init(1)-+-acpid(3432)
        |-crond(3423)
        |-dbus-daemon(3469)
        |-gpm(3485)
        |-mylogin(3536)
        |-ngetty(3535)---login(3954)---zsh(4043)---pstree(4326)
        |-polkitd(4033)---{polkitd}(4035)
        |-syslog-ng(3413)---syslog-ng(3414)
        `-udevd(643)-+-udevd(3194)
                     `-udevd(3218)

除了系统初始化,init还负责重启、关机、单用户恢复模式。为了支持上述操作,inittab把条目分到不同的运行级别(runlevel)中去。Arch使用以下运行级别:0——关机,1(又叫S)——单用户模式,3——普通的多用户模式,5——X使用,6——重启。其他发行版可能有所不同,但0、1、6级别是通用的。

运行时,init检查inittab并进行适当的操作。inittab中的启动项目格式如下:

id:runlevels:action:process

id是项目独一无二的标识符(但只是个名称,对init没任何作用);runlevels是一串无分隔字符串,设置运行级别;当init进入了指定的runlevels,执行action;如果顺利,执行process。某些特殊的action会忽略runlevels,使用特殊的匹配方法。下一节有更详细的介绍。

调整运行级别

通过启动加载器

想要改变系统启动时的运行级别,只需要添加想要的运行级别 n 到启动加载器的内核参数。这通常的应用是 #inittab。要启动到需要的运行级别,将号码加入 内核参数 (例如 3 则启动要运行级别 3)。

运行级别追加到最后,这样内核就知道用哪个运行级别启动。想要使用另一个 init 程序(如 systemd),添加init=/usr/lib/systemd/systemd或者类似的命令到内核行。

注意: 如果你使用 sysvinit 之外的 init 程序,运行级别参数可能被忽略。

启动之后

系统启动后,可以调用telinit n通知init切换到运行级别n。然后init读取inittab,并做出当前运行级别到新的运行级别需要的改变——杀死新级别中没有的进程,执行旧级别未执行过的操作。两个级别共有的进程此时都会保留不动。杀死进程的过程有些复杂,技术信息参见init的manpage。

init不会监视inittab的改动,需要执行telinit应用更改。telinit q 命令只应用inittab而不会修改运行级别。

inittab

这一部分将探究inittab中的常见项目,之后会给出几个inittab项目的实例。叙述顺序按照Arch默认的inittab。

警告: 重启之前,务必使用 telinit q 测试修改过的 /etc/inittab,任何小小的语法错误都将导致系统无法启动。

默认运行级别

默认运行级别为3。如果想要设置默认运行级别为5(通常X使用的级别),添加下面一行内容:

id:5:initdefault:

主启动脚本

下面几行描述了主启动脚本:

rc::sysinit:/etc/rc.sysinit
rs:S1:wait:/etc/rc.single
rm:2345:wait:/etc/rc.multi
rh:06:wait:/etc/rc.shutdown

单用户启动

有时,因为重要文件丢失、文件系统损坏或硬件问题,内核可能启动失败。此时init可能自动进入单用户模式,此模式只允许使用root登陆,使用/sbin/sulogin(而非/sbin/login)控制login进程。也可以在 GRUB, LILOsyslinux 启动项添加S参数进入单用户模式。如果不想使用sulogin,可以在这里设置:

su:S:wait:/sbin/sulogin -p

终端初始化

该部分是初始化虚拟终端的关键。默认设置会在tty1-6开启6个getty,显示终端登陆提示。另见:openvt, chvt,stty,ioctl。

c1:234:respawn:/sbin/agetty 9600 tty1 xterm-color
c5:5:respawn:/sbin/agetty 57600 tty2 xterm-256color

Ctrl-Alt-Del

以下内容定义按下Ctrl+Alt+Del组合键时进行的操作:

ca::ctrlaltdel:/sbin/shutdown -t3 -r now

X 程序

如果不怕麻烦,在inittab中启动各种程序都是可以的。以下内容示范了如何设置系统进入运行级别5时启动登陆管理器 SLiM

x:5:respawn:/usr/bin/slim >/dev/null 2>&1
#x:5:respawn:/usr/bin/xdm -nodaemon -confi /etc/X11/xdm/archlinux/xdm-config

电源检测脚本

init可以根据UPS设备状态执行相应进程,示例如下:

pf::powerfail:/sbin/shutdown -f -h +2 "Power Failure; System Shutting Down"
pr:12345:powerokwait:/sbin/shutdown -c "Power Restored; Shutdown Cancelled"

自定义键盘请求

类似Ctrl+Alt+Del,下面的内容添加了按下特定组合键时执行命令的功能:

kb::kbrequest:/usr/bin/wall "Keyboard Request -- edit /etc/inittab to customize"

触发 kbrequest

使用root用户,可以通过向init发送WINCH信号触发kbrequest。对于上述例子,命令:

kill -WINCH 1

会导致wall命令执行,向所有用户发送信息:

Broadcast message from root@askapachehost (console) (Wed Oct 27 14:02:26 2010):  
Keyboard Request -- edit /etc/inittab to customize

另见

外部链接