cdev_init和register_chrdev区别
2016-07-08 16:46
246 查看
---
01:include/linux/fs.h
fs/char_dev.c
02:fs/char_dev.c
---------------------------------使用--------------------------
---
01:include/linux/fs.h
static inline int register_chrdev(unsigned int major, const char *name, const struct file_operations *fops) { return __register_chrdev(major, 0, 256, name, fops); }
fs/char_dev.c
/** * __register_chrdev() - create and register a cdev occupying a range of minors * @major: major device number or 0 for dynamic allocation * @baseminor: first of the requested range of minor numbers * @count: the number of minor numbers required * @name: name of this range of devices * @fops: file operations associated with this devices * * If @major == 0 this functions will dynamically allocate a major and return * its number. * * If @major > 0 this function will attempt to reserve a device with the given * major number and will return zero on success. * * Returns a -ve errno on failure. * * The name of this device has nothing to do with the name of the device in * /dev. It only helps to keep track of the different owners of devices. If * your module name has only one type of devices it's ok to use e.g. the name * of the module here. */ int __register_chrdev(unsigned int major, unsigned int baseminor, ¦ ¦ unsigned int count, const char *name, ¦ ¦ const struct file_operations *fops) { struct char_device_struct *cd; struct cdev *cdev; int err = -ENOMEM; cd = __register_chrdev_region(major, baseminor, count, name); if (IS_ERR(cd)) return PTR_ERR(cd); cdev = cdev_alloc(); if (!cdev) goto out2; cdev->owner = fops->owner; cdev->ops = fops; kobject_set_name(&cdev->kobj, "%s", name); err = cdev_add(cdev, MKDEV(cd->major, baseminor), count); if (err) goto out; cd->cdev = cdev; return major ? 0 : cd->major; out: kobject_put(&cdev->kobj); out2: kfree(__unregister_chrdev_region(cd->major, baseminor, count)); return err; }
02:fs/char_dev.c
/** * cdev_init() - initialize a cdev structure * @cdev: the structure to initialize * @fops: the file_operations for this device * * Initializes @cdev, remembering @fops, making it ready to add to the * system with cdev_add(). */ void cdev_init(struct cdev *cdev, const struct file_operations *fops) { memset(cdev, 0, sizeof *cdev); INIT_LIST_HEAD(&cdev->list); kobject_init(&cdev->kobj, &ktype_cdev_default); cdev->ops = fops; }
---------------------------------使用--------------------------
static int flashlight_probe(struct platform_device *dev) { int ret = 0, err = 0; logI("[flashlight_probe] start ~"); #ifdef ALLOC_DEVNO ret = alloc_chrdev_region(&flashlight_devno, 0, 1, FLASHLIGHT_DEVNAME); if (ret) { logI("[flashlight_probe] alloc_chrdev_region fail: %d ~", ret); goto flashlight_probe_error; } else { logI("[flashlight_probe] major: %d, minor: %d ~", MAJOR(flashlight_devno), ¦ ¦MINOR(flashlight_devno)); } cdev_init(&flashlight_cdev, &flashlight_fops); flashlight_cdev.owner = THIS_MODULE; err = cdev_add(&flashlight_cdev, flashlight_devno, 1); if (err) { logI("[flashlight_probe] cdev_add fail: %d ~", err); goto flashlight_probe_error; } #else #define FLASHLIGHT_MAJOR 242 ret = register_chrdev(FLASHLIGHT_MAJOR, FLASHLIGHT_DEVNAME, &flashlight_fops); if (ret != 0) { logI("[flashlight_probe] Unable to register chardev on major=%d (%d) ~", ¦ ¦FLASHLIGHT_MAJOR, ret); return ret; } flashlight_devno = MKDEV(FLASHLIGHT_MAJOR, 0); #endif flashlight_class = class_create(THIS_MODULE, "flashlightdrv"); if (IS_ERR(flashlight_class)) { logI("[flashlight_probe] Unable to create class, err = %d ~", ¦ ¦(int)PTR_ERR(flashlight_class)); goto flashlight_probe_error; } flashlight_device = ¦ device_create(flashlight_class, NULL, flashlight_devno, NULL, FLASHLIGHT_DEVNAME); if (NULL == flashlight_device) { logI("[flashlight_probe] device_create fail ~"); goto flashlight_probe_error; } /* initialize members */ spin_lock_init(&flashlight_private.lock); init_waitqueue_head(&flashlight_private.read_wait); /* init_MUTEX(&flashlight_private.sem); */ sema_init(&flashlight_private.sem, 1); flashlight_gpio_init(dev); logI("[flashlight_probe] Done ~"); return 0; flashlight_probe_error: #ifdef ALLOC_DEVNO if (err == 0) cdev_del(&flashlight_cdev); if (ret == 0) unregister_chrdev_region(flashlight_devno, 1); #else if (ret == 0) unregister_chrdev(MAJOR(flashlight_devno), FLASHLIGHT_DEVNAME); #endif return -1; }
---
相关文章推荐
- phpstorm一个窗口打开多个项目
- 【SpringMVC学习03】SpringMVC中注解和非注解方式下的映射器和适配器总结
- 关于spring在程序中读取properties文件配置项的方法
- [iOS]wallet开发demo
- 布莱叶盲文
- 解决同一页面jQuery多个版本或和其他js库冲突方法
- jq 回到顶部
- 关于SQL Server将一列的多行内容拼接成一行的问题讨论
- C#图像处理(各种旋转、改变大小、柔化、锐化、雾化、底片、浮雕、黑白、滤镜效果)
- maven 打包 符号不存在 删除<scope>test</scope>
- PHP原生态分页
- 举火燎天
- 特别行动队 [APIO 2010]
- 移动直播技术秒开优化经验
- DAG训练题 奥赛奖金
- linux内核启动第二阶段分析 start_kernel
- UILabel attributedText的一个坑
- 解决有 sql中 &XXX 插入数据的时候弹出提示框输入内容
- android布局--fill_parent、wrap_content和match_parent的区别
- 一个程序员的自白