From 3f6ac850fcce75b79076c4ed9d4688d0fa8b708e Mon Sep 17 00:00:00 2001 From: Stanislav Vorobiov Date: Fri, 21 Feb 2014 16:19:31 +0400 Subject: [PATCH] VIGS/YaGL: Using same OpenGL env variable VIGS and YaGL should use the same env variable, so that they could create compatible contexts Change-Id: Ibe63f5d8abdb281a71f62118af0d0413ea8c8a7d --- hw/vigs/vigs_gl_backend.c | 15 +++ hw/vigs/vigs_gl_backend.h | 17 +++ hw/vigs/vigs_gl_backend_glx.c | 130 ++++++++++++++++++-- hw/yagl/yagl_drivers/egl_glx/yagl_egl_glx.c | 20 +-- 4 files changed, 165 insertions(+), 17 deletions(-) diff --git a/hw/vigs/vigs_gl_backend.c b/hw/vigs/vigs_gl_backend.c index a9443e2428..de3d99cef0 100644 --- a/hw/vigs/vigs_gl_backend.c +++ b/hw/vigs/vigs_gl_backend.c @@ -1316,6 +1316,17 @@ bool vigs_gl_backend_init(struct vigs_gl_backend *gl_backend) return false; } + if (!gl_backend->is_gl_2) { + gl_backend->GenVertexArrays(1, &gl_backend->vao); + + if (!gl_backend->vao) { + VIGS_LOG_CRITICAL("cannot create VAO"); + goto fail; + } + + gl_backend->BindVertexArray(gl_backend->vao); + } + gl_backend->tex_prog_vs_id = vigs_gl_create_shader(gl_backend, g_vs_tex_source, GL_VERTEX_SHADER); @@ -1436,6 +1447,10 @@ void vigs_gl_backend_cleanup(struct vigs_gl_backend *gl_backend) gl_backend->DeleteShader(gl_backend->tex_prog_fs_id); gl_backend->DeleteProgram(gl_backend->tex_prog_id); + if (!gl_backend->is_gl_2) { + gl_backend->DeleteVertexArrays(1, &gl_backend->vao); + } + gl_backend->make_current(gl_backend, false); } diff --git a/hw/vigs/vigs_gl_backend.h b/hw/vigs/vigs_gl_backend.h index 8a5163ba81..8a4109acfa 100644 --- a/hw/vigs/vigs_gl_backend.h +++ b/hw/vigs/vigs_gl_backend.h @@ -45,6 +45,8 @@ struct vigs_gl_backend struct winsys_gl_info ws_info; + bool is_gl_2; + bool (*has_current)(struct vigs_gl_backend */*gl_backend*/); bool (*make_current)(struct vigs_gl_backend */*gl_backend*/, @@ -117,6 +119,19 @@ struct vigs_gl_backend void (GLAPIENTRY* Uniform4fv)(GLint location, GLsizei count, const GLfloat* value); void (GLAPIENTRY* UniformMatrix4fv)(GLint location, GLsizei count, GLboolean transpose, const GLfloat* value); + /* + * @} + */ + + /* + * OpenGL 3.1+ core functions and extensions. + * @{ + */ + + void (GLAPIENTRY* GenVertexArrays)(GLsizei n, GLuint* arrays); + void (GLAPIENTRY* BindVertexArray)(GLuint array); + void (GLAPIENTRY* DeleteVertexArrays)(GLsizei n, const GLuint* arrays); + /* * @} */ @@ -137,6 +152,8 @@ struct vigs_gl_backend * Other. */ + GLuint vao; + GLuint tex_prog_vs_id; GLuint tex_prog_fs_id; GLuint tex_prog_id; diff --git a/hw/vigs/vigs_gl_backend_glx.c b/hw/vigs/vigs_gl_backend_glx.c index 4e1e62d94a..6d6c24287c 100644 --- a/hw/vigs/vigs_gl_backend_glx.c +++ b/hw/vigs/vigs_gl_backend_glx.c @@ -84,6 +84,7 @@ struct vigs_gl_backend_glx PFNGLXDESTROYCONTEXTPROC glXDestroyContext; PFNGLXMAKECONTEXTCURRENTPROC glXMakeContextCurrent; PFNGLXGETCURRENTCONTEXTPROC glXGetCurrentContext; + PFNGLXCREATENEWCONTEXTPROC glXCreateNewContext; /* GLX_ARB_create_context */ PFNGLXCREATECONTEXTATTRIBSARBPROC glXCreateContextAttribsARB; @@ -95,6 +96,100 @@ struct vigs_gl_backend_glx GLXContext read_pixels_ctx; }; +static bool vigs_gl_backend_glx_check_gl_version(struct vigs_gl_backend_glx *gl_backend_glx, + bool *is_gl_2) +{ + int config_attribs[] = + { + GLX_DOUBLEBUFFER, True, + GLX_RED_SIZE, 8, + GLX_GREEN_SIZE, 8, + GLX_BLUE_SIZE, 8, + GLX_ALPHA_SIZE, 8, + GLX_BUFFER_SIZE, 32, + GLX_DEPTH_SIZE, 24, + GLX_STENCIL_SIZE, 8, + GLX_RENDER_TYPE, GLX_RGBA_BIT, + GLX_DRAWABLE_TYPE, GLX_PBUFFER_BIT, + None + }; + int ctx_attribs[] = + { + GLX_CONTEXT_MAJOR_VERSION_ARB, 3, + GLX_CONTEXT_MINOR_VERSION_ARB, 1, + GLX_RENDER_TYPE, GLX_RGBA_TYPE, + GLX_CONTEXT_PROFILE_MASK_ARB, GLX_CONTEXT_CORE_PROFILE_BIT_ARB, + None + }; + bool res = false; + const char *tmp; + int n = 0; + GLXFBConfig *configs = NULL; + GLXContext ctx = NULL; + + tmp = getenv("GL_VERSION"); + + if (tmp) { + if (strcmp(tmp, "2") == 0) { + VIGS_LOG_INFO("GL_VERSION forces OpenGL version to 2.1"); + *is_gl_2 = true; + res = true; + } else if (strcmp(tmp, "3_1") == 0) { + VIGS_LOG_INFO("GL_VERSION forces OpenGL version to 3.1"); + *is_gl_2 = false; + res = true; + } else if (strcmp(tmp, "3_1_es3") == 0) { + VIGS_LOG_INFO("GL_VERSION forces OpenGL version to 3.1 ES3"); + *is_gl_2 = false; + res = true; + } else if (strcmp(tmp, "3_2") == 0) { + VIGS_LOG_INFO("GL_VERSION forces OpenGL version to 3.2"); + *is_gl_2 = false; + res = true; + } else { + VIGS_LOG_CRITICAL("Bad GL_VERSION value = %s", tmp); + } + + goto out; + } + + configs = gl_backend_glx->glXChooseFBConfig(gl_backend_glx->dpy, + DefaultScreen(gl_backend_glx->dpy), + config_attribs, + &n); + + if (n <= 0) { + VIGS_LOG_ERROR("glXChooseFBConfig failed"); + goto out; + } + + ctx = gl_backend_glx->glXCreateContextAttribsARB(gl_backend_glx->dpy, + configs[0], + NULL, + True, + ctx_attribs); + + *is_gl_2 = (ctx == NULL); + res = true; + + if (ctx) { + VIGS_LOG_INFO("Using OpenGL 3.1+ core"); + } else { + VIGS_LOG_INFO("glXCreateContextAttribsARB failed, using OpenGL 2.1"); + } + +out: + if (ctx) { + gl_backend_glx->glXMakeContextCurrent(gl_backend_glx->dpy, 0, 0, NULL); + gl_backend_glx->glXDestroyContext(gl_backend_glx->dpy, ctx); + } + if (configs) { + XFree(configs); + } + + return res; +} + static GLXFBConfig vigs_gl_backend_glx_get_config(struct vigs_gl_backend_glx *gl_backend_glx) { int config_attribs[] = @@ -180,19 +275,28 @@ static bool vigs_gl_backend_glx_create_context(struct vigs_gl_backend_glx *gl_ba int attribs[] = { GLX_CONTEXT_MAJOR_VERSION_ARB, 3, - GLX_CONTEXT_MINOR_VERSION_ARB, 0, + GLX_CONTEXT_MINOR_VERSION_ARB, 1, GLX_RENDER_TYPE, GLX_RGBA_TYPE, + GLX_CONTEXT_PROFILE_MASK_ARB, GLX_CONTEXT_CORE_PROFILE_BIT_ARB, None }; - *ctx = gl_backend_glx->glXCreateContextAttribsARB(gl_backend_glx->dpy, - config, - share_ctx, - True, - attribs); + if (gl_backend_glx->base.is_gl_2) { + *ctx = gl_backend_glx->glXCreateNewContext(gl_backend_glx->dpy, + config, + GLX_RGBA_TYPE, + share_ctx, + True); + } else { + *ctx = gl_backend_glx->glXCreateContextAttribsARB(gl_backend_glx->dpy, + config, + share_ctx, + True, + attribs); + } if (!*ctx) { - VIGS_LOG_CRITICAL("glXCreateContextAttribsARB failed"); + VIGS_LOG_CRITICAL("glXCreateContextAttribsARB/glXCreateNewContext failed"); return false; } @@ -312,6 +416,7 @@ struct vigs_backend *vigs_gl_backend_create(void *display) VIGS_GLX_GET_PROC(PFNGLXDESTROYCONTEXTPROC, glXDestroyContext); VIGS_GLX_GET_PROC(PFNGLXMAKECONTEXTCURRENTPROC, glXMakeContextCurrent); VIGS_GLX_GET_PROC(PFNGLXGETCURRENTCONTEXTPROC, glXGetCurrentContext); + VIGS_GLX_GET_PROC(PFNGLXCREATENEWCONTEXTPROC, glXCreateNewContext); VIGS_GLX_GET_PROC(PFNGLXCREATECONTEXTATTRIBSARBPROC, glXCreateContextAttribsARB); VIGS_GL_GET_PROC(GenTextures, glGenTextures); @@ -375,6 +480,17 @@ struct vigs_backend *vigs_gl_backend_create(void *display) gl_backend_glx->dpy = x_display; + if (!vigs_gl_backend_glx_check_gl_version(gl_backend_glx, + &gl_backend_glx->base.is_gl_2)) { + goto fail2; + } + + if (!gl_backend_glx->base.is_gl_2) { + VIGS_GL_GET_PROC(GenVertexArrays, glGenVertexArrays); + VIGS_GL_GET_PROC(BindVertexArray, glBindVertexArray); + VIGS_GL_GET_PROC(DeleteVertexArrays, glDeleteVertexArrays); + } + config = vigs_gl_backend_glx_get_config(gl_backend_glx); if (!config) { diff --git a/hw/yagl/yagl_drivers/egl_glx/yagl_egl_glx.c b/hw/yagl/yagl_drivers/egl_glx/yagl_egl_glx.c index bca0887372..8f687a8c10 100644 --- a/hw/yagl/yagl_drivers/egl_glx/yagl_egl_glx.c +++ b/hw/yagl/yagl_drivers/egl_glx/yagl_egl_glx.c @@ -168,27 +168,27 @@ static bool yagl_egl_glx_get_gl_version(struct yagl_egl_glx *egl_glx, YAGL_EGL_GLX_ENTER(yagl_egl_glx_get_gl_version, NULL); - tmp = getenv("YAGL_GL_VERSION"); + tmp = getenv("GL_VERSION"); if (tmp) { - if (strcmp(tmp, "gl_2") == 0) { - YAGL_LOG_INFO("YAGL_GL_VERSION forces OpenGL version to 2.1"); + if (strcmp(tmp, "2") == 0) { + YAGL_LOG_INFO("GL_VERSION forces OpenGL version to 2.1"); *version = yagl_gl_2; res = true; - } else if (strcmp(tmp, "gl_3_1") == 0) { - YAGL_LOG_INFO("YAGL_GL_VERSION forces OpenGL version to 3.1"); + } else if (strcmp(tmp, "3_1") == 0) { + YAGL_LOG_INFO("GL_VERSION forces OpenGL version to 3.1"); *version = yagl_gl_3_1; res = true; - } else if (strcmp(tmp, "gl_3_1_es3") == 0) { - YAGL_LOG_INFO("YAGL_GL_VERSION forces OpenGL version to 3.1 ES3"); + } else if (strcmp(tmp, "3_1_es3") == 0) { + YAGL_LOG_INFO("GL_VERSION forces OpenGL version to 3.1 ES3"); *version = yagl_gl_3_1_es3; res = true; - } else if (strcmp(tmp, "gl_3_2") == 0) { - YAGL_LOG_INFO("YAGL_GL_VERSION forces OpenGL version to 3.2"); + } else if (strcmp(tmp, "3_2") == 0) { + YAGL_LOG_INFO("GL_VERSION forces OpenGL version to 3.2"); *version = yagl_gl_3_2; res = true; } else { - YAGL_LOG_CRITICAL("Bad YAGL_GL_VERSION value = %s", tmp); + YAGL_LOG_CRITICAL("Bad GL_VERSION value = %s", tmp); } goto out; -- 2.34.1