一、模块
1、什么是模块
模块(modules)是包含了linux内核核心部分以外的外围设备或外围功能,他们被封装成模块文
件,供Linux内核来动态的进行挂接和调用。
2、模块(modules)的位置:
1)/lib/modules
其中build/和source/目录是内核编译的相应的源代码文件存放的位置。
其他的目录是外围内容存放的目录
主要的文件存放在/kernel目录下
arch 对一些硬件平台方面支持的模块,例如CPU
crypto 对一些加密方面功能的模块
drivers 硬件方面的驱动,例如显卡、硬盘、硬件驱动器等
fs 文件系统驱动
lib 库的调用
net 网络设备、网络功能、网络协议、防火墙等
sound 声音系统方面
2)/boot/下的initrd-2.6.18-194.el5.img
3)*.ko
3、模块的管理
1)lsmod 查看当前系统模块的使用情况
Module 模块名称
Size 模块大小,单位是字节
Use by 该模块被其他多少个程序或模块所调用
2)模块之间是有依赖关系的
lsmod | grep lp
lp模块的加载依赖于parport_pc
3)手动加载或卸载模块
(1)手动卸载模块
rmmod 模块名称
remmod lp
(2)手动加载模块
insmod 模块的绝对路径或者存储位置
insmod /lib/modules/2.6.18-194.el5/kernel/drivers/char/lp.ko
注意事项:<1>模块的依赖关系
<2>模块文件的具体保存位置
查找命令modinfo
modinfo 模块名称
(3)测试模块之间的依赖关系
<1>首先找到相应模块的具体保存位置,并记录下来
modinfo parport_pc
modinfo ppdev
<2>rmmod parport
提示错误:该模块正在被其他的模块调用,所以不能卸载。因此需要按顺序卸载
<3>依次执行 rmmod lp
rmmod parport_pc
rmmod ppdev
rmmod parport
<4>执行lsmod | grep parport_pc 查看无显示,确认已经卸载
<5>手动加载insmod /lib/modules/2.6.18-194.el5/kernel/drivers/char/lp.ko
出现这种错误表示模块依赖性不完整,无法加载。
所以要按顺序安装
<6>由于目录较长,我们指定一个变量
MODULESDIR=/lib/modules/2.6.18-194.el5/kernel/*
<7>执行insmod $MODULESDIR/parport/parport.ko加载 parport模块,lsmod |grep parport检测安
装成功
<8>依次执行insmod $MODULESDIR/parport/parport_pc.ko
insmod $MODULESDIR/char/ppdev.ko
insmod $MODULESDIR/char/lp.ko
(4)实际中linux启动时,使用modprobe命令调用insmod的使用
<1>首先依次执行rmmod lp
rmmod ppdev
rmmod parport_pc
rmmod parport
卸载lp、ppdev、parport_pc、parport模块
<2>然后执行modprobe lp,自动将lp使用需要的依赖的模块加载。
modprobe命令不会还原模块挂接,而只是帮助用户自动解决模块挂接所产生的依赖关系
然后继续modprode ppdev 还原模块挂接
<3> modprobe自动挂接并解决模块依赖关系的原理:
在/lib/modules/2.6.18-194.el5/目录下有个特殊文件
modules.dep
vi modules.dep查看该文件的内容,文件内容是相应的模块以及相应模块依赖关系的声明
modprobe依据modules.dep文件描述的模块依赖关系实现自动加载相应的模块。
4、如果modprobe文件丢失、误删除等,
depmod命令会自动检测当前系统运行状态下系统各种模块的之间的依赖挂接,并且将相应模块之间
的依赖关系写入到对应的文件中,重新建立modules的一系列文件
当linux系统中安装新的硬件、驱动之后,执行depmod -a命令将新的硬件模块信息更新到modules
相应的记录文件中。
depmod -a 重建模块依赖关系
其他的文件保存的内容
vi modules.alias
alias别名是把相应的硬件的编码和名称做的一个别名的映射。
二、kernel modules挂接过程
1、kudzu 读取当前系统中相应硬件的信息。
参数
kudzu -p --class=network
每次开机kudzu会把所有的分类全部查一遍,然后将查找到内容与/etc/sysconfig/ hwconf文件的
内容进行比对。hwconf文件保存的是上一次系统启动之后发现的硬件信息。如果出现不同,发现新
的硬件时,则会读取相应硬件的支持列表(modules.alias文件),如果列表文件不存在,提示用
户,系统无法驱动该硬件;如果存在表示系统支持该硬件,然后查询驱动模块信息(modules.dep
文件);加载启用,将新硬件的内容更新到hwconf文件。
模块挂接过程总结:
vmlinuz(内核加载) --> initrd.img的模块 --> rc.sysinit
--> rc(启动服务) --> kudzu (发现硬件的信息) --> 通过比
对/etc/sysconfig/hwconf判断是否有新的硬件 --> 如果有新
硬件判断modules.alias文件记录的相应内容和对应硬件的识
别信息 --> modules.dep找到对应硬件的模块及相应依赖的模块信息 --> modprobe加载相应的模块 --> 模块加载成功之后,将新硬件的内容更新到/etc/sysconfig/hwconf并记录下来。
注意内核判断硬件类型,不是根据总线,而是根据相应硬件的信息。
2、加载多个同种类型的驱动的时候如何分辨:
vi /etc/modprobe.conf
定义了使用modprobe自动挂接模块时对模块下达的相应的参数,这些参数可以更改模块挂接的相应
不同的指令
alias eth1 vmxnet当我们挂接一个模块叫做vmnet的时候,把对应的硬件的名称alias成eth1来操
作,当我们对应eth1来操作时就是对应这个模块来操作
options snd-card-0 index=0添加参数
remove snd-ens1371{..} 当我们卸载这些模块挂接的时候同时执行{ }内的命令
在什么动作的时候同时执行那些命令
3、当系统不支持新硬件时,如何安装驱动,分两种情况:
1)内核中存在设备相应的驱动,我们只需要把该驱动加载
例如,/usr/src/kernels/2.6.18-194.el5-i686/fs/下的reiserfs文件系统,内核中有相应的驱
动,但是redhat内核中默认没有编译,所以不能使用。
如果需要使用,将reiserfs编译成模块的方式,在编译内核的时候,我们只需要编译需要的相应
模块。
首先,我们需要下载内核,
注意下载的内核版本与当前系统使用内核的版本必须一致,否则可能会导致编译的模块无法使用。
(1)usname �Cr查看当前系统使用的内核版本
(2)登陆ftp://ftp.redhat.com/找到相应的内核下载目录,下载相应内核
(3)清空/usr/src/redhat/SPECS和/SOURCES下的文件,确保这两个文件无数据,然后安装下载的
内核
(4)组装内核的源代码
(5)执行cd ..切换到上一层目录
(6)执行mv linux-2.6.18.i6868/ /usr/src/kernels/,将相应的源代码移动到/usr/src/kernels/
(7)make menuconfig进入linux内核的选项页面
Reiserfs support我们可以选择 * 编译到内核内部,但是选择 * 必须重新编译一次内核;所
以选择M编译成模块。
其子选项都是[]表示表示只能编译进内核内部,不能编译成模块,所以不选。
(8)现在执行make prepare
make modules_prepare
按照.config文件所记录的对linux内核相应选项,生成相应的makefile文件,在各个子目录和
子文件中生成makefile文件,按照makefile文件的描述编译出需要的模块。
(9)执行make M=fs/reiserfs/ 编译mudules模块
M是make命令下达的参数,编译mudules模块的目录位置
显示执行的操作都是[M],reiserfs的编译,
第二部部分创建的是我们需要的模块文件
(10)使用模块
reiserfs模块文件应该放在
/lib/modules/2.6.18-194.el5/kernel/fs/,当前显示没有reiserfs目录,因为系统内核编译
时未编译reiserfs模块。
<1>执行mkdir reiserfs创建,然后将编译的结果拷贝
到/lib/modules/2.6.18194.el5/kernel/fs/reiserfs/目录下
<2>执行insmod命令加载使用
lsmod | grep reiserfs显示模块正常挂接
现在通过编译内核指定模块增加内核功能的操作完成。
存在的缺陷:
<1>现在如果我们卸载reiserfs模块
<2>使用modprobe命令加载reiserfs模块,显示失败
原因:modprobe是依据modules.dep文件描述的模块依赖关系实现自动加载相应的模块。目前我们所做
的模块加载没有更新到modules.dep文件。所以当linux系统中安装新的硬件、驱动之后,执行
depmod -a命令将新的硬件模块信息更新到modules相应的记录文件中。
<3>执行depmod �Ca命令更新,然后执行modprobe reiserfs加载,显示成功
2)内核中没有指定驱动或功能模块,如何增加驱动或相应功能模块
(1)更新内核的目录内容
创建模块对应的目录,拷贝相应的文件,在程序的调用,直接读到对应的头文件或库文件或者其
他类型信息。
(2)更新/lib/modules的内容
编译出来的模块拷贝到/lib/modules,系统就可以调用手动加载最后不要忘记depmod -a更新