CentOS6系统启动流程
1. Linux组成
Linux: kernel+rootfs
- 内核(kernel)的基本功能:
进程管理、内存管理、网络管理、驱动程序、文件系统、安全功能 rootfs:程序和glibc
库:函数集合, function, 调用接口(头文件负责描述)
- 过程调用:procedure,无返回值
- 函数调用:function
- 程序:二进制执行文件
- 查看:ldd可以查看可执行文件所调用的库
内核设计流派:
单内核(monolithic kernel):Linux
把所有功能集成于同一个程序微内核(micro kernel):Windows, Solaris
每种功能使用一个单独子系统实现
- 内核(kernel)的基本功能:
Linux内核
特点:
- 支持模块化:.ko(kernel object内核对象)
如:文件系统,硬件驱动,网络协议等 - 支持内核模块的动态装载和卸载
- 支持模块化:.ko(kernel object内核对象)
组成部分:
核心文件
命令ll /boot/ 查看目录下文件,其中2个相当重要的/boot/vmlinuz-VERSION-release
- 放置核心工具内容,其他相对不是核心的东西分门别类放在/lib/modules下个各种模块中,模块化优点是易于维护。
- 安装之前已经确定好的文件,日期早与系统安装时间
- 文件破坏后修复方法
1. 进入救援模式,方法见后面实验,这里不重复了。
2. 创建一个挂载点/mnt/cdrom,挂载光盘
3. mount /dev/sr0 /mnt/cdrom
4. 进入光盘找到对应文件/mnt/cdrom/isolinux/vmlinuz
5. 拷贝到原系统误删目录下,/mnt/sysimage/boot/vmlinuz-`uname -r`
6. 确认文件是否拷贝
- ramdisk:辅助的伪根系统,使用缓冲和缓存来加速对磁盘上的文件访问,并加载相应的硬件驱动
- CentOS 5: /boot/initrd-VERSION-release.img
initrd解释为init-ramdisk,模拟磁盘
生成工具:mkinitrd - CentOS 6,7: /boot/initramfs-VERSION-release.img
initramfs解释为init-ramfilesystem,模拟分区,效率高于模拟磁盘
生成工具:mkinitrd, dracut
- CentOS 5: /boot/initrd-VERSION-release.img
- 模块文件:/lib/modules/VERSION-release
实验:删除伪根系统文件,然后修复
- 删除initramfs-3.10.0-862.el7.x86_64.img
- 重启系统,在载入画面按一次ESC键,选择CD加载
- 选择Rescue installed system
进入系统后会让选择语言,和键盘,都选英语
网络不用配,选择no
系统挂载信息,这里选择Continue,如果选择read-only则只能看,skip为忽略,也就不挂载,advanced为高级选项,一般用不到。
系统会去找根目录,找到后就会挂载到/mnt/sysimage下,会提示可以使用chroot /mnt/sysimage来切换到原系统根上
选择shell
df查看原根目录挂载点
- 切换到原根目录
命令chroot /mnt/sysimage/ - 进入到被破坏文件的目录下/boot
输入:mkinitrd /boot/initramfs-$(uname -r).img $(uname -r)
或者:dracut /boot/initramfs-$(uname -r).img $(uname -r)
- 确认文件已经生成
ls
- 输入两次eixt
- 选择重启
2. CentOS6启动流程
加电自检
加载BIOS的硬件信息,获取第一个启动设备- POST:Power-On-Self-Test,加电自检,是BIOS功能的一个主要部分。负责完成对CPU、主板、内存、硬盘子系统、显示子系统、串并行接口、键盘等硬件情况的检测
- ROM:BIOS,Basic Input and Output System,保存着有关计算机系统最重要的基本输入输出程序,系统信息设置、开机加电自检程序和系统启动自举程序等
- RAM:CMOS互补金属氧化物半导体,保存各项参数的设定
MBR引导
- 按次序查找引导设备,第一个有引导程序的设备为本次启动设备,读取MBR的引导,把用户选定的内核装载到内存中的特定空间中,解压、展开,并把系统控制权移交给内核
- MBR读取第一扇区的前446个字节去尝试引导操作系统
446: bootloader;64: 分区表; 2: 55AA
GRUB:GRand Unified Bbootloader 引导加载器
- 在MBR引导完成后,开始寻找各操作系统的引导程序,Linux使用的为GRUB加载程序
GRUB有2部分内容,都不能破坏,不然系统无法启动
- primary boot loader : 1st stage,1.5 stage
- 1st stage在MBR前446个字节中,不属于任何分区,里面指针指向2阶段文件
- 1.5 stage在MBR后面的27个sectors
secondary boot loader :2nd stage
文件存放在/boot/grub ,新安装系统grub.conf和图片文件,只要修复一次后,就会将1、1.5、2阶段需要的文件系统驱动文件备份到此目录下,所以关键文件为grub.conf,如下所示#boot=/dev/sda 1:default=0 <==定义启动优先级 2:timeout=5 <==等待倒计时,不指定则按默认启动 3:splashimage=(hd0,0)/grub/splash.xpm.gz <==背景图片 4:hiddenmenu 5:title CentOS 6 (2.6.32-754.el6.x86_64) <==菜单名字,可以修改,也可以再增加几栏 6: root (hd0,0) <==boot分区所在,修复命令中就是这样表示 7: kernel /vmlinuz-2.6.32-754.el6.x86_64 ro root=UUID=bc5e1202-11ed-42d4-bbec-16c1d408f809 rd_NO_LUKS rd_NO_LVM LANG=en_US.UTF-8 rd_NO_MD SYSFONT=latarcyrheb-sun16 crashkernel=auto KEYBOARDTYPE=pc KEYTABLE=us rd_NO_DM rhgb quiet 8: initrd /initramfs-2.6.32-754.el6.x86_64.img
- default:定义启动优先级,例如第5-8行为第一个菜单序号为(0),如果在后再增加一个菜单序号为(1),启动顺序有小到大
- splashimage:菜单栏背景图,图片在/boot/grub/下,后缀为xpm.gz,可修改
- 找到素材,像素大小640/480,导入Linux中
- 安装工具
yum install ImageMagick
- -resize调整大小,-colors定义颜色,原图片,生成格式
#convert -resize 640x480 -colors 14 a.png a.xpm
- 压缩图片
gzip a.xpm
- 将图片放在/boot/grub/目录中
- 修改文件中图片项,示例修改结果如下
splashimage=(hd0,0)/grub/a.xpm.gz
- hiddenmenu:隐藏菜单,删除后不需要敲任意键,直接显示菜单
password: 可在hiddenmenu上添加passwor项,可以给菜单设置密码,需要操作菜单需要输入密码,防止单人模式破解密码
- 明文密码格式为:
password 123456
- 加密密码格式:
password --encrypted $6$9xD......HrS7qQ7phXD0
- 生成加密口令grub-crypt
- 示例
`# grub-crypt
Password: <==输入需要创建的密码
Retype password: <==确认
6 6 <script type="math/tex" id="MathJax-Element-1">6</script>9xD….HrS7qQ7phXD0 <==生成的加密口令
- 明文密码格式为:
第7行kernel最后面的两个参数
- rhgb:定义了启动界面为图形界面,删除后为字符界面
- quiet:隐藏内核的启动过程,删除后会显示处理过程
- primary boot loader : 1st stage,1.5 stage
加载内核
加载核心操作系统的核心信息,核心开始解压缩,并尝试驱动所有的硬件设备,以只读方式挂载根文件系统- 首先加载/boot/vmlinuz-2.6.32-754.el6.x86_64
- 内核后会去找根目录,就需要辅助伪根程序 initramfs-2.6.32-754.el6.x86_64.img
- 找到根目录开始一项一项加载
核心执行init程序,并获取默认的运行信息
读取/etc/inittab文件,此文件定义了启动的默认模式,- init程序执行/etc/rc.d/rc.sysinit文件
- 运行相关的启动脚本,把环境初始化,如时钟,交换分区swap,逻辑卷、raid等都是在脚本中设置的
- 设置主机名
- 设置欢迎信息
- 激活udev和selinux
- 挂载/etc/fstab文件中定义的文件系统
- 检测根文件系统,并以读写方式重新挂载根文件系统
- 设置系统时钟
- 激活swap设备
- 根据/etc/sysctl.conf文件设置内核参数
- 激活lvm及software raid设备
- 加载额外设备的驱动程序
- 清理操作
- 根据etc/inittab文件定义的启动模式,运行各种服务/etc/rc.d/rc -> ../init.d脚本,比如SH、HTTP、MSQ数据库服务
- 运行相关的启动脚本,把环境初始化,如时钟,交换分区swap,逻辑卷、raid等都是在脚本中设置的
- init执行/etc/rc.d/rc.local
此脚本用于用户自定义开机启动程序,也就是说用户可以把需要开机启动的程序、命令写入这个文件 - 执行/bin/login程序,等待用户登录
- 登录之后开始以Shell控制主机
3. init程序
类型
- CentOS 5之前来自SysV: init读取配置文件
配置文件:/etc/inittab - CentOS 6 来自Upstart: init,
配置文件:/etc/inittab, /etc/init/*.conf - Systemd:systemd, CentOS 7
配置文件:/usr/lib/systemd/system;/etc/systemd/system
- CentOS 5之前来自SysV: init读取配置文件
运行级别
- 为系统运行或维护等目的而设定;0-6共7个级别
- 级别0:关机
- 级别1:单用户模式(root自动登录), single, 维护模式
- 级别2: 多用户模式,启动网络功能,但不会启动NFS;维护模式
- 级别3:多用户模式,正常模式;文本界面
- 级别4:预留级别;可同3级别
- 级别5:多用户模式,正常模式;图形界面
- 级别6:重启
- 默认级别:3, 5
- 切换级别:init #
- 查看级别:runlevel ; who -r
- 为系统运行或维护等目的而设定;0-6共7个级别
init初始化
CentOS6之前版本,读取其初始化文件:/etc/inittab- Default runlevel. The runlevels used by RHS are
初始运行级别(RUN LEVEL) 文件中对应行id:5:initdefault:
System initialization
系统初始化脚本 文件中对应行si::sysinit:/etc/rc.d/rc.sysinit
- rc.sysinit运行后,开始执行对应运行级别的脚本目录,也就是调用/etc/rc$runlevel.d/下的脚本,例如,定义级别为5,调用的就是
/etc/rc.d/rc5.d/
- /etc/rc.d/rc5.d/下都是以k或s开头的脚本,k为关闭服务,s为开启服务。此目录下的脚本都是软链接,指向/etc/init.d下的文件
- 先执行k系脚本,再执行s系脚本
设定需要开启的服务
- 命令:ntsysv
ntsysv --level=3
指定为模式3设定启动项,会进入一个点选菜单,*表示s系列,空表示k系列 - 命令:chkconfig
- 列出所有的系统服务
chkconfig --list
。 - 增加httpd服务至列表
chkconfig --add httpd
- 从列表删除httpd服务。
chkconfig --del httpd
- 设置atd在23级别为启动,on表示启动,off表示关闭。
chkconfig --level 23 atd on
- 设置atd在2、3、4、5级别为off
chkconfig atd off
- 列出所有的系统服务
- 命令:ntsysv
设置自编译服务
方法一
借鉴系统服务脚本格式,创建一个服务脚本满足start status restart stop等参数#!/bin/bash # chkconfig: 345 96 3 345表示在相应运行级别的状态,不加为开启,-345为关闭,只写-为所有运行级别关闭, 96为s后的序号,3为k后的序号,指定时查看/etc/rc.d文件序号是否被占用 #description: . /etc/init.d/functions case $1 in start) action "starting testsrv:" true ;; stop) action "stopping testsrv:" false ;; restart) action "stopping testsrv:" true action "stopping testsrv:" false ;; *) echo $"usage: so{start|stop|restart}" exit 2 esac
方法二将需要开机启动的服务放在/etc/rc.d/rc.local目录下
- rc.sysinit运行后,开始执行对应运行级别的脚本目录,也就是调用/etc/rc$runlevel.d/下的脚本,例如,定义级别为5,调用的就是
Trap CTRL-ALT-DELETE
- 按上述组合键会执行以下命令,防止误操作,可以注释掉
ca::ctrlaltdel:/sbin/shutdown -t3 -r now 在CentOS 6中此项设置在 /etc/init/control-alt-delete.conf 中
start on control-alt-delete exec /sbin/shutdown -r now "Control-Alt-Delete pressed"
- 按上述组合键会执行以下命令,防止误操作,可以注释掉
定义UPS电源终端恢复脚本
- 停电后提示语,多久关机
pf::powerfail:/sbin/shutdown -f -h +2 “Power Failure; System Shutting Down” - 恢复供电后, 提示语取消关机
-pr:12345:powerokwait:/sbin/shutdown -c “Power Restored; Shutdown Cancelled”
- 停电后提示语,多久关机
在虚拟控制台生成getty
# Run gettys in standard runlevels
1:2345:respawn:/sbin/mingetty tty1定义在运行级别5初始化xdm图形界面,如果改为3,则3位图形界面
# Run xdm in runlevel 5
x:5:respawn:/etc/X11/prefdm -nodaemon
- Default runlevel. The runlevels used by RHS are
实验1:将默认模式设为6,循环重启,然后修复
- 实验环境CentOS6,将默认运行模式设置为6
vim /etc/inittab
id:6:initdefault: - 重启系统,在倒计时界面输入任意键如下图所示,输入a
- 在光标后输入3或5,对应运行级别,就会跳过inittab文件,直接按输入模式启动
- 启动后,将文件改回3或5
- 实验环境CentOS6,将默认运行模式设置为6
实验2:centos6破解口令
- 重新启动时,在倒计时画面输入任意键,同上例画面,输入a
- 同上例,输入1或s或S或single,进入单用户模式
- 进入即为root身份,输入passwd,创建新密码
- 重启,或者切换模式到3或5即可
4. xinetd管理的服务
Linux根据守护进的启动和管理,分为独立启动守护进程和超级守护进程两类
- 独立启动守护进程
进程启动后常驻内存,占用系统资源,一直处于启动状态,响应速度快 超级守护进程
- 早期的超级守护进程为inetd,非独立服务名称会以in.telnetd形式出现,就是保留inetd的含义
- 系统启动时由守护进程xinetd来复制管理一下进程,当用户发出请求时,需要首先被xinetd代理,再去启动服务。这种不需要常开的进程叫做瞬态(Transient)服务或非独立服务,由xinetd管理,也就只有超级守护进程占用系统资源。
具体表现为如下所示
# chkconfig --list NetworkManager 0:off 1:off 2:on 3:on 4:on 5:on 6:off ...... xinetd based services: <==超级守护进程 chargen-dgram: off <==非独立进程 chargen-stream: off daytime-dgram: off daytime-stream: off ...... telnet: off
如上所示,非独立服务处于off状态时,是不能被xinetd激活的,需要使其处于on状态,以telnet服务为例:改变其状态
- 使用命令
chkconfig telnet on
修改配置文件
目录/etc/xinetd.d/,其下对应的就是xinetd管理的非独立服务# vim /etc/xinetd.d/telnet ...... disable = yes <==将此项改为no,表示处于on状态
非独立服务在运行级别中的开启状态,与超级守护进程相同
例如:
xinetd 0:off 1:off 2:off 3:on 4:on 5:on 6:off
独立服务进程将继承这种设置
telnet 0:off 1:off 2:off 3:on 4:on 5:on 6:off配置文件
- 主配置文件,其设置将由所有服务继承
/etc/xinetd.conf - 非独立服务配置文件
/etc/xinetd.d/
- 主配置文件,其设置将由所有服务继承
- 使用命令
- 独立启动守护进程
5. GRUB各阶段修复实验
以下实验需要关闭防火墙及selinux
关闭selinux
vim /etc/sysconfig/selinux <==编辑此文件
# disabled - No SELinux policy is loaded.
SELINUX=enforcing <==修改为disabled
5.1 GRUB第一阶段实验
- 方法一
1、 将第一个扇区前446个字节删除,也就是没有MBR引导以及GRUB第一阶段
2、 备份第一扇区的446个字节
# dd if=/dev/sda of=/root/grbu1 bs=1 count=446
3: GRUB一阶段破坏后,重新启动如下图所示,系统判断此硬盘不具有启动功能,会去尝试找别的设备,例如光盘,U盘,网络等
4: 重新启动进入救援模式(前文有具体步骤)
5: 将备份的文件读入到第一扇区
dd if=/mnt/sysimage/root/grbu1 of =/dev/sda
6: 重启系统,出现如下倒计时画面,说明grub第一阶段正常
- 方法二:
1、进入救援模式
2、先切根到原始目录
chroot /mnt/sysimage/
3、 使用命令本地命令
grub-install /dev/sda
4、多敲几次sync
5、重新启动
- 方法三:命令grub,此方法依赖于/boot/grub/下的备份文件,如果文件丢失,命令出错
交互式命令grub,适用于误删后没有重启,救援模式执行,退出之前敲几次sync,保证数据写入磁盘。
1. grub> root (hd0,0) <==根目录所在,在一阶段系统认为/boot/为根,hd0表示第一个磁盘,0表示第一个分区
root (hd0,0)
Filesystem type is ext2fs, partition type 0x83
2. grub> setup (hd0) <==将GRUB装在第一个磁盘,相当于grub-install /dev/sda
setup (hd0)
Checking if "/boot/grub/stage1" exists... no
Checking if "/grub/stage1" exists... yes
Checking if "/grub/stage2" exists... yes
Checking if "/grub/e2fs_stage1_5" exists... yes
Running "embed /grub/e2fs_stage1_5 (hd0)"... 27 sectors are embedded.
succeeded
Running "install /grub/stage1 (hd0) (hd0)1+27 p (hd0,0)/grub/stage2 /grub/grub.conf"... succeeded
Done.
3. grub> quit <==退出
quit
5.2 破坏GRUB1.5阶段,然后修复
1、破坏GRUB1.5阶段,也就是跳过前面512个字节,后面27个扇区范围内的数据
# dd if=/dev/zero of=/dev/sda bs=1 count=8000 seek=512
2、出现如下画面,系统认为一阶段正常,此设备可以正常启动,但是1.5阶段损坏,就会卡在这里
3、 主动启用光盘来引导,进入救援模式
4.、使用grub-install /dev/sda来修复
5、重启
5.3 破坏GRUB2阶段,然后修复
1、删除文件/boot/grub/grub.conf
2、重启出现如下画面,说明二阶段故障
3. 在画面grub处可以输入命令,也就是菜单栏按e弹出的引导顺序
kernel /vmlinuz-2.6.32-754.el6.x86_64 root=/dev/sda2
initrd /initramfs-2.6.32-754.el6.x86_64.img
5.4 实验:将/boot/grub/目录删除
1、删除目录
2、重启如下画面,表示目录下文件丢失
3、救援模式
chroot /mnt/sysimage/ <==切根
grub-install /dev/sda <==修复
4、修复后缺少grub.conf文件,手工添加一个
vim /boot/grub/grub.conf
default=0
timeout=3
title moli (hd0,0) <==这个可以随意指定,菜单栏名称
kernel /vmlinuz-2.6.32-754.el6.x86_64 root=/dev/sda2 <==内核文件 根目录路径
initrd /initramfs-2.6.32-754.el6.x86_64.img <==辅助伪根系统
5.5 实验:将/boot都删了
1、删除
2、故障画面同上
3、救援模式,切根
4、挂载光盘
5、拷贝内核文件
cp /mnt/isolinux/vmlinuz /boot/
6、在boot下生成initramfs.imgname -r
文件
mkinitrd /boot/initramfs-$(uname -r).img $(uname -r)
7、生成grub
grub-install /dev/sda
8、grub.conf文件,手工添加一个
vim /boot/grub/grub.conf
default=0
timeout=3
title moli (hd0,0) <==这个可以随意指定,菜单栏名称
kernel /vmlinuz-2.6.32-754.el6.x86_64 root=/dev/sda2 <==内核文件 根目录路径
initrd /initramfs-2.6.32-754.el6.x86_64.img <==辅助伪根系统
5.6 实验:删除/etc/fstab,/boot目录,挂载信息文件,然后修复
1、 重启进入救援模式,会有如下画面,找不到Linux分区,点击ok继续下去
2、进入救援模式后,输入blkid查看文件系统, fdisk -l /dev/sda1挨个查看大小,初步判断根目录存放在那个分区。
3、建一个空文件夹,将各分区分别挂载上去查看,找到根目录所在
1:mkdir /mnt/tmp
2:mount /dev/sdaq /mnt/tmp
3:ls /mnt/tmp
4、找到根目录后,在其下创建fstab文件,手动添加
vim /mnt/tmp/etc/fstab
/dev/sda1 / ext4 defaults 0 0
/dev/sda2 /boot ext4 defaults 0 0
/dev/sda3 /data ext4 defaults 0 0
/dev/sda5 swap swap defaults 0 0
5、 退出救援模式,重新进入让系统完成挂载
6、 切根,挂载光盘
mount dev/sr0 /mnt
7、安装内核包,包内包括内核和伪根系统
rpm -ivh /mnt/Packages/kernel-2.6.32-754.el6.x86_64.rpm --force
8、修复grub
grub-install /dev/sda
9、grub.conf文件,手工添加一个
5.7 实验:在逻辑卷分区的系统中,删除/etc/fstab,删除/boot目录,挂载信息文件,然后修复
1、前面操作同上
2、 进入救援模式后,判断根目录
3、找到lv_root所在目录,lvdisplay或lvscan查看逻辑卷状态,为不可用状态
4、激活卷组
vgchange -ay
5、激活后就可以挂载了,将根目录挂载到/mnt/tmp上
/mount /dev/Vo1Group/lv_root /mnt/tmp
6、创建fstab文件
/dev/VolGroup/lv_root / ext4 defalts 0 0
/dev/VolGroup/lv_home /home ext4
/dev/VolGroup/lv_swap /swap swap
/dev/sda1 /boot ext4 defalts 0 0
7、重新启动,光盘加载,启动救援模式,让系统挂载根目录
8、余下操作同上例
5.8 实验,删除init文件,修复
1、删除
rm -f /sbin/init
2、故障画面如下,卡在这里
3、重启、进入菜单画面,输入a键,输入init=/bin/bash
4、 以bash为启动程序,相当于系统的第一个进程
5、mount -o remount,rw / 重新挂载根为读写
6、mount /dev/sr0 /mnt 挂载光盘
7、rpm -ivh /mnt/Packages/upstart-0.6.5-17.el6.x86_64.rpm –force
8、sync几下,重启
方法二
1、救援模式
2、切根
3、挂光盘
4、安装
方法三
1、进入救援模式或者以bash为启动程序的画面
2、配置临时网络地址
3、找同版本其他主机拷贝/sbin/init
$scp -r 172.20.129.251:/sbin/init /sbin/
新安装系统不在目录中,修复后才集中在此目录下。其中1阶段和1.5阶段文件作用是备份修复用的,例如使用grub命令,调用的就是这些文件 grub-install不依赖这些文件
回顾一下启动过程
1. post加电自检
2. MBR引导
3. GRUB1、1.5、2阶段
4. GRUB2阶段读取grub.conf文件,记录内核文件去加载内核
5. 内核文件加载,尝试找操作系统根目录
6. 挂载操作系统的根需要驱动程序,读取initramfs文件
7. 运行第一个进程init
8. 读取inittab文件,定义默认的运行模式,例如模式3
9. 运行/etc/rc.d/rc.sysinit初始化脚本
10. 根据运行模式执行/etc/rc3.d下服务脚本
11. 运行/etc/rc.d/rc.local自定义服务脚本
12. 登录界面
在博客上看到的图形介绍启动流程,以下为链接
http://blog.51cto.com/zhang789/1851675