Linux USB subsystem --- USB bus registration

Linux USB subsystem --- USB bus registration

[Linux 3.2] [driver/usb/core/driver.c]

定义:usb_bus_type

[cpp] view plain copy
  1. struct bus_type usb_bus_type = {  
  2.     .name =     "usb",  
  3.     .match =    usb_device_match,  
  4.     .uevent =   usb_uevent,  
  5. };  

 

[Linux 3.2] [driver/base/bus.c]

函数:bus_register(struct bus_type *bus)

[cpp] view plain copy
  1. /** 
  2.  * bus_register - register a bus with the system. 
  3.  * @bus: bus. 
  4.  * 
  5.  * Once we have that, we registered the bus with the kobject 
  6.  * infrastructure, then register the children subsystems it has: 
  7.  * the devices and drivers that belong to the bus. 
  8.  */  
  9. int bus_register(struct bus_type *bus)  
  10. {  
  11.     int retval;  
  12.     struct subsys_private *priv;  
  13.   
  14.     priv = kzalloc(sizeof(struct subsys_private), GFP_KERNEL);  
  15.     if (!priv)  
  16.         return -ENOMEM;  
  17.   
  18.     priv->bus = bus;  
  19.     bus->p = priv;  
  20.   
  21.     BLOCKING_INIT_NOTIFIER_HEAD(&priv->bus_notifier);  
  22.   
  23.     retval = kobject_set_name(&priv->subsys.kobj, "%s", bus->name);  
  24.     if (retval)  
  25.         goto out;  
  26.   
  27.     priv->subsys.kobj.kset = bus_kset;  
  28.     priv->subsys.kobj.ktype = &bus_ktype;  
  29.     priv->drivers_autoprobe = 1;  
  30.   
  31.     retval = kset_register(&priv->subsys);  
  32.     if (retval)  
  33.         goto out;  
  34.   
  35.     retval = bus_create_file(bus, &bus_attr_uevent);  
  36.     if (retval)  
  37.         goto bus_uevent_fail;  
  38.   
  39.     priv->devices_kset = kset_create_and_add("devices", NULL,  
  40.                          &priv->subsys.kobj);  
  41.     if (!priv->devices_kset) {  
  42.         retval = -ENOMEM;  
  43.         goto bus_devices_fail;  
  44.     }  
  45.   
  46.     priv->drivers_kset = kset_create_and_add("drivers", NULL,  
  47.                          &priv->subsys.kobj);  
  48.     if (!priv->drivers_kset) {  
  49.         retval = -ENOMEM;  
  50.         goto bus_drivers_fail;  
  51.     }  
  52.   
  53.     klist_init(&priv->klist_devices, klist_devices_get, klist_devices_put);  
  54.     klist_init(&priv->klist_drivers, NULL, NULL);  
  55.   
  56.     retval = add_probe_files(bus);  
  57.     if (retval)  
  58.         goto bus_probe_files_fail;  
  59.   
  60.     retval = bus_add_attrs(bus);  
  61.     if (retval)  
  62.         goto bus_attrs_fail;  
  63.   
  64.     pr_debug("bus: '%s': registered\n", bus->name);  
  65.     return 0;  
  66.   
  67. bus_attrs_fail:  
  68.     remove_probe_files(bus);  
  69. bus_probe_files_fail:  
  70.     kset_unregister(bus->p->drivers_kset);  
  71. bus_drivers_fail:  
  72.     kset_unregister(bus->p->devices_kset);  
  73. bus_devices_fail:  
  74.     bus_remove_file(bus, &bus_attr_uevent);  
  75. bus_uevent_fail:  
  76.     kset_unregister(&bus->p->subsys);  
  77. out:  
  78.     kfree(bus->p);  
  79.     bus->p = NULL;  
  80.     return retval;  
  81. }  
  82. EXPORT_SYMBOL_GPL(bus_register);  


bus_register的目的主要是处理Linux设备模型的相关事宜。

此函数的主要作用如下:

1. line 21 : 初始化一个blocking的通知链。

2. line 23 ~ 31: 将USB总线加入总线集,并在/sys/bus下面创建usb子目录。

3. line 35 : 在/sys/bus/usb/下面创建uevent的属性文件。

4. line 39 ~ 51: 在usb总线子集上面创建devices, drivers两个子集,同时创建目录。

5. line 53 ~54 : 初始化两条链表:klist_devices, klist_drivers。

6. line 56 : 添加bus的drivers_probe,drivers_autoprobe属性文件。(需要CONFIG_HOTPLUG的支持)

7. line 60 : 添加bus的其余属性文件,对USB来说,没有。

这些完成之后,可以在/sys/bus下面看到usb目录,

在USB目录下面可以看到:

# ls /sys/bus/usb

devices   drivers_autoprobe  uevent   drivers            drivers_probe


你可能感兴趣的:(Linux USB subsystem --- USB bus registration)