#include <linux/init.h> #include <linux/module.h> static int __init hello_init(void) { printk(KERN_EMERG "ha"); return 0; } static void hello_exit(void) { printk("le"); } module_init(hello_init); module_exit(hello_exit);
__init 表示初始化程序段 ,运行完后,系统就会回收内存空间
Makefile 文件
ifneq ($(KERNELRELEASE),) obj-m := hello.o else KDIR := /lib/modules/2.6.31-14-generic/build all : make -C $(KDIR) M=$(PWD) modules clean: rm -f *.ko *.o *.mod.c *.symvers endif
编译模块 #make
产生hell0.ko
添加hello 模块 # insmod hello.ko
查看hello 模块 #lsmod
删除hello 模块 #rmmod hello
注意:模块操作以root身份运行
MODULE_PARAM(name(名称),type(类型),perm(访问权限))
type常见值:bool int charp(字符串)
如int a = 1;
char *st;
module_param(a,int,S_IRUGO);
module_param(st,charp,S_IRUGO);
#include <linux/init.h> #include <linux/module.h> static char *name = "chen"; static int age = 30; module_param(age, int, S_IRUGO); module_param(name, charp, S_IRUGO); static int hello_init(void) { printk(KERN_EMERG "name:%s\n",name); printk(KERN_EMERG "age:%d\n",age); return 0; } static void hello_exit(void) { printk("le"); } module_init(hello_init); module_exit(hello_exit);
控制台优先级 决定模块里的printk()能否打印出来
vi /proc/sys/kernel/printk 可以查看 级别 控制台 默认级别 最小级别
#define KERN_EMERG 0/*紧急事件消息,系统崩溃之前提示,表示系统不可用*/ #define KERN_ALERT 1/*报告消息,表示必须立即采取措施*/ #define KERN_CRIT 2/*临界条件,通常涉及严重的硬件或软件操作失败*/ #define KERN_ERR 3/*错误条件,驱动程序常用KERN_ERR来报告硬件的错误*/ #define KERN_WARNING 4/*警告条件,对可能出现问题的情况进行警告*/ #define KERN_NOTICE 5/*正常但又重要的条件,用于提醒*/ #define KERN_INFO 6/*提示信息,如驱动程序启动时,打印硬件信息*/ #define KERN_DEBUG 7/*调试级别的消息*/
默认级别与printk级别决定 是否可以显示出来(纯字符模式等级低,可以到纯字符模式,查看打印效果,或者修改上面的问件)
ifneq ($(KERNELRELEASE),) obj-m := hello.o hello-objs := main.o add.o else KDIR := /lib/modules/2.6.31-14-generic/build all: make -C $(KDIR) M=$(PWD) modules clean: rm -f *.ko *.o *.mod.c *.symvers endif
// main.c #include <linux/module.h> #include <linux/init.h> MODULE_LICENSE("GPL"); MODULE_AUTHOR("chen"); MODULE_DESCRIPTION("a simple module"); extern int add(int a,int b); static int hello_init() { printk(KERN_EMERG "hello \n"); add(1,2); return 0; } static void hello_exit() { printk(KERN_EMERG "ok\n"); } module_init(hello_init); module_exit(hello_exit);
// add.c int add(int a,int b) { return a+b; }
// 模块 add.ko #include <linux/init.h> #include <linux/module.h> int add(int a,int b) { return a+b; } static int __init sym_init() { return 0; } static void __exit sym_exit() { } EXPORT_SYMBOL(add); //模块之间传递函数 module_init(sym_init); module_exit(sym_exit);
// 模块 hello.ko #include <linux/module.h> #include <linux/init.h> MODULE_LICENSE("GPL"); MODULE_AUTHOR("chen"); MODULE_DESCRIPTION("a simple module"); extern int add(int a,int b); static int __init hello_init() { printk(KERN_EMERG "hello \n"); int sum = add(1,2); return 0; } static void __exit hello_exit() { printk(KERN_EMERG "ok\n"); } module_init(hello_init); module_exit(hello_exit);
ifneq ($(KERNELRELEASE),) obj-m := hello.o ;这里分别写add.o和hello.o编译两个模块 else KDIR := /lib/modules/2.6.31-14-generic/build all: make -C $(KDIR) M=$(PWD) modules clean: rm -f *.ko *.o *.mod.c *.symvers endif