summaryrefslogtreecommitdiff
path: root/common.c
diff options
context:
space:
mode:
authorIlia Mirkin <imirkin@alum.mit.edu>2018-02-09 20:49:48 -0500
committerDaniel Stone <daniels@collabora.com>2018-02-16 12:33:32 +0000
commit56c3917ffd1f05942246e2532ca4a5707554a2fc (patch)
treeb648a03a8ead1b859236d819773aafbd9e61154e /common.c
parentc2d4ba86de1bebca536ef03525b067a42106f06e (diff)
downloadkmscube-56c3917ffd1f05942246e2532ca4a5707554a2fc.tar.gz
formats: use weston's egl config matching logic, centralize format
The GBM surface format has to match the DRM mode. Both are used in a couple of places, so unify it so that it's only set in one place. Note that the GBM and DRM formats are identical. Signed-off-by: Ilia Mirkin <imirkin@alum.mit.edu> Reviewed-by: Eric Engestrom <eric.engestrom@imgtec.com> Reviewed-by: Daniel Stone <daniels@collabora.com>
Diffstat (limited to 'common.c')
-rw-r--r--common.c78
1 files changed, 73 insertions, 5 deletions
diff --git a/common.c b/common.c
index b76c994..a092cdb 100644
--- a/common.c
+++ b/common.c
@@ -47,6 +47,7 @@ get_modifiers(uint64_t **mods)
const struct gbm * init_gbm(int drm_fd, int w, int h, uint64_t modifier)
{
gbm.dev = gbm_create_device(drm_fd);
+ gbm.format = GBM_FORMAT_XRGB8888;
#ifndef HAVE_GBM_MODIFIERS
if (modifier != DRM_FORMAT_MOD_INVALID) {
@@ -54,7 +55,7 @@ const struct gbm * init_gbm(int drm_fd, int w, int h, uint64_t modifier)
return NULL;
}
gbm.surface = gbm_surface_create(gbm.dev, w, h,
- GBM_FORMAT_XRGB8888,
+ gbm.format,
GBM_BO_USE_SCANOUT | GBM_BO_USE_RENDERING);
#else
uint64_t *mods;
@@ -66,7 +67,7 @@ const struct gbm * init_gbm(int drm_fd, int w, int h, uint64_t modifier)
count = get_modifiers(&mods);
}
gbm.surface = gbm_surface_create_with_modifiers(gbm.dev, w, h,
- GBM_FORMAT_XRGB8888, mods, count);
+ gbm.format, mods, count);
#endif
if (!gbm.surface) {
@@ -100,9 +101,75 @@ static bool has_ext(const char *extension_list, const char *ext)
}
}
+static int
+match_config_to_visual(EGLDisplay egl_display,
+ EGLint visual_id,
+ EGLConfig *configs,
+ int count)
+{
+ int i;
+
+ for (i = 0; i < count; ++i) {
+ EGLint id;
+
+ if (!eglGetConfigAttrib(egl_display,
+ configs[i], EGL_NATIVE_VISUAL_ID,
+ &id))
+ continue;
+
+ if (id == visual_id)
+ return i;
+ }
+
+ return -1;
+}
+
+static bool
+egl_choose_config(EGLDisplay egl_display, const EGLint *attribs,
+ EGLint visual_id, EGLConfig *config_out)
+{
+ EGLint count = 0;
+ EGLint matched = 0;
+ EGLConfig *configs;
+ int config_index = -1;
+
+ if (!eglGetConfigs(egl_display, NULL, 0, &count) || count < 1) {
+ printf("No EGL configs to choose from.\n");
+ return false;
+ }
+ configs = malloc(count * sizeof *configs);
+ if (!configs)
+ return false;
+
+ if (!eglChooseConfig(egl_display, attribs, configs,
+ count, &matched) || !matched) {
+ printf("No EGL configs with appropriate attributes.\n");
+ goto out;
+ }
+
+ if (!visual_id)
+ config_index = 0;
+
+ if (config_index == -1)
+ config_index = match_config_to_visual(egl_display,
+ visual_id,
+ configs,
+ matched);
+
+ if (config_index != -1)
+ *config_out = configs[config_index];
+
+out:
+ free(configs);
+ if (config_index == -1)
+ return false;
+
+ return true;
+}
+
int init_egl(struct egl *egl, const struct gbm *gbm)
{
- EGLint major, minor, n;
+ EGLint major, minor;
static const EGLint context_attribs[] = {
EGL_CONTEXT_CLIENT_VERSION, 2,
@@ -174,8 +241,9 @@ int init_egl(struct egl *egl, const struct gbm *gbm)
return -1;
}
- if (!eglChooseConfig(egl->display, config_attribs, &egl->config, 1, &n) || n != 1) {
- printf("failed to choose config: %d\n", n);
+ if (!egl_choose_config(egl->display, config_attribs, gbm->format,
+ &egl->config)) {
+ printf("failed to choose config\n");
return -1;
}