Commit d8fc70ea1ed37daedf6686c50e60d86d96a8f708

Ryan C. Gordon 2017-08-24T21:30:53

opengl: add support for GL_KHR_no_error. This is completely untested! Fixes Bugzilla #3721.

diff --git a/include/SDL_video.h b/include/SDL_video.h
index 0700023..97b3aef 100644
--- a/include/SDL_video.h
+++ b/include/SDL_video.h
@@ -202,7 +202,8 @@ typedef enum
     SDL_GL_SHARE_WITH_CURRENT_CONTEXT,
     SDL_GL_FRAMEBUFFER_SRGB_CAPABLE,
     SDL_GL_CONTEXT_RELEASE_BEHAVIOR,
-    SDL_GL_CONTEXT_RESET_NOTIFICATION
+    SDL_GL_CONTEXT_RESET_NOTIFICATION,
+    SDL_GL_CONTEXT_NO_ERROR
 } SDL_GLattr;
 
 typedef enum
diff --git a/src/video/SDL_egl.c b/src/video/SDL_egl.c
index 20884af..6241c49 100644
--- a/src/video/SDL_egl.c
+++ b/src/video/SDL_egl.c
@@ -463,6 +463,18 @@ SDL_EGL_ChooseConfig(_THIS)
         attribs[i++] = _this->gl_config.multisamplesamples;
     }
 
+    if (_this->gl_config.no_error) {
+#ifdef GL_KHR_no_error
+        if (SDL_EGL_HasExtension(_this, SDL_EGL_DISPLAY_EXTENSION, "GL_KHR_no_error")) {
+            attribs[i++] = EGL_CONTEXT_OPENGL_NO_ERROR_KHR;
+            attribs[i++] = _this->gl_config.no_error;
+        } else
+#endif
+        {
+            return SDL_SetError("EGL implementation does not support no_error contexts");
+        }
+    }
+
     if (_this->gl_config.framebuffer_srgb_capable) {
 #ifdef EGL_KHR_gl_colorspace
         if (SDL_EGL_HasExtension(_this, SDL_EGL_DISPLAY_EXTENSION, "EGL_KHR_gl_colorspace")) {
diff --git a/src/video/SDL_sysvideo.h b/src/video/SDL_sysvideo.h
index ff0d222..c3ca82d 100644
--- a/src/video/SDL_sysvideo.h
+++ b/src/video/SDL_sysvideo.h
@@ -331,6 +331,7 @@ struct SDL_VideoDevice
         int release_behavior;
         int reset_notification;
         int framebuffer_srgb_capable;
+        int no_error;
         int retained_backing;
         int driver_loaded;
         char driver_path[256];
diff --git a/src/video/SDL_video.c b/src/video/SDL_video.c
index 7debc48..4c6b45c 100644
--- a/src/video/SDL_video.c
+++ b/src/video/SDL_video.c
@@ -2989,6 +2989,7 @@ SDL_GL_ResetAttributes()
 #endif
     _this->gl_config.flags = 0;
     _this->gl_config.framebuffer_srgb_capable = 0;
+    _this->gl_config.no_error = 0;
     _this->gl_config.release_behavior = SDL_GL_CONTEXT_RELEASE_BEHAVIOR_FLUSH;
     _this->gl_config.reset_notification = SDL_GL_CONTEXT_RESET_NO_NOTIFICATION;
 
@@ -3103,6 +3104,9 @@ SDL_GL_SetAttribute(SDL_GLattr attr, int value)
     case SDL_GL_CONTEXT_RESET_NOTIFICATION:
         _this->gl_config.reset_notification = value;
         break;
+    case SDL_GL_CONTEXT_NO_ERROR:
+        _this->gl_config.no_error = value;
+        break;
     default:
         retval = SDL_SetError("Unknown OpenGL attribute");
         break;
@@ -3307,6 +3311,11 @@ SDL_GL_GetAttribute(SDL_GLattr attr, int *value)
             *value = _this->gl_config.framebuffer_srgb_capable;
             return 0;
         }
+    case SDL_GL_CONTEXT_NO_ERROR:
+        {
+            *value = _this->gl_config.no_error;
+            return 0;
+        }
     default:
         return SDL_SetError("Unknown OpenGL attribute");
     }
diff --git a/src/video/windows/SDL_windowsopengl.c b/src/video/windows/SDL_windowsopengl.c
index d91ca5b..a46c4e4 100644
--- a/src/video/windows/SDL_windowsopengl.c
+++ b/src/video/windows/SDL_windowsopengl.c
@@ -82,6 +82,11 @@
 #define WGL_CONTEXT_RELEASE_BEHAVIOR_FLUSH_ARB          0x2098
 #endif
 
+#ifndef WGL_ARB_create_context_no_error
+#define WGL_ARB_create_context_no_error
+#define WGL_CONTEXT_OPENGL_NO_ERROR_ARB                 0x31B3
+#endif
+
 typedef HGLRC(APIENTRYP PFNWGLCREATECONTEXTATTRIBSARBPROC) (HDC hDC,
                                                             HGLRC
                                                             hShareContext,
@@ -593,6 +598,11 @@ WIN_GL_SetupWindowInternal(_THIS, SDL_Window * window)
         *iAttr++ = _this->gl_config.framebuffer_srgb_capable;
     }
 
+    if (_this->gl_config.no_error) {
+        *iAttr++ = WGL_CONTEXT_OPENGL_NO_ERROR_ARB;
+        *iAttr++ = _this->gl_config.no_error;
+    }
+
     /* We always choose either FULL or NO accel on Windows, because of flaky
        drivers. If the app didn't specify, we use FULL, because that's
        probably what they wanted (and if you didn't care and got FULL, that's
diff --git a/src/video/x11/SDL_x11opengl.c b/src/video/x11/SDL_x11opengl.c
index 8a658df..37267ed 100644
--- a/src/video/x11/SDL_x11opengl.c
+++ b/src/video/x11/SDL_x11opengl.c
@@ -114,6 +114,13 @@ typedef GLXContext(*PFNGLXCREATECONTEXTATTRIBSARBPROC) (Display * dpy,
 #endif
 #endif
 
+#ifndef GLX_ARB_create_context_no_error
+#define GLX_ARB_create_context_no_error
+#ifndef GLX_CONTEXT_OPENGL_NO_ERROR_ARB
+#define GLX_CONTEXT_OPENGL_NO_ERROR_ARB                 0x31B3
+#endif
+#endif
+
 #ifndef GLX_EXT_swap_control
 #define GLX_SWAP_INTERVAL_EXT              0x20F1
 #define GLX_MAX_SWAP_INTERVAL_EXT          0x20F2
@@ -494,6 +501,11 @@ X11_GL_GetAttributes(_THIS, Display * display, int screen, int * attribs, int si
         attribs[i++] = True;  /* always needed, for_FBConfig or not! */
     }
 
+    if (_this->gl_config.no_error) {
+        attribs[i++] = GLX_CONTEXT_OPENGL_NO_ERROR_ARB;
+        attribs[i++] = _this->gl_config.no_error;
+    }
+
     if (_this->gl_config.accelerated >= 0 &&
         _this->gl_data->HAS_GLX_EXT_visual_rating) {
         attribs[i++] = GLX_VISUAL_CAVEAT_EXT;