【1】register_chrdev函数
使用register_chrdev注册字符设备
int register_chrdev(unsignedintmajor,constcharname,structfile_operationsfops);
其中参数major如果等于0,则表示采用系统动态分配的主设备号;不为0,则表示静态注册。
注销字符设备可以使用unregister_chrdev函数。
int unregister_chrdev(unsignedintmajor,constchar*name);
register_chrdev_region是register_chrdev的升级版本,
unregist_chrdev_region是unregister_chrdev的升级版本。
使用register_chrdev_region()比register_chrdev()多了一步,就是想内核注册添加cdev设备的步骤。
追代码:
用来明白底层的实现原理
static inline int register_chrdev(unsigned int major, const char *name, const struct file_operations *fops)
__register_chrdev(major, 0, 256, name, fops);
cd = __register_chrdev_region(major, baseminor, count, name);
cd = kzalloc(sizeof(struct char_device_struct), GFP_KERNEL);
/* temporary 表示动态分配*/
if (major == 0) {
for (i = ARRAY_SIZE(chrdevs)-1; i > 0; i--) { //ARRAY_SIZE(chrdevs)-1 = 254 对应结构体指针数组
if (chrdevs[i] == NULL) //如果结构体指针数组为NULL,表示未占用,可以分配给申请者
break;
}
if (i == 0) { //忙的情况
ret = -EBUSY;
goto out;
}
major = i; //动态分配的原理
ret = major;
}
cd->major = major; //默认静态分配或动态分配的填充主设备号
cd->baseminor = baseminor;
cd->minorct = minorct;
strlcpy(cd->name, name, sizeof(cd->name));
cdev = cdev_alloc();
cdev->owner = fops->owner; | --- cdev_init
cdev->ops = fops; |
err = cdev_add(cdev, MKDEV(cd->major, baseminor), count);
register_chrdev(unsigned int major, const char *name, const struct file_operations *fops)
功能: 创建并注册一个字符设备
参数:
major :主设备号
major == 0; 动态分配
0 < major < 254 ;静态分配
name :设备的名字
fops :操作方法集
返回值:
* If @major == 0 返回主设备号major
* If @major > 0 成功返回0
失败返回错误码
代码实例:
#include <linux/module.h>
#include <linux/moduleparam.h>
#include <linux/fs.h>
#include <linux/cdev.h>
//定义一个字符设备对象
struct cdev *cdev;
unsigned int major = 0;
const char * name = "demochar";
//向上层提供的接口
//向下层操作硬件----在接口里去操作硬件
const struct file_operations fops = {
};
static int __init demo_init(void)
{
printk("----%s---%d.\n",__func__,__LINE__);
major = register_chrdev(0, name, &fops);//创建并注册一个字符设备
if(major <= 0){
printk("register_chrdev failed.\n");
return major;
}
printk("major :%d.\n",major);
return 0;
}
static void __exit demo_exit(void)
{
printk("----%s---%d.\n",__func__,__LINE__);
unreg