linux设备模型

来源:互联网 发布:ubuntu自带gcc吗 编辑:程序博客网 时间:2024/05/20 20:03

sysfs 把连接在系统上的设备和总线组织成为一个分级的文件,展示设备驱动模型中各组件的层次关系


总线bus:类型class:设备device

此处的device是系统注册上的device,是bus、class下的device的子集。


在/sys/bus 的 pci 等子目录下,又会在分出 drivers 和 devices 目录,而 devices 目录中的文件是对/sys/devices 目录中文件的符号链接。同样地,/sys/class 目录下包含许多对/sys/devices 下文件的链接。


struct device:

1、系统中的任一设备在设备模型中都由一个 device 对象描述,但不单独使用

2、内嵌kobject来组织驱动层次。

3、device_register()函数将一个新的 device 对象插入设备模型,并自动在/sys/devices 下创建一个对应的目录。

struct device  {  struct klist    klist_children; // 设备列表中的孩子列表   struct klist_node  knode_parent;// 兄弟节点    struct klist_node  knode_driver; // 驱动结点   struct klist_node  knode_bus; // 总线结点   struct device   * parent; // 指向父设备     struct kobject kobj;   // 内嵌一个 kobject 对象   char  bus_id[BUS_ID_SIZE];// 总线上的位置      struct bus_type * bus;  // 总线    struct device_driver *driver;// 使用的驱动   void    *driver_data;  // 驱动私有数据   void    *platform_data; //平台特定的数据   void    *firmware_data; //固件特定的数据(如 ACPI、BIOS 数据)    void  (*release)(struct device * dev); // 释放设备方法   };   


struct device_driver:

1、内嵌的 kobject

2、内核提供类似的函数用于操作 device_driver 对象。如 get_driver()增加引用计数,driver_register()用于向设备模型插入新的 driver 对象,同时在 sysfs 文件系统中创建对应的目录。

 struct device_driver     {     const char    * name;   //设备驱动程序的名称     struct bus_type   * bus; //总线         struct completion  unloaded;     struct kobject    kobj;//内嵌的 kobject 对象     struct klist    klist_devices;     struct klist_node  knode_bus;         struct module    * owner;         int (*probe)  (struct device * dev); //指向设备探测函数     int (*remove)  (struct device * dev); //指向设备移除函数     void  (*shutdown) (struct device * dev);     int (*suspend)  (struct device * dev, pm_message_t state);     int (*resume)  (struct device * dev);    };   

struct bus_type

1、内嵌subsystem

2、包含处理热插拔、即插即拔和电源管理事件的函数

    1  struct bus_type        2  {       3   const char    * name;//总线类型的名称       4         5   struct subsystem  subsys;//与该总线相关的 subsystem       6   struct kset   drivers;//所有与该总线相关的驱动程序集合       7   struct kset   devices;//所有挂接在该总线上的设备集合       8   struct klist    klist_devices;       9   struct klist    klist_drivers;       10        11  struct bus_attribute  * bus_attrs;//总线属性       12  struct device_attribute * dev_attrs;//设备属性       13  struct driver_attribute * drv_attrs; //驱动程序属性       14        15  int   (*match)(struct device * dev, struct device_driver * drv);       16  int   (*uevent)(struct device *dev, char **envp,       17          int num_envp, char *buffer, int buffer_size);//事件       18  int   (*probe)(struct device * dev);       19  int   (*remove)(struct device * dev);       20  void    (*shutdown)(struct device * dev);       21  int   (*suspend)(struct device * dev, pm_message_t state);       22  int   (*resume)(struct device * dev);       23 };   

struct class

1、设备类

2、内嵌sub system

3、包括用于处理热插拔、即插即拔和电源管理事件的函数

struct class_device    {    struct list_head  node;       struct kobject    kobj;//内嵌的 kobject    struct class    * class;  //所属的类    dev_t      devt;    // dev_t    struct class_device_attribute *devt_attr;    struct class_device_attribute uevent_attr;    struct device    * dev;  //如果存在,创建到/sys/devices 相应入口的符号链接    void      * class_data;  //私有数据    struct class_device *parent;  //父设备       void  (*release)(struct class_device *dev);    int (*uevent)(struct class_device *dev, char **envp,           int num_envp, char *buffer, int buffer_size);    char  class_id[BUS_ID_SIZE];  //类标识   };  








kobject:

1、注册的 kobject 对象都对应于sysfs 文件系统中的一个目录。

2、这个数据结构使所有设备在底层都具有统一的接口。

3、父对象指向kset内嵌kobject

 struct kobject    {      char *k_name;       char name[KOBJ_NAME_LEN]; //对象名称      struct kref kref; //对象引用计数      struct list_head entry; //用于挂接该 kobject 对象到 kset 链表      struct kobject *parent; //指向父对象的指针      struct kset *kset; //所属 kset 的指针      struct kobj_type *ktype; //指向对象类型描述符的指针      struct dentry *dentry; //sysfs 文件系统中与该对象对应的文件节点入口    };  


kset:

1、具有相同类型的 kobject 的集合(一个双向循环链表)

2、kset 数据结构还内嵌了一个 kobject 对象(kobj 成员表示),所有属于这个 kset的 kobject 对象的 parent 均指向这个内嵌的对象。

3、kobject 被创建或删除时会产生事件(event),kobject 所属的 kset 将有机会过滤事件或为用户空间添加信息。

 struct kset     {      struct subsystem  * subsys; //所在的 subsystem 的指针      struct kobj_type  * ktype; //指向该 kset 对象类型描述符的指针      struct list_head  list; //用于连接该 kset 中所有 kobject 的链表头      spinlock_t    list_lock;      struct kobject    kobj; //嵌入的 kobject      struct kset_uevent_ops  * uevent_ops;//事件操作集    };   

kset 的uevent_ops 成员是执行该 kset 事件操作集 kset_uevent_ops 的指针

1、filter()函数用于过滤掉不需要导出到用户空间的事件,

2、uevent()函数用于导出一些环境变量给用户的热插拔处理程序

struct kset_uevent_ops    {     int (*filter)(struct kset *kset, struct kobject *kobj);//事件过滤     const char *(*name)(struct kset *kset, struct kobject *kobj);     int (*uevent)(struct kset *kset, struct kobject *kobj, char **envp,         int num_envp, char *buffer, int buffer_size);//环境变量设置   };   

subsystem :

1、kset 的集合,对 应 于 /sysfs/  目录 。

2、内嵌 kset ,keset通过指向内嵌kset 加入到该 subsystem。

 struct subsystem    {      struct kset kset; //内嵌的 kset 对象      struct rw_semaphore rwsem; //互斥访问信号量    };   



0 0
原创粉丝点击