Chinaunix首页 | 论坛 | 博客
  • 博客访问: 177864
  • 博文数量: 34
  • 博客积分: 0
  • 博客等级: 民兵
  • 技术积分: 374
  • 用 户 组: 普通用户
  • 注册时间: 2013-10-30 10:46
文章分类

全部博文(34)

文章存档

2018年(5)

2015年(13)

2014年(13)

2013年(3)

我的朋友

分类: 嵌入式

2015-06-12 17:47:51

http://blog.csdn.net/fudan_abc/article/details/1797677

总线、设备和驱动 
的关系:
linux中关于设备驱动不管 usb设备,i2c设备 还是 spi设备。这些设备能够驱动起来,Linux内核中不得不了解的3个结构体。
struct bus_type{}  //
struct device_driver {}
struct device{}   
查看结构体定义,发现
            bus_type.dev_root        (类型 struct device *)
           device_driver.p->driver (类型 struct device_driver *)   
            device.driver                (类型 struct device_driver *)

总线、设备和驱动它们只见是如何和谐共处:
每次出现一个设备就要向总线汇报,或者说注册,每次出现一个驱动,也要向总线汇报,或者说注册。比如系统初始化的时候,会扫描连接了哪些设备,并为每一个设备建立起一个struct device的变量,每一次有一个驱动程序,就要准备一个struct device_driver结构的变量。把这些变量统统加入相应的链表,device 插入devices 链表,driver插入drivers链表。


device可以在计算机启动以后在插入或者拔出计算机了。因此,很难再说是先有device还是先有driver了。因为都有可能。device可以在任何时刻出现,而driver 也可以在任何时刻被加载,所以,出现的情况就是,每当一个struct device诞生,它就会去bus的drivers链表中寻找自己的另一半,反之,每当一个一个struct device_driver诞生,它就去bus的devices链表中寻找它的那些设备。如果找到了合适的,那么ok,和之前那种情况一下,调用device_bind_driver绑定好.如果找不到,没有关系,等待吧,等到昙花再开,等到风景看透,心中相信,这世界上总有一个人是你所等的,只是还没有遇到而已。

这三个结构体在 include\linux\device.h 中定义。一下将结构体定义贴出来,建议使用sourceinsight 工具查看源码。
struct bus_type {
const char *name;
const char *dev_name;
struct device *dev_root;
struct device_attribute *dev_attrs; /* use dev_groups instead */
const struct attribute_group **bus_groups;
const struct attribute_group **dev_groups;
const struct attribute_group **drv_groups;

int (*match)(struct device *dev, struct device_driver *drv);
int (*uevent)(struct device *dev, struct kobj_uevent_env *env);
int (*probe)(struct device *dev);
int (*remove)(struct device *dev);
void (*shutdown)(struct device *dev);

int (*online)(struct device *dev);
int (*offline)(struct device *dev);

int (*suspend)(struct device *dev, pm_message_t state);
int (*resume)(struct device *dev);

const struct dev_pm_ops *pm;

const struct iommu_ops *iommu_ops;

struct subsys_private *p;
struct lock_class_key lock_key;
}

struct device_driver {
const char *name;
struct bus_type *bus;

struct module *owner;
const char *mod_name; /* used for built-in modules */

bool suppress_bind_attrs; /* disables bind/unbind via sysfs */

const struct of_device_id *of_match_table;
const struct acpi_device_id *acpi_match_table;

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);
const struct attribute_group **groups;

const struct dev_pm_ops *pm;

struct driver_private *p;
}

struct device {
struct device *parent;


struct device_private *p;


struct kobject kobj;
const char *init_name; /* initial name of the device */
const struct device_type *type;


struct mutex mutex; /* mutex to synchronize calls to
* its driver.
*/


struct bus_type *bus; /* type of bus device is on */
struct device_driver *driver; /* which driver has allocated this
  device */
void *platform_data; /* Platform specific data, device
  core doesn't touch it */
void *driver_data; /* Driver data, set and get with
  dev_set/get_drvdata */
struct dev_pm_info power;
struct dev_pm_domain *pm_domain;


#ifdef CONFIG_PINCTRL
struct dev_pin_info *pins;
#endif


#ifdef CONFIG_NUMA
int numa_node; /* NUMA node this device is close to */
#endif
u64 *dma_mask; /* dma mask (if dma'able device) */
u64 coherent_dma_mask;/* Like dma_mask, but for
    alloc_coherent mappings as
    not all hardware supports
    64 bit addresses for consistent
    allocations such descriptors. */
unsigned long dma_pfn_offset;


struct device_dma_parameters *dma_parms;


struct list_head dma_pools; /* dma pools (if dma'ble) */


struct dma_coherent_mem *dma_mem; /* internal for coherent mem
    override */
#ifdef CONFIG_DMA_CMA
struct cma *cma_area; /* contiguous memory area for dma
  allocations */
#endif
/* arch specific additions */
struct dev_archdata archdata;


struct device_node *of_node; /* associated device tree node */
struct acpi_dev_node acpi_node; /* associated ACPI device node */


dev_t devt; /* dev_t, creates the sysfs "dev" */
u32 id; /* device instance */


spinlock_t devres_lock;
struct list_head devres_head;


struct klist_node knode_class;
struct class *class;
const struct attribute_group **groups; /* optional groups */


void (*release)(struct device *dev);
struct iommu_group *iommu_group;


bool offline_disabled:1;
bool offline:1;
}




阅读(2077) | 评论(0) | 转发(0) |
给主人留下些什么吧!~~