- 论坛徽章:
- 0
|
本帖最后由 hk2305621 于 2012-09-09 15:56 编辑
在 Linux 设备模型中, bus 和 driver 的关系是, driver 都是服务于某一种 bus 上的某一类型 device的. 我这里看的代码是 Linux 2.6.38 的. 好像从2.6.32都差不多这样.
如果 bus 有定义 prober 函数, 那就直接执行 bus 的probe 函数, 会忽略掉 driver 的probe 函数. 但是, bus 一般不会声明 probe 函数.
当你注册一个 driver 的时候, 会调用- int driver_register(struct device_driver *drv) // define in <drivers/base/driver.c>
复制代码 driver_register 函数会调用- int bus_add_driver(struct device_driver *drv) //define in <driver/base/bus.c>
复制代码 bus_add_driver 函数中有如下一段代码
- if (drv->bus->p->drivers_autoprobe) {
- error = driver_attach(drv);
- if (error)
- goto out_unregister;
- }
复制代码 就是用来调用 probe 函数.
driver_attach(drv) 函数如下:- int driver_attach(struct device_driver *drv)
- {
- return bus_for_each_dev(drv->bus, NULL, drv, __driver_attach);
- }
复制代码 其中 __driver_attach 是一个函数. 如下. 这个函数会调用 driver_probe_device 去调用 bus 或者 driver 的 probe 函数.- static int __driver_attach(struct device *dev, void *data)
- {
- struct device_driver *drv = data;
- /*
- * Lock device and try to bind to it. We drop the error
- * here and always return 0, because we need to keep trying
- * to bind to devices and some drivers will return an error
- * simply if it didn't support the device.
- *
- * driver_probe_device() will spit a warning if there
- * is an error.
- */
- if (!driver_match_device(drv, dev))
- return 0;
- if (dev->parent) /* Needed for USB */
- device_lock(dev->parent);
- device_lock(dev);
- if (!dev->driver)
- driver_probe_device(drv, dev);
- device_unlock(dev);
- if (dev->parent)
- device_unlock(dev->parent);
- return 0;
- }
复制代码 driver_probe_device 函数定义如下: 它会调用函数 really_probe 函数.- int driver_probe_device(struct device_driver *drv, struct device *dev)
- {
- int ret = 0;
- if (!device_is_registered(dev))
- return -ENODEV;
- pr_debug("bus: '%s': %s: matched device %s with driver %s\n",
- drv->bus->name, __func__, dev_name(dev), drv->name);
- pm_runtime_get_noresume(dev);
- pm_runtime_barrier(dev);
- ret = really_probe(dev, drv);
- pm_runtime_put_sync(dev);
- return ret;
- }
复制代码 really_probe 函数如下:- static int really_probe(struct device *dev, struct device_driver *drv)
- {
- int ret = 0;
- atomic_inc(&probe_count);
- pr_debug("bus: '%s': %s: probing driver %s with device %s\n",
- drv->bus->name, __func__, drv->name, dev_name(dev));
- WARN_ON(!list_empty(&dev->devres_head));
- dev->driver = drv;
- if (driver_sysfs_add(dev)) {
- printk(KERN_ERR "%s: driver_sysfs_add(%s) failed\n",
- __func__, dev_name(dev));
- goto probe_failed;
- }
- if (dev->bus->probe) {
- ret = dev->bus->probe(dev);
- if (ret)
- goto probe_failed;
- } else if (drv->probe) {
- ret = drv->probe(dev);
- if (ret)
- goto probe_failed;
- }
- driver_bound(dev);
- ret = 1;
- pr_debug("bus: '%s': %s: bound device %s to driver %s\n",
- drv->bus->name, __func__, dev_name(dev), drv->name);
- goto done;
- probe_failed:
- devres_release_all(dev);
- driver_sysfs_remove(dev);
- dev->driver = NULL;
- if (ret != -ENODEV && ret != -ENXIO) {
- /* driver matched but the probe failed */
- printk(KERN_WARNING
- "%s: probe of %s failed with error %d\n",
- drv->name, dev_name(dev), ret);
- }
- /*
- * Ignore errors returned by ->probe so that the next driver can try
- * its luck.
- */
- ret = 0;
- done:
- atomic_dec(&probe_count);
- wake_up(&probe_waitqueue);
- return ret;
- }
复制代码 really_probe 函数有一段代码:如下, 就是,
1. 判断 bus 有没有声明 probe 函数, 如果有, 就调用 bus 的 probe 函数.
2. 如果 bus 没有定义 probe 函数, 就检查 driver 有没有定义 probe 函数, 如果有, 就调用 driver 的 probe 函数.
3. 如果 bus 和 driver 都没有定义 probe 函数, 就不执行. 继续往下.- if (dev->bus->probe) {
- ret = dev->bus->probe(dev);
- if (ret)
- goto probe_failed;
- } else if (drv->probe) {
- ret = drv->probe(dev);
- if (ret)
- goto probe_failed;
- }
复制代码 |
|