efi-framebuffer device的注册和显示参数的传递

在drivers/firmware/efi/linstub/arm-stub.c 中efi_entry 中会调用setup_graphics
static struct screen_info *setup_graphics(efi_system_table_t *sys_table_arg)
{
    efi_guid_t gop_proto = EFI_GRAPHICS_OUTPUT_PROTOCOL_GUID;
    efi_status_t status;
    unsigned long size;
    void **gop_handle = NULL;
    struct screen_info *si = NULL;

    size = 0;
    status = efi_call_early(locate_handle, EFI_LOCATE_BY_PROTOCOL,
                &gop_proto, NULL, &size, gop_handle);
    if (status == EFI_BUFFER_TOO_SMALL) {
        si = alloc_screen_info(sys_table_arg);
        if (!si)
            return NULL;
        efi_setup_gop(sys_table_arg, si, &gop_proto, size);
    }
    return si;
}
在setup_graphics 中会parse bios 中传递过来的参数,并保存到si中。
然后在init_screen_info 中让screen_info指向si,这样screen_info中就保持从bios中传递过来的framebuffer的参数
static void __init init_screen_info(void)
{
    struct screen_info *si;

    if (screen_info_table != EFI_INVALID_TABLE_ADDR) {
        si = early_memremap_ro(screen_info_table, sizeof(*si));
        if (!si) {
            pr_err("Could not map screen_info config table\n");
            return;
        }
        screen_info = *si;
        early_memunmap(si, sizeof(*si));

        /* dummycon on ARM needs non-zero values for columns/lines */
        screen_info.orig_video_cols = 80;
        screen_info.orig_video_lines = 25;
    }

    if (screen_info.orig_video_isVGA == VIDEO_TYPE_EFI &&
        memblock_is_map_memory(screen_info.lfb_base))
        memblock_mark_nomap(screen_info.lfb_base, screen_info.lfb_size);
}
最后会调用register_gop_device 来注册platform_device
static int __init register_gop_device(void)
{
    void *pd;

    if (screen_info.orig_video_isVGA != VIDEO_TYPE_EFI)
        return 0;

    pd = platform_device_register_data(NULL, "efi-framebuffer", 0,
                       &screen_info, sizeof(screen_info));
    return PTR_ERR_OR_ZERO(pd);
}
subsys_initcall(register_gop_device);

这样当用户打开CONFIG_FB_EFI的时候,就会生成/dev/fbn device。通过对这个device的read和read 就可以将画面显示到fbcon上。

static struct platform_driver efifb_driver = {
    .driver = {
        .name = "efi-framebuffer",
    },
    .probe = efifb_probe,
    .remove = efifb_remove,
};

builtin_platform_driver(efifb_driver);
efi-framebuffer 对应的driver是在/drivers/video/fbdev/efifb.c中。
其通过在efifb_probe中调用register_framebuffer来得到对console的控制权。




评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值