linux 模块机制

一、背景

linux内核框架庞大,如果把所有需要的功能都编译到linux内核中,会导致两个问题:

1、生成的内核非常大。

2、新增或删除功能需要重新编译内核。

linux为了解决上述问题,引入了模块机制,使得编译出的内核并不需要包含所有功能,而在这些功能需要被使用的时候,动态加载加载相应代码到内核中。

模块具有这样的特点:

1、模块本身不被编译入内核映像,从而控制住了内核大小。

2、模块一旦被加载,它就和内核中其它部分完全一样。

二、编译方法

object-y:编译进内核

object-m:编译成模块(xxx.ko)

三、模块加载方法

1、insmod moduleName.ko

     使用rmmod moduleName 进行卸载

2、modprobe 

    modprobe -r 进行卸载

modprobe比insmod 强大,它在加载模块时,会加载模块所依赖的其它模块;卸载时会卸载依赖的模块。

四、模块的构成

1、模块加载函数

(1)在模块加载时,模块的加载函数会被内核执行,完成本模块的相关的初始化工作,使用  module_init(funcName);进行声明。

(2)在内核代码中可以使用request_module()函数动态加载模块。

(3)内核加载函数一般以_ _init 标识。

         在linux中,所有标识为_ _init 的函数如果直接编译进内核,在链接的时候都会放在.init.text区段。

        #define   _ _init        _ _attribute_ _ ((_ _section_ _(".init.text")))  

       所有的_ _init函数在区段.initcall.init.中还保存了一份函数指针,在初始化时内核会通过这些函数指针调用这些_ _init函数,并在初始化完成后释放init区段(包括.init.text、.initcall.init等)的内存。

      另外,还可以定义初始化阶段需要的数据,使用_ _initdata进行标识,内核在初始化完成后,也可以释放他们占用的内存。

2、模块的下载函数

  (1)在模块卸载时,模块的卸载函数会被内核执行,完成与模块加载相反的工作,使用  module_exit(funcName);进行声明。

  (2)模块的下载函数一般以_ _exit进行标识。如果模块被直接编译进内核,卸载函数会被忽略,不被编入内核。这是因为模块被编入内核了,就不可能卸载了,所以卸载函数就没有必要存在了

3、模块许可证声明

     许可证声明描述内核模块的许可权限,如果不声明权限,模块加载时将收到内核被污染(Kernel Tainted)的警告。常用的LICENSSE有GPL、GPL v2、GPL and additional rights、Dual BSD/GPL、Dual MPL/GPL等,使用MODULE_LICENSE(LICENSE)进行声明

4、其它可选函数

MODULE_AUTHOR("XXX");-----------模块作者
MODULE_DESCRIPTION("XXXXXXX");----------模块描述


   


  • 1
    点赞
  • 8
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值