Implemented the EGL_KHR_create_context extension Implemented EGL_KHR_create_context as described here: www.khronos.org/registry/egl/extensions/KHR/EGL_KHR_create_context.txt A small part of it was already implemented, which was to add support for the EGL_OPENGL_ES3_BIT bit in the EGL_RENDERABLE_TYPE bitfield. Note that the EGL_OPENGL_ES3_BIT is explicitly disabled on Android right now. Change-Id: I10e6222511b29f2d91bd55bfeb0f39bc5b884f89 Reviewed-on: https://swiftshader-review.googlesource.com/5380 Reviewed-by: Nicolas Capens <capn@google.com> Tested-by: Nicolas Capens <capn@google.com>
diff --git a/src/OpenGL/libEGL/libEGL.cpp b/src/OpenGL/libEGL/libEGL.cpp index 7a801d9..610d1c3 100644 --- a/src/OpenGL/libEGL/libEGL.cpp +++ b/src/OpenGL/libEGL/libEGL.cpp
@@ -193,7 +193,8 @@ case EGL_CLIENT_APIS: return success("OpenGL_ES"); case EGL_EXTENSIONS: - return success("EGL_KHR_gl_texture_2D_image " + return success("EGL_KHR_create_context " + "EGL_KHR_gl_texture_2D_image " "EGL_KHR_gl_texture_cubemap_image " "EGL_KHR_gl_renderbuffer_image " "EGL_KHR_fence_sync " @@ -644,22 +645,88 @@ TRACE("(EGLDisplay dpy = %p, EGLConfig config = %p, EGLContext share_context = %p, " "const EGLint *attrib_list = %p)", dpy, config, share_context, attrib_list); - EGLint clientVersion = 1; + EGLint majorVersion = 1; + EGLint minorVersion = 0; + if(attrib_list) { for(const EGLint* attribute = attrib_list; attribute[0] != EGL_NONE; attribute += 2) { - if(attribute[0] == EGL_CONTEXT_CLIENT_VERSION) + switch(attribute[0]) { - clientVersion = attribute[1]; - } - else - { + case EGL_CONTEXT_MAJOR_VERSION_KHR: // This token is an alias for EGL_CONTEXT_CLIENT_VERSION + majorVersion = attribute[1]; + break; + case EGL_CONTEXT_MINOR_VERSION_KHR: + minorVersion = attribute[1]; + break; + case EGL_CONTEXT_FLAGS_KHR: + switch(attribute[1]) + { + case EGL_CONTEXT_OPENGL_DEBUG_BIT_KHR: + // According to the EGL_KHR_create_context spec: + // "Khronos is still defining the expected and required features of debug contexts, so + // implementations are currently free to implement "debug contexts" with little or no debug + // functionality. However, OpenGL and OpenGL ES implementations supporting the GL_KHR_debug + // extension should enable it when this bit is set." + break; + case EGL_CONTEXT_OPENGL_FORWARD_COMPATIBLE_BIT_KHR: + case EGL_CONTEXT_OPENGL_ROBUST_ACCESS_BIT_KHR: + // These bits are for OpenGL contexts only, not OpenGL ES contexts + return error(EGL_BAD_ATTRIBUTE, EGL_NO_CONTEXT); + default: + return error(EGL_BAD_ATTRIBUTE, EGL_NO_CONTEXT); + } + break; + case EGL_CONTEXT_OPENGL_PROFILE_MASK_KHR: + switch(attribute[1]) + { + case EGL_CONTEXT_OPENGL_CORE_PROFILE_BIT_KHR: + case EGL_CONTEXT_OPENGL_COMPATIBILITY_PROFILE_BIT_KHR: + // These bits are for OpenGL contexts only, not OpenGL ES contexts + return error(EGL_BAD_ATTRIBUTE, EGL_NO_CONTEXT); + default: + return error(EGL_BAD_ATTRIBUTE, EGL_NO_CONTEXT); + } + break; + case EGL_CONTEXT_OPENGL_RESET_NOTIFICATION_STRATEGY_KHR: + switch(attribute[1]) + { + case EGL_NO_RESET_NOTIFICATION_KHR: + case EGL_LOSE_CONTEXT_ON_RESET_KHR: + // These bits are for OpenGL contexts only, not OpenGL ES contexts + return error(EGL_BAD_ATTRIBUTE, EGL_NO_CONTEXT); + default: + return error(EGL_BAD_ATTRIBUTE, EGL_NO_CONTEXT); + } + break; + default: return error(EGL_BAD_ATTRIBUTE, EGL_NO_CONTEXT); } } } + switch(majorVersion) + { + case 1: + if(minorVersion != 0 && minorVersion != 1) + { + // 1.X: Only OpenGL ES 1.0 and 1.1 contexts are supported + return error(EGL_BAD_MATCH, EGL_NO_CONTEXT); + } + break; + case 2: + case 3: + if(minorVersion != 0) + { + // 2.X and 3.X: Only OpenGL ES 2.0 and 3.0 contexts are currently supported + return error(EGL_BAD_MATCH, EGL_NO_CONTEXT); + } + break; + default: + return error(EGL_BAD_MATCH, EGL_NO_CONTEXT); + } + egl::Display *display = egl::Display::get(dpy); egl::Context *shareContext = static_cast<egl::Context*>(share_context); @@ -668,12 +735,12 @@ return EGL_NO_CONTEXT; } - if(shareContext && shareContext->getClientVersion() != clientVersion) + if(shareContext && shareContext->getClientVersion() != majorVersion) { return error(EGL_BAD_CONTEXT, EGL_NO_CONTEXT); } - return display->createContext(config, shareContext, clientVersion); + return display->createContext(config, shareContext, majorVersion); } EGLBoolean DestroyContext(EGLDisplay dpy, EGLContext ctx)