我是靠谱客的博主 粗暴缘分,最近开发中收集的这篇文章主要介绍04-Weston DRM Backend,觉得挺不错的,现在分享给大家,希望可以做个参考。

概述

调用过程:

weston/compositor/main.c

wet_main-->...
        const struct weston_option core_options[] = {
        { WESTON_OPTION_STRING, "backend", 'B', &backend }//根据-B参数加载指定的backend
        ...
        cmdline = copy_command_line(argc, argv);
        parse_options(core_options, ARRAY_LENGTH(core_options), &argc, argv);
    load_backend-->        
        load_drm_backend-->
             weston_compositor_load_backend(c, WESTON_BACKEND_DRM,&config.base)-->
                 backend_init = weston_load_module(backend_map[backend], "weston_backend_init");
                     -->weston_module_path_from_env
                     -->dlope
                     ...
                     -->weston_backend_init
                         -->drm_backend_create

1、load_backend()函数

调用不同的函数加载不同的.so。DRM后端是load_drm_backend()函数,和drm-backend.so

static int
load_backend(struct weston_compositor *compositor, const char *backend,
         int *argc, char **argv, struct weston_config *config)
{
    if (strstr(backend, "headless-backend.so"))
        return load_headless_backend(compositor, argc, argv, config);
    else if (strstr(backend, "rdp-backend.so"))
        return load_rdp_backend(compositor, argc, argv, config);
    else if (strstr(backend, "fbdev-backend.so"))
        return load_fbdev_backend(compositor, argc, argv, config);
    else if (strstr(backend, "drm-backend.so"))
        return load_drm_backend(compositor, argc, argv, config);
    else if (strstr(backend, "x11-backend.so"))
        return load_x11_backend(compositor, argc, argv, config);
    else if (strstr(backend, "wayland-backend.so"))
        return load_wayland_backend(compositor, argc, argv, config);

    weston_log("Error: unknown backend "%s"n", backend);
    return -1;
}

2、weston_compositor_load_backend()

weston_compositor_load_backend()函数通过WESTON_BACKEND_DRM参数调用到DRM,

libweston.h中定义了枚举类型,包括几种常见的后端。

 

 

enum weston_compositor_backend {
    WESTON_BACKEND_DRM,
    WESTON_BACKEND_FBDEV,
    WESTON_BACKEND_HEADLESS,
    WESTON_BACKEND_RDP,
    WESTON_BACKEND_WAYLAND,
    WESTON_BACKEND_X11,
};

3、weston_load_module()

weston_load_module加载drm-backend.so,路径./build/libweston/backend-drm/drm-backend.so

backend_init = weston_load_module(backend_map[backend], "weston_backend_init");

static const char * const backend_map[] = {
    [WESTON_BACKEND_DRM] =      "drm-backend.so",
    [WESTON_BACKEND_FBDEV] =    "fbdev-backend.so",
    [WESTON_BACKEND_HEADLESS] = "headless-backend.so",
    [WESTON_BACKEND_RDP] =      "rdp-backend.so",
    [WESTON_BACKEND_WAYLAND] =  "wayland-backend.so",
    [WESTON_BACKEND_X11] =      "x11-backend.so",
};

4、drm_backend_create()

drm_backend源码:libweston/backend-drm/

weston/libweston/backend-drm$ tree -L 1
.
├── drm.c
├── drm-gbm.c
├── drm-internal.h
├── drm-virtual.c
├── fb.c
├── kms.c
├── libbacklight.c
├── libbacklight.h
├── meson.build
├── modes.c
├── state-helpers.c
├── state-propose.c
├── vaapi-recorder.c
└── vaapi-recorder.h

0 directories, 14 files

./libweston/backend-drm/drm.c:3234:weston_backend_init-->drm_backend_create

drm_backend_create:
-->weston_launcher_connect
...
     if (config->specific_device)
        drm_device = open_specific_drm_device(b, config->specific_device);
    else
        drm_device = find_primary_gpu(b, seat_id);
    if (drm_device == NULL) {
        weston_log("no drm device foundn");
        goto err_udev;
    }
...
-->init_kms_caps//kms.c
    -->drmGetCap(b->drm.fd, DRM_CAP_TIMESTAMP_MONOTONIC, &cap);
    -->drmGetCap(b->drm.fd, DRM_CAP_CURSOR_WIDTH, &cap);
    -->drmGetCap(b->drm.fd, DRM_CAP_CURSOR_HEIGHT, &cap);
    -->drmSetClientCap(b->drm.fd, DRM_CLIENT_CAP_UNIVERSAL_PLANES, 1);//If set to 1, the DRM core will expose all planes (overlay, primary, and
cursor) to userspace.
    -->drmGetCap(b->drm.fd, DRM_CAP_CRTC_IN_VBLANK_EVENT, &cap);
    -->drmSetClientCap(b->drm.fd, DRM_CLIENT_CAP_ATOMIC, 1);//If set to 1, the DRM core will expose atomic properties to userspace
    -->drmSetClientCap(b->drm.fd, DRM_CLIENT_CAP_WRITEBACK_CONNECTORS, 1);//以上这些都是libdrm中的定义了
...//render 选择CPU使用pixman,GPU使用egl
if (b->use_pixman) {
        if (init_pixman(b) < 0) {
            weston_log("failed to initialize pixman renderern");
            goto err_udev_dev;
        }
    } else {
        if (init_egl(b) < 0) {//drm-gbm.c
            weston_log("failed to initialize egln");
            goto err_udev_dev;
        }

流程一

open_specific_drm_device()函数最终调用到libdrm库中的drmModeGetResources

-->udev_device_new_from_subsystem_sysname
-->drm_device_is_kms
    -->weston_launcher_open
    -->drmModeGetResources//libdrm

流程二

find_primary_gpu()

-->e = udev_enumerate_new(b->udev);
-->udev_enumerate_add_match_subsystem(e, "drm");
-->udev_enumerate_add_match_sysname(e, "card[0-9]*");
-->udev_enumerate_scan_devices(e);
-->path = udev_list_entry_get_name(entry);
-->device = udev_device_new_from_syspath(b->udev, path);

-->drm_device_is_kms(b, device)
    -->weston_launcher_open
    -->drmModeGetResources//libdrm

流程三

render的选择

1)init_pixman()

-->pixman_renderer_init//pixman-renderer.c

2)init_egl()

init_egl()
-->create_gbm_device
    -->weston_load_module("gl-renderer.so", "gl_renderer_interface");
    -->dlopen("libglapi.so.0", RTLD_LAZY | RTLD_GLOBAL);
    -->gbm_create_device

-->drm_backend_create_gl_renderer

最后

以上就是粗暴缘分为你收集整理的04-Weston DRM Backend的全部内容,希望文章能够帮你解决04-Weston DRM Backend所遇到的程序开发问题。

如果觉得靠谱客网站的内容还不错,欢迎将靠谱客网站推荐给程序员好友。

本图文内容来源于网友提供,作为学习参考使用,或来自网络收集整理,版权属于原作者所有。
点赞(53)

评论列表共有 0 条评论

立即
投稿
返回
顶部