Linux sys文件系统和驱动模型是紧密相关的,本系列以s3c2410 I2C驱动为例总结整理。内核版本2.6.32
函数调用关系如下:
start_kernel
|
|
|->do_basic_setup
| |
| |
| |->driver_init() //驱动模型初始化,按照层次关系,创建/sys/下的各个子目录
| | |
| | |->devices_init //创建kset对象devices_kset,指向/sys/devices目录
| | |->buses_init
| | |->classes_init
| | |->firmware_init
| | |->hypervisor_init
| | |->platform_bus_init //注册虚拟platform设备,platform bus。platform设备是其他设备的父亲设备
| | |->device_register(&platform_bus) //platform_bus虚拟设备注册
| | | |->device_initialize(&platform_bus)
| | | | |->dev->kobj.kset = devices_kset
| | | | |->device_init_wakeup
| | | | |->device_pm_init
| | | |
| | | |->device_add(&platform_bus)
| | | |->kobject_add(&dev->kobj, dev->kobj.parent, NULL)
| | | |->bus_add_device(&platform_bus)
| | | |->kobject_uevent(&dev->kobj, KOBJ_ADD)
| | | |->bus_probe_device(dev)
| | | |->device_attach
| | | |->bus_for_each_drv
| | | |->__device_attach
| | | |->driver_probe_device
| | | |->really_probe(dev,drv)
| | |
| | |->bus_register(&platform_bus_type) //platform_bus_type总线注册,创建/sys/bus/platform目录和其中的子目录及文件
| | | |->kset_register(&priv->subsys)
| | | |->bus_create_file(bus, &bus_attr_uevent)
| | | |->kset_create_and_add("devices",NULL,&priv->subsys.kobj)
| | | |->kset_create_and_add("drivers",NULL,&priv->subsys.kobj)
| |
| |->do_initcalls //各种初始化,包括i2c_init
|
|
|->i2c_init //注册i2c_bus
| |->bus_register(&i2c_bus_type) //i2c_bus_type总线注册创建/sys/bus/i2c目录和其中的子目录及文件
|
|->customize_machine
| |->smdk2440_machine_init //I2C adapter作为platform设备注册
| |->platform_add_devices(&s3c_device_i2c0) //
| |->platform_device_register(&s3c_device_i2c0)
| |->device_initialize(&s3c_device_i2c0)
| |->dev->kobj.kset = devices_kset
|
| |->platform_device_add(&s3c_device_i2c0)
| |->pdev->dev.parent = &platform_bus
| |->pdev->dev.bus = &platform_bus_type
| |->insert_resource
| |->device_add(&s3c_device_i2c0->dev)
| | //创建/sys/devices/s3c2410-i2c.0文件
| |->kobject_add(&dev->kobj, dev->kobj.parent, NULL)
| | /* /sys/devices/platform/s3c2410-i2c.0下建立
| | 链接subsystem和bus,他们指向/sys/bus/platform */
| | /* /sys/bus/platform/devices/下建立链接s3c2410-i2c.0
| | 指向/sys/devices/platform/s3c2410-i2c.0 */
| |->bus_add_device(&platform_bus)
|
|->i2c_adap_s3c_init //I2C adapter驱动注册
| |->platform_driver_register(&s3c24xx_i2c_driver)
| |->drv->driver.bus = &platform_bus_type
| |->drv->driver.probe = platform_drv_probe
| |->drv->driver.remove = platform_drv_remove
| |->drv->driver.shutdown = platform_drv_shutdown
| |->driver_register(&s3c24xx_i2c_driver->driver)
| |->driver_find
| |->bus_add_driver
| |->kobject_init_and_add//在/sys/bus/platform/drivers/目录下创建s3c-i2c目录
| |->driver_attach(s3c24xx_i2c_driver->driver)
| |->bus_for_each_dev
| |->__driver_attach(dev,drv)
| |->driver_match_device
| |->driver_probe_device
| |->really_probe // 用户空间呈现出驱动和设备的关系
| | /*建立/sys/bus/platform/drivers/s3c2410-i2c.0/s3c2410-i2c.0
| | 链接,指向/sys/devices/platform/s3c2410-i2c.0
| | 建立/sys/devices/platform/s3c2410-i2c.0/driver链接
| | 指向/sys/bus/platform/drivers/s3c2410-i2c.0 */
| |->driver_sysfs_add
| |->drv->probe(dev)
| | |/* */
| | |->s3c24xx_i2c_probe
| | |->init_waitqueue_head
| | |->clk_enable
| | |->platform_get_resource
| | |->request_mem_region
| | |->ioremap
| | |->s3c24xx_i2c_init //i2c控制器初始化
| | |->i2c_add_numbered_adapter
| | | |->i2c_register_adapter
| | | |->device_register //i2c adapter注册到i2c bus
| | | |->i2c_scan_static_board_info
| | | |->i2c_new_device()
| | | |->device_register //i2c clint注册到i2c bus
| |
| |
| |
| |
| |->driver_bound //
|
|
|->i2c_dev_init //
| |->register_chrdev()
| |->class_create(THIS_MODULE, "i2c-dev")
| |->i2c_add_driver(&i2cdev_driver)
| |->i2c_register_driver
| |->driver->driver.owner = owner
| |->driver->driver.bus = &i2c_bus_type
| |->driver_register // i2cdev_driver注册到i2c bus