{
int i, ret = 0;
ret = platform_device_register(devs[i]);
{
device_initialize(&pdev->dev);//初始化平台设备的dev结构体,为加入设备驱动模型做准备
return platform_device_add(pdev);
}
{
if (!pdev->dev.parent)
pdev->dev.parent = &platform_bus;//如果pdev->dev.parent为空就赋值为platform_bus
dev_set_name(&pdev->dev, "%s.%d", pdev->name, pdev->id);
else
dev_set_name(&pdev->dev, "%s", pdev->name);
struct resource *p, *r = &pdev->resource[i];
r->name = dev_name(&pdev->dev);
if (!p) {
if (resource_type(r) == IORESOURCE_MEM)
p = &iomem_resource;
else if (resource_type(r) == IORESOURCE_IO)
p = &ioport_resource;
}
printk(KERN_ERR
"%s: failed to claim resource %d\n",
dev_name(&pdev->dev), i);
ret = -EBUSY;
goto failed;
}
}
.init_name = "platform",
};
.name = "platform",
.dev_attrs = platform_dev_attrs,
.match = platform_match,
.uevent = platform_uevent,
.pm = &platform_dev_pm_ops,
};
asmlinkage void __init start_kernel(void)
{
......
rest_init();
}
start_kernel()中的函数rest_init()将创建第一个核心线程kernel_thread(init, NULL, CLONE_FS | CLONE_SIGHAND),调用init()函数:
static int init(void * unused)-------------------
{
do_basic_setup();
}
static void __init do_basic_setup(void)-----------------
{
.......
driver_init(); //建立设备模型子系统
}
<./drivers/base/init.c>-------------------------
void __init driver_init(void)
{
platform_bus_init();
}
下面进去看看platform_bus_init();的实现。
int __init platform_bus_init(void)
{
device_register(&platform_bus);//注册platform_bus设备
bus_register(&platform_bus_type);//注册platform bus总线
}
下面看看这个平台总线到底怎么注册的:
int bus_register(struct bus_type *bus)
{
struct bus_type_private *priv;
priv = kzalloc(sizeof(struct bus_type_private), GFP_KERNEL);//分配一个priv结构体
priv->bus = bus;//把priv结构体依附在该总线上
bus->p = priv;//把总线的p指针赋值为priv
BLOCKING_INIT_NOTIFIER_HEAD(&priv->bus_notifier);//初始化通知链的
retval = kobject_set_name(&priv->subsys.kobj, "%s", bus->name);//设置priv->sybsys的name
priv->subsys.kobj.kset = bus_kset;
priv->subsys.kobj.ktype = &bus_ktype;
priv->drivers_autoprobe = 1;
retval = kset_register(&priv->subsys);//注册subsys
retval = bus_create_file(bus, &bus_attr_uevent);//为总线创建属性
/*初始化priv的两个kset,分别存放属于该总线的devices和drivers*/
priv->devices_kset = kset_create_and_add("devices", NULL,&priv->subsys.kobj);
priv->drivers_kset = kset_create_and_add("drivers", NULL,&priv->subsys.kobj);
/*初始化priv的两个链表,该链表链接了该总线的设备与驱动*/
klist_init(&priv->klist_devices, klist_devices_get, klist_devices_put);
klist_init(&priv->klist_drivers, NULL, NULL);
}
上述函数总结起来如下:
建立一条总线,把她加入bus_kset专门存放bus的容器中,然后初始化该总线所用的devices kset,driver kset,devices driver链表,创建总线的属性等,以后在该总线上注册的驱动或者是设备,都会挂载到相应的链表和kset下。