The Road to Linux Kernel - platform driver interface

    技术2026-02-15  24

    platform driver驱动,下面这样的方式是其中一种注册方式, 驱动会注册到形如**__initcall**的段中,然后在start_kernel时进行调用。

    static struct platform_driver tegra_ahb_driver = { .probe = tegra_ahb_probe, .driver = { .name = DRV_NAME, .of_match_table = tegra_ahb_of_match, .pm = &tegra_ahb_pm, }, }; module_platform_driver(tegra_ahb_driver);

    调用关系如下,在initcall_levels这个结构体中,保存了每个section的起始与结束地址

    static initcall_entry_t *initcall_levels[] __initdata = { __initcall0_start, __initcall1_start, __initcall2_start, __initcall3_start, __initcall4_start, __initcall5_start, __initcall6_start, __initcall7_start, __initcall_end, }; start_kernel arch_call_rest_init rest_init kernel_init kernel_init_freeable do_basic_setup do_initcalls static void __init do_initcall_level(int level) { initcall_entry_t *fn; strcpy(initcall_command_line, saved_command_line); parse_args(initcall_level_names[level], initcall_command_line, __start___param, __stop___param - __start___param, level, level, NULL, &repair_env_string); trace_initcall_level(initcall_level_names[level]); for (fn = initcall_levels[level]; fn < initcall_levels[level+1]; fn++) do_one_initcall(initcall_from_entry(fn)); }

    其中就会调用platform_driver_register,调用关系如下, 最终就会调用之前注册的probe函数,观察probe函数的入参dev,那么dev是什么时候分配的?

    platform_driver_register __platform_driver_register driver_register bus_add_driver driver_attach bus_for_each_dev __driver_attach device_driver_attach driver_probe_device driver_probe_device really_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; }

    以arm64为例,简单过一下通过device tree动态生成device的过程

    解析设备树 start_kernel setup_arch setup_machine_fdt unflatten_device_tree __unflatten_device_tree unflatten_dt_nodes populate_node of_node_init populate_properties 生成platform device of_platform_default_populate_init of_platform_default_populate of_platform_populate of_platform_bus_create of_platform_device_create_pdata of_device_alloc of_device_add device_add
    Processed: 0.010, SQL: 9