假设以个人架设的linux主机为例:当你按下电源键之后,计算机硬件会主动读取BIOS来加载硬件信息及进行硬件系统的自我测试,之后系统会主动读取系统第一个可启动的设备,此时就可以读入引导装载程序了。
引导程序可以指定使用哪个内核文件来启动,并实际加载内核到内存中解压缩与执行,此时内核就能够开始在内存内活动,并检测所有硬件信息,与加载适当的驱动程序来使这部主机开始运行,等到内核检测硬件与加载驱动程序之后就可以启动系统了。
linux系统的启动流程如下:
1、 加载BIOS的硬件信息与进行自我测试,并依据设置取得第一个可启动的设备。
boot Sequence:按次序查找各引导设备,第一个有引导程序的设备即为本地启用要用到的设备 (BIOS)
2、 读取执行第一个启动设备内MBR的Bootloader(grub)
Boot Loader的功能:要认识操作系统的文件格式,并根据这个加载内核到内存中去执行。
MBR是整个硬盘的第一个扇区内的一个块,充其量整个大小也有446,要加载boot的分区的驱动程序,ll -h `locate *ext4.ko`可以看到驱动程序有631k,因此446个字节根本装不下,不能加载驱动程序,因此linux将boot loader的程序代码执行与设置分为两个阶段:
阶段1、446个字节,不属于任何一个分区,他是硬盘上面第一个扇区,也没有文件系统,不需要驱动,
阶段1.5、位于第一个扇区后面的扇区,用于存放/boot分区的文件系统的驱动程序,因为/boot是被ext4格式化的,因此需要驱动程序,才能该分区,/boot/grub/*,可以看到1.5阶段的一些文件(备份使用)(fdisk -l 可以看到分区是从第一个柱面开始分的,所以还有0柱面8M的空间,用于存放这些数据,所以空间非常充裕 hexdump -C -n 15000 /dev/sda)。
阶段2、挂载/boot目录,加载内核文件,加载虚拟文件系统,挂载根文件系统,就是第三步所实现的功能,2st及内核等通常放置于一个基本磁盘分区(非raid,非lvs等/boot目录可以单独分区,如果想把根做成raid等非基本磁盘分区)。
grub功能:提供一个菜单,允许用户选择要启动的系统或不同的内核版本,把用户选定的内核版本装载到RAM中的特定空间中,解压,展开,而后把系统控制权移交给内核
3、 依据Bootloader的设置加载Kernel文件到内存中,Kernel会开始检测硬件与加载驱动程序(此时接管bios工作)。
内核文件:/boot/vmlinuz-2.6.32-642.el6.x86_64
驱动程序:/lib/modules/
该文件存在磁盘上,内核需要加载磁盘驱动,才能挂载根目录,访问驱动程序,所以此时根根本无法挂载,因此就需要一个虚拟文件系统文件
虚拟文件系统文件:/boot/initramfs-2.6.32-642.el6.x86_64.img
在内存中解压成一个伪根文件系统,内核借此加载适当的驱动程序,最总释放虚拟文件系统,并挂载实际根目录文件系统。
通过/bootloader加载到内存中,然后在内存中仿真成一个根目录,且此仿真在内存中的文件系统能够提供一个可执行程序,通过该程序来加载启动过程中所最需要的驱动程序 (USB,raid,lv,scsi等),等载入完成之后,内核就能识别真正的根了,然后进程根切换,切换完成后,调用/sbin/init来开始后续的正常启动流程。
该文件的查看方法:有file initramfs-2.6.32-642.el6.x86_64.img可以看到该文件是压缩文件因此:
1、mv initramfs-2.6.32-642.el6.x86_64.img initramfs-2.6.32-642.el6.x86_64.img.gz
gzip -d initramfs-2.6.32-642.el6.x86_64.img.gz
cat initramfs-2.6.32-642.el6.x86_64.img | cpio -id
2、zcat initramfs-2.6.32-642.el6.x86_64.img | cpio -id
该文件删除后的恢复方法:
1、救援模式
2、chroot /mnt/sysimage 切换根 救援模式的工具比较少 因此切换到根
3、mkinitrd /boot/initramfs-`uname -r`.img `uname -r` 此操作要在/boot目录下运行
4、exit;exit;reboot
4、 在硬件驱动成功后,Kernel会主动调用init进程,而init进程会取得run-level信息
Init:准备软件执行环境,包括系统主机名,网络设置,文件系统格式及其他服务的启动等。
配置文件:/etc/inittab,在配置文件有一个重要的设置,就是默认run-level
5、 Init 执行/etc/rc.d/rc.sysinit文件来准备软件执行的操作环境,配合好整个系统(如网络,时区)
功能:
1、设置主机名:
2、设置欢迎信息
3、激活udey和selinux
4、挂载/etc/fstab文件中的定义的所有文件系统
5、检测根文件系统,并以读写方式重新挂载根文件系统
6、设置系统时钟;
7、根据/etc/sysctl.conf文件的设定,来设定内核参数;
8、激活lvm及软raid
9、激活swap设备
10、加载额外设备的驱动程序;
11、清理操作;
6、 启动核心的外挂模块(/etc/modprobe.conf)
用户加载自定义模块的驱动程序,通常该文件可以自行产生。
7、 Init运行runl-level的各个服务的启动(script方式)
运行级别:为了系统运行或维护的目的而设定的机制
0-6:7个级别
0:关机shutdown
1:单用户模式(single user),root用户,无需认证,维护模式
2、多用户模式(multi user),会启用网络功能,但不会启动NFS;维护模式
3、多用户模式(mutli suer),完全功能模式;文本界面;
4、预留级别:目前无特别适用目的,但习惯以同3界别使用;
5、多用户级别(multi user),完全功能模哦;
6、重启模式,reboot
centos 6中/etc/inittab设置的默认级别为:
id:5:initdefault:
其中:
id:runlevels:action:process
id:一个任务的标识符
runlevels:在哪些级别下启用此任务;
action:在什么条件下启动此任务;
process:任务
action:
wait:等待切换至此任务所在的级别时执行一次;
respawn:一旦此任务终止时,就会重新启动
initdefault:设定默认运行级别;此时process会省略
sysinit:设定系统初始化方式,此处一般指定/etc/rc.d/rc.sysinit脚本;
启动对应级别下的服务(看默认级别,如果默认级别是5 就运行5下面的程序):
0:0:wait:/etc/rc.d/rc 0
。。。。
11:0:wait:/etc/rc.d/rc 5
12:0:wait:/etc/rc.d/rc 6
init要读取/etc/inittab配置文件完成初始化,该配置文件中有一堆的/etc/rc.d/rc 0,每个级别都有分别做了定义,他会等到你切换到该级别上来,切换过来后,init会到该级别下,将所有k开头的文件stop掉,所有s启动起来,这就是有些服务开机自动能启动的原因。Fl,rc5.d 目录下面的文件都是软连接,对应的都是/etc/init.d/下面对应的服务脚本,且配置文件在/etc/sysconfig/目录下,rc5.d目录下都是以k或者s打头的,后面跟的数字代表执行的顺序,且是以字符进行排序,表示执行的优先级。
当然我们也可以自定义/etc/inittab中的服务:
例如:
1、进入/etc/init.d下建立脚本
#!/bin/bash
#chkconfig:35 88 22
#description:test service
echo "How are you?"
2、chmod +x testrv
3、chkconfig –add testsrv
4、chkconfig –list testsrv
testrv 0:关闭 1:关闭 2:关闭 3:启用 4:启用 5:启用 6:关闭
5、service testsrv
6、chkconfig –del testsrv
注意:chkconfig [–level <levels>] [–type <type>] <name> <on|off|reset|resetpriorities>
8、 Init执行/etc/rc.d/rc.local文件
目录下中的/rc.local脚本,我们有任何启动时就要运行的脚本可以写到该文件中,在开机启动的时候就会自动被加载。
9、 Init执行终端机模拟程序mingetty来启动login进程,最后等待用户登录。
10、登录后开始以shell控制合主机。
POST –> Boot Sequence (BIOS) –> Boot Loader (MBR) –> kernel(ramdisk) –rootfs –> switchroot –> /sbin/init –>(/etc/init/*.conf,/etc/inittab) –> 设定默认运行级别 –> 运行系统初始化脚本 –> 关闭或启动对应级别下的服务 –> 启动终端
内核模块的增删查
目前内核都是具有可读取模块化驱动程序的功能,我们也可以理解为驱动程序,那么到底目前内核中加载了多少模块呢?
lsmod:查询内核中加载的模块 常配合grep使用
Module Size Used by nls_utf8 1455 1 fuse 79892 2 rfcomm 71079 4 sco 17493 2 bridge 85674 0 模块名称 模块大小 此模块是否被其他模块所使用
modinfo:查询模块信息
格式:modinfo [-adln] [module_name][filename]
选项:
-a:仅列出作者名称
-d:仅列出该modules的说明
-l:仅列出授权
-n:仅列出该模块的详细路径
insmod:加载内核模块(需要用户自行加载一个完整文件名的模块)
格式:insmod [/full/path/module_name][parameters]
insmod /lib/modules/$(uname -r)/kernel/fs/cifs/cifs.ko(必须要完整的文件名)
modprobe:加载内核模块
格式:modprobe [-lcfr] module_name
选项:
-c:列出目前系统所有模块
-l:列出目前在/lib/modules/`uname -r`/kernel 当中的所有模块完整文件名
-f:起那个会加载模块
-r:类似rmmod,就是删除某个模块
rmmod:删除模块
格式:rmmod [-fw] module_name
选项:
-f:强制将模块删除掉,不管是否使用
-w:若该模块正被使用,则rmmod会等待该模块被使用完毕后才删除他
原创文章,作者:Naruto,如若转载,请注明出处:http://www.178linux.com/45390