linux驱动--设备节点生成

linux 同时被 2 个专栏收录
16 篇文章 0 订阅

linux驱动–设备节点生成

关于设备注册于驱动注册,参考前一篇文章http://blog.csdn.net/cole10540316/article/details/51848272

linux驱动一般分为三类:字符设备、块设备、网络设备,但是这三类设备并不能完全包含所有的设备,所以引入了杂项设备。linux下采用杂项设备可能包含字符设备、块设备、网络设备中的一项或者多项设备。本文是在杂项设备下生成设备节点,杂项设备,在内核编译时强制编译进内核。linux下的设备号为主设备号0-255,每个主设备号下又分为256个子设备号,杂项设备的主设备号为10.

设备节点生成代码

#include <linux/module.h>//与module相关的信息
#include <linux/kernel.h>
#include <linux/init.h>      //与init相关的函数
#include <linux/platform_device.h>
#include <linux/miscdevice.h> //杂项设备头文件
#include <linux/fs.h>
/***************用到的函数******************
extern int platform_driver_register(struct platform_driver *);
extern void platform_driver_unregister(struct platform_driver *);

        int (*probe)(struct platform_device *);
        int (*remove)(struct platform_device *);
        void (*shutdown)(struct platform_device *);
        int (*suspend)(struct platform_device *, pm_message_t state);
        int (*resume)(struct platform_device *);
杂项设备结构体
struct miscdevice  {
        int minor;      //MISC_DYNAMIC_MINOR,由宏定义给定,一般就为10
        const char *name;
        const struct file_operations *fops;
        struct list_head list;
        struct device *parent;
        struct device *this_device;
        const char *nodename;
        mode_t mode;
};
//杂项设备注册于解除函数  一般在 probe函数 中调用
extern int misc_register(struct miscdevice * misc);
extern int misc_deregister(struct miscdevice *misc);

struct file_operations {
        struct module *owner;
         long (*unlocked_ioctl) (struct file *, unsigned int, unsigned long);
        long (*compat_ioctl) (struct file *, unsigned int, unsigned long);
        int (*mmap) (struct file *, struct vm_area_struct *);
        int (*open) (struct inode *, struct file *);
        int (*flush) (struct file *, fl_owner_t id);
        int (*release) (struct inode *, struct file *);
        int (*fsync) (struct file *, int datasync);
        int (*aio_fsync) (struct kiocb *, int datasync);
        int (*fasync) (int, struct file *, int);
        int (*lock) (struct file *, int, struct file_lock *);


**********************************/

MODULE_LICENSE("GPL");
MODULE_AUTHOR("zhangsan");

#define DRIVER_NAME "hello_ctl"
#define DEVICE_NAME "hello_ctldevice"
//file ops结构体的内容实现
static long hello_ioctl(struct file *file, unsigned int cmd, unsigned long arg)
{
    printk(KERN_INFO "The cmd is %d,arg is %d\n",cmd,arg);
    return 0;
}
static int hello_release(struct inode *inode, struct file *file)
{
    printk(KERN_INFO "hello_release\n");    
    return 0;
}
static int hello_open(struct inode *inode, struct file *file)
{
    printk(KERN_INFO "hello_open\n");   
    return 0;
}
//
static struct file_operations hello_ops={

    .owner=THIS_MODULE, //THIS_MODULE
    .open=hello_open,   //对应上层的open函数
    .release=hello_release,
    .unlocked_ioctl=hello_ioctl,
};
//杂项设备结构体
static struct miscdevice hello_dev={
    .minor=MISC_DYNAMIC_MINOR,  //宏定义为10
    .name=DEVICE_NAME,     //设备名
    .fops=&hello_ops,       // 驱动需要实现的主体内容,在include/linux/fs.h头文件中有定义  
};

static int hello_probe(struct platform_device *pdv)
{
    misc_register(&hello_dev);//杂项设备注册
    return 0;
}
static int hello_remove(struct platform_device *pdv)
{
    misc_deregister(&hello_dev);//杂项设备解除
    return 0;
}
static void hello_shutdown(struct platform_device *pdv)
{
    printk(KERN_INFO "hello_shutdown\n");   
}
static int hello_suspend(struct platform_device *pdv)
{
    printk(KERN_INFO "Hello_suspend\n");
    return 0;
}
static int hello_resume(struct platform_device *pdv)
{
    printk(KERN_INFO "Hello_resume\n");
    return 0;
}
// 注册设备结构体
struct  platform_driver hello_driver={
    .probe=hello_probe,
    .remove=hello_remove,
    .shutdown=hello_shutdown,
    .suspend=hello_suspend,
    .resume=hello_resume,
    .driver={
        .name=DRIVER_NAME,
        .owner=THIS_MODULE,
    }
};

static int hellodriver_init()
{
    int Driverstate;
    printk(KERN_INFO "Hello_init\n");
    Driverstate=platform_driver_register(&hello_driver);
    printk(KERN_INFO "Driverstate is %d\n",Driverstate);
    return 0;
}

static void hellodriver_exit()
{

    printk(KERN_INFO "Hello_exit\n");
    platform_driver_unregister(&hello_driver);
}
module_init(hellodriver_init);
module_exit(hellodriver_exit);
  • 0
    点赞
  • 2
    评论
  • 0
    收藏
  • 打赏
    打赏
  • 扫一扫,分享海报

©️2022 CSDN 皮肤主题:大白 设计师:CSDN官方博客 返回首页

打赏作者

cole10540316

你的鼓励将是我创作的最大动力

¥2 ¥4 ¥6 ¥10 ¥20
输入1-500的整数
余额支付 (余额:-- )
扫码支付
扫码支付:¥2
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值