分配设备编号,注册设备与注销设备的函数均在fs.h中申明,如下:
extern int register_chrdev_region(dev_t, unsigned, const char *); //静态的申请和注册设备号
extern int alloc_chrdev_region(dev_t, unsigned, const char *); //动态的申请注册一个设备号
extern int register_chrdev(unsigned int, const char *,struct file_operations *);//int为0时候动态注册,非零时候静态注册。
extern int unregister_chrdev(unsigned int, const char *); //注销设备号
extern void unregister_chrdev_region(dev_t, unsigned); //注销设备号
静态注册:
使用register_chrdev_region()首先需要定义一个dev_t变量来作为一个设备号,
dev_t dev_num;
要想注册一个设备则需要一个主设备号。
根据主设备号获取设备号:
dev_num=MKDEV(major,minor); major是一个表示设备号的主设备号,minor次设备号
注册:
register_chrdev_region(dev_num,2,"dev_name");
第一个参数表示设备号,第二个参数表示注册的此设备数目,第三个表示设备名称。
动态注册:
如果我们提前知道设备的编号,那么就用register_chrdev_region(),但是如果我们不知道呢,我们就使用动态申请设备编号。
alloc_chrdev_region(&dev_num, minor, 2, "dev_name");
第一个参数保存生成的设备号,第二个参数注册设备的数目,第三个参数表示设备名称。
根据设备号获取主设备号:
dev_major = MAJOR(dev_num);
struct cdev devno;
cdev_init(&devno,&file_ops); //初始化设备
devno.owner = THIS_MODULE; //.owner这表示谁拥有你这个驱动程序,
devno.ops = &mem_fops;
对于已经知道了主设备号,就用cdev_add(&devno, dev_num,count);来添加设备
如果是动态申请的设备号,就用cdev_add(&devno, MKDEV(mem_major, 0), count);
向内核添加设备,第一个参数是设备,第二个参数是设备号,第三个参数是要注册的次设备数目,mem_major在动态申请时候保存起来了。
注销设备时候,使用unregister_chrdev_region(dev_t, unsigned);第一个参数设备号,和注册时候的要一致,因此如果是动态分配的就需要保存起来,第二个参数是次设备的个数。
register_chrdev(unsigned int, const char *,struct file_operations *); // 申请注册设备号以第一个参数来辨别动态与静态。
1、如果第一个参数是0,表示动态的分配给此驱动程序一个主设备号,
2、非零时候,表示备驱动程序向系统申请主设备号,
第二个是设备名,第三个file_operations,如果是动态分配的,则函数返回分配的主设备号。
对应的使用unregister_chrdev(unsigned int, const char *);来注销设备,第一个参数是主设备号,必须和注册时候的主设备号一致,如果注册时候是动态的分配的主设备号,就需要保存起来,第二个是设备名。
综上得出:register_chrdev_region()比register_chrdev()多了一步,就是想内核注册添加cdev设备的步骤。
register_chrdev_region()是register_chrdev()的升级版本。