开启内核对模块的支持
在编译内核时确保开启加载模块支持。
Loadable module support --->
[*] Enable loadable module support
[*] Module unloading
[ ] Module versioning support (EXPERIMENTAL)
[*] Automatic kernel module loading
勾选如上选项,重新编译安装内核。
Hello module
首先确保运行的内核和源代码版本一致。
进入linux源码目录drivers/misc/,创建文件mymodule.c, 代码如下
#include <linux/module.h>
#include <linux/config.h>
#include <linux/init.h>
static int __init mymodule_init(void)
{
printk ("Hello module!\n");
return 0;
}
static void __exit mymodule_exit(void)
{
printk ("Unloading my module.\n");
return;
}
module_init(mymodule_init);
module_exit(mymodule_exit);
MODULE_LICENSE("GPL");
然后在同一个目录下的Makefile文件追加一行
obj-m += mymodule.o
make -C <top directory of your kernel source> SUBDIRS=$PWD modules
insmod ./mymodule.ko
成功会打印出 Hello module!
移除
rmmod mymodule
模块和内核
现在来用模块做一些有意思的事。
有一个关键是模块只能访问内核导出的函数和变量。示例如下:
在内核kernel/prink/printk.c中添加全局变量
int my_variable = 0;
重新编译并重启内核
在mymodule_init中添加如下代码:
extern int my_variable;
printk ("my_variable is %d\n", my_variable);
my_variable++;
重现编译并加载模块
<span style="font-family: Arial, Helvetica, sans-serif;">这次出现了错误信息 insmod: error inserting './mymodule.ko': -1 Unknown symbol in module</span>
它的意思是内核不允许模块访问变量, 当模块加载的时,它查找函数和变量的外部引用,my_variable变量一定是在内核中,只是没有找到。
在prinkf.c my_variable下添加导出符号代码
EXPORT_SYMBOL(my_variable);
问题解决。
加载模块
my_variable is 0
Hello module!
# rmmod mymodule && insmod ./mymodule.ko
打印:
Unloading my module.
my_variable is 1
Hello module!
模块可以传参(不详细介绍)
# insmod module.ko [param1=value param2=value ...]
让模块支持中断
未完成