视频教程:Lecture 9 - 手动创建字符设备_哔哩哔哩_bilibili
#include <linux/module.h>
#include <linux/init.h>
#include <linux/fs.h>
#include <linux/cdev.h>
static dev_t dev_nr;
static struct cdev my_cdev;
static ssize_t my_read(struct file *f, char __user *u, size_t l, loff_t *o)
{
pr_info("hello_cdev - Read is called\n");
return 0;
}
static struct file_operations fops = {
.read = my_read
};
static int __init my_init(void)
{
int status;
#ifdef STATIC_DEVNR
dev_nr = STATIC_DEVNR;
status = register_chrdev_region(dev_nr, MINORMASK + 1, "hello_cdev");
#else
status = alloc_chrdev_region(&dev_nr, 0, MINORMASK + 1, "hello_cdev");
#endif
if (status) {
pr_err("hello_cdev - Error reserving the region of device numbers\n");
return status;
}
cdev_init(&my_cdev, &fops);
my_cdev.owner = THIS_MODULE;
status = cdev_add(&my_cdev, dev_nr, MINORMASK + 1);
if (status) {
pr_err("hello_cdev - Error adding cdev\n");
goto free_devnr;
}
pr_info("hello_cdev - Registered a character device for Major %d starting with Minor %d\n", MAJOR(dev_nr), MINOR(dev_nr));
return 0;
free_devnr:
unregister_chrdev_region(dev_nr, MINORMASK + 1);
return status;
}
static void __exit my_exit(void)
{
cdev_del(&my_cdev);
unregister_chrdev_region(dev_nr, MINORMASK + 1);
}
module_init(my_init);
module_exit(my_exit);
MODULE_LICENSE("GPL");
MODULE_AUTHOR("Johannes 4Linux");
MODULE_DESCRIPTION("A sample driver for manually registering a character device");
添加了头文件<linux/cdev.h>,
程序中调用的宏 :STATIC_DEVNR ,MINORMASK
手动注册字符设备:
status = register_chrdev_region(dev_nr, MINORMASK + 1, "hello_cdev");
register_chrdev_region 需要配置主/副设备号,这里用的 STATIC_DEVNR ,MINORMASK+1 来注册字符设备 hello_cdev
动态注册字符设备:
status = alloc_chrdev_region(&dev_nr, 0, MINORMASK + 1, "hello_cdev");
不需要手动配置,自动配置字符设备 hello_cdev
创建并添加字符设备:
cdev_init(&my_cdev, &fops);
&my_cdev 指向全局变量里这个指针,fops就将字符设备和读写操作结合起来
全局变量my_cdev 的所有者是这个模块,这样就将hello_cdev 接上了
my_cdev.owner = THIS_MODULE;
这样系统内核就添加字符设备,在 /proc/dev/中可以看到字符设备 hello_cdev,主设备号是dev_nr
status = cdev_add(&my_cdev, dev_nr, MINORMASK + 1);
不过这节系统内核添加hello_cdev这个设备驱动之后还是要mknod 创建字符设备 mknod /dev/hello0 c 236 0