最简单的模块
-
hello.c
#include <linux/module.h> int hello_init(void) { printk("Hello module init\n"); return 0; } void hello_exit(void) { printk("Hello module exit\n"); } module_init(hello_init); module_exit(hello_exit); MODULE_LICENSE("GPL");
-
Makefile
KDIR ?= /lib/modules/`uname -r`/build obj-m += hello.o module: make -C $(KDIR) M=$(PWD) modules clean: make -C $(KDIR) M=$(PWD) clean
-
运行
$ make $ sudo insmod hello.ko $ lsmod | grep hello $ cat /proc/modules | grep hello $ sudo rmmod hello $ dmesg | tail
获取主设备号
-
hello.c
#include <linux/module.h> #include <linux/fs.h> /* 设置主设备号, 0 则由系统创建 */ static int major = 0; static int hello_init(void) { int result; dev_t dev = MKDEV(major, 0); /* 配置主设备号 */ if(major) result = register_chrdev_region(dev, 1, "hello"); else { /* major 为 0 则动态创建 */ result = alloc_chrdev_region(&dev, 0, 1, "hello"); major = MAJOR(dev); } if(result < 0) { printk("register device error\n"); return result; } printk("register device major %d\n", major); return 0; } static void hello_exit(void) { dev_t dev = MKDEV(major, 0); unregister_chrdev_region(dev, 1); printk("unregister device major %d\n", major); } module_init(hello_init); module_exit(hello_exit); MODULE_LICENSE("GPL");
-
运行
$ make $ sudo insmod hello.ko $ dmesg | tail $ cat /proc/devices | grep hello $ sudo rmmod hello $ dmesg | tail $ cat /proc/devices | grep hello
添加字符设备
-
hello.c
#include <linux/module.h> #include <linux/fs.h> #include <linux/cdev.h> /* 填入希望绑定的主设备号, 0 则由系统决定 */ static int major = 0; static struct cdev mycdev; #define MIN(a, b) (((a) < (b)) ? (a) : (b)) static int hello_open(struct inode *node, struct file *file) { printk("open hello module\n"); return 0; } static ssize_t hello_read(struct file *file, char __user *buf, size_t size, loff_t *ofs) { int n, m; char say[] = "Hello World\n"; if(*ofs >= sizeof(say)) return 0; m = MIN(sizeof(say) - *ofs, size); n = copy_to_user(buf, say + *ofs, m); *ofs += m - n; return m - n; } static struct file_operations fops = { .owner = THIS_MODULE, .open = hello_open, .read = hello_read, }; static int hello_init(void) { int result; dev_t dev = MKDEV(major, 0); /* 配置主设备号 */ if(major) result = register_chrdev_region(dev, 1, "hello"); else { /* major 为 0 则动态创建 */ result = alloc_chrdev_region(&dev, 0, 1, "hello"); major = MAJOR(dev); } if(result < 0) { printk("register device error\n"); return result; } printk("register device major %d\n", major); /* 添加字符设备 */ cdev_init(&mycdev, &fops); mycdev.owner = THIS_MODULE; cdev_add(&mycdev, dev, 1); return 0; } static void hello_exit(void) { cdev_del(&mycdev); unregister_chrdev_region(MKDEV(major, 0), 1); printk("unregister device major %d\n", major); } module_init(hello_init); module_exit(hello_exit); MODULE_LICENSE("GPL");
-
运行
$ make $ sudo insmod hello.ko $ cat /proc/devices | grep hello # 填入获取的主设备号, 这里是 511 $ sudo mknod /dev/hello c 511 0 $ cat /dev/hello Hello World
网友评论