设备节点创建以及驱动改权限

本文档展示了如何在Linux中动态创建设备节点,分配设备号,并使用cdev结构进行操作。通过class_create和device_create函数创建设备节点文件,并使用chmod修改权限。模块初始化和退出函数确保了设备注册和注销的正确执行。
摘要由CSDN通过智能技术生成
/**
 **  MicroArray Corp.
 **  Author     GUQ.
 **  TIME       2015-04-24 am.
 **  MAIL       guq@microarray.com.cn
 **/
#include<linux/init.h>
#include<linux/module.h>
#include<linux/device.h>
#include<linux/fs.h>
#include<linux/kernel.h>
#include<linux/cdev.h>

#define DEV_NAME "auto_create_dev_node_init_test"
#define MOUNT_POINT "test"
#define D_FILE_NAME "test"
#define SLAVE_NUM 1


static int major;
static struct class * cls = NULL;
static struct device * dev_status = NULL;
static struct file *filp = NULL;
static struct inode *inode = NULL;
static struct cdev test_cdev;

static int test_open (struct inode * inode,
            struct file * filp){
    return 0;
}

Linux 驱动程序中,如果需要创建设备节点,可以使用 `class_create()` 函数创建设备类,使用 `device_create()` 函数创建设备节点。 例如,以下是在 Linux 驱动程序中创建设备节点的示例代码: ```c #include <linux/module.h> #include <linux/fs.h> #include <linux/device.h> static dev_t dev_num; static struct class *dev_class; static struct device *dev; static int my_open(struct inode *inode, struct file *file) { // 打开设备节点时的操作 return 0; } static int my_release(struct inode *inode, struct file *file) { // 关闭设备节点时的操作 return 0; } static struct file_operations my_fops = { .owner = THIS_MODULE, .open = my_open, .release = my_release, }; static int __init my_init(void) { int ret = 0; dev_num = MKDEV(0, 0); ret = alloc_chrdev_region(&dev_num, 0, 1, "mydev"); if (ret < 0) { printk(KERN_ERR "Failed to allocate device number\n"); return ret; } dev_class = class_create(THIS_MODULE, "myclass"); if (IS_ERR(dev_class)) { printk(KERN_ERR "Failed to create device class\n"); unregister_chrdev_region(dev_num, 1); return PTR_ERR(dev_class); } dev = device_create(dev_class, NULL, dev_num, NULL, "mydev"); if (IS_ERR(dev)) { printk(KERN_ERR "Failed to create device node\n"); class_destroy(dev_class); unregister_chrdev_region(dev_num, 1); return PTR_ERR(dev); } // 设置设备节点权限 ret = device_create_file(dev, &dev_attr_mode); if (ret < 0) { printk(KERN_ERR "Failed to create device attribute\n"); device_destroy(dev_class, dev_num); class_destroy(dev_class); unregister_chrdev_region(dev_num, 1); return ret; } cdev_init(&my_cdev, &my_fops); my_cdev.owner = THIS_MODULE; ret = cdev_add(&my_cdev, dev_num, 1); if (ret < 0) { printk(KERN_ERR "Failed to add character device\n"); device_remove_file(dev, &dev_attr_mode); device_destroy(dev_class, dev_num); class_destroy(dev_class); unregister_chrdev_region(dev_num, 1); return ret; } printk(KERN_INFO "Device node created successfully\n"); return 0; } static void __exit my_exit(void) { cdev_del(&my_cdev); device_remove_file(dev, &dev_attr_mode); device_destroy(dev_class, dev_num); class_destroy(dev_class); unregister_chrdev_region(dev_num, 1); printk(KERN_INFO "Device node removed\n"); } module_init(my_init); module_exit(my_exit); ``` 在上面的代码中,`my_init()` 函数中使用了 `class_create()` 函数创建设备类,使用 `device_create()` 函数创建设备节点,并使用 `device_create_file()` 函数创建设备节点属性。设备节点属性可以用来设置设备节点权限。 例如,可以创建一个名为 `mode` 的设备节点属性,并设置其权限为 `0666`,即用户、组和其他用户都有读写权限。代码如下: ```c static DEVICE_ATTR(mode, S_IRUGO | S_IWUSR, NULL, mode_show); ``` 在上面的代码中,`DEVICE_ATTR()` 宏用于创建设备节点属性,其中 `S_IRUGO | S_IWUSR` 表示该属性的权限为用户读写权限和组、其他用户只读权限,`mode_show` 表示读取该属性时调用的函数。该属性可以使用 `device_create_file()` 函数添加到设备节点中。 可以使用 `chmod` 命令来设置设备节点权限,例如: ``` chmod 666 /dev/mydev ``` 如果需要在驱动程序中设置设备节点权限,可以在 `my_init()` 函数中使用 `device_create_file()` 函数创建设备节点属性,并设置其权限。例如,可以创建一个名为 `mode` 的设备节点属性,并设置其权限为 `0666`,代码如下: ```c static DEVICE_ATTR(mode, S_IRUGO | S_IWUSR, NULL, mode_show); static ssize_t mode_show(struct device *dev, struct device_attribute *attr, char *buf) { return sprintf(buf, "%o\n", (int)dev->mode); } static int __init my_init(void) { int ret = 0; dev_num = MKDEV(0, 0); ret = alloc_chrdev_region(&dev_num, 0, 1, "mydev"); if (ret < 0) { printk(KERN_ERR "Failed to allocate device number\n"); return ret; } dev_class = class_create(THIS_MODULE, "myclass"); if (IS_ERR(dev_class)) { printk(KERN_ERR "Failed to create device class\n"); unregister_chrdev_region(dev_num, 1); return PTR_ERR(dev_class); } dev = device_create(dev_class, NULL, dev_num, NULL, "mydev"); if (IS_ERR(dev)) { printk(KERN_ERR "Failed to create device node\n"); class_destroy(dev_class); unregister_chrdev_region(dev_num, 1); return PTR_ERR(dev); } // 设置设备节点权限 ret = device_create_file(dev, &dev_attr_mode); if (ret < 0) { printk(KERN_ERR "Failed to create device attribute\n"); device_destroy(dev_class, dev_num); class_destroy(dev_class); unregister_chrdev_region(dev_num, 1); return ret; } // 设置设备节点权限为 0666 dev->mode = 0666; cdev_init(&my_cdev, &my_fops); my_cdev.owner = THIS_MODULE; ret = cdev_add(&my_cdev, dev_num, 1); if (ret < 0) { printk(KERN_ERR "Failed to add character device\n"); device_remove_file(dev, &dev_attr_mode); device_destroy(dev_class, dev_num); class_destroy(dev_class); unregister_chrdev_region(dev_num, 1); return ret; } printk(KERN_INFO "Device node created successfully\n"); return 0; } ``` 在上面的代码中,`mode_show()` 函数用于读取设备节点权限,并将其转换为八进制格式输出;`device_create_file()` 函数用于创建设备节点属性;`dev->mode = 0666` 语句用于设置设备节点权限为 0666。
评论 7
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值