From 5f35382fe36debde51c7ce98bf72ddd52643d1ca Mon Sep 17 00:00:00 2001 From: havoc Date: Sun, 29 Jul 2018 23:12:41 +0000 Subject: [PATCH] Add gl_debug cvar, if enabled the GL context will have GL_ARB_debug_output enabled, which will print in the console. git-svn-id: svn://svn.icculus.org/twilight/trunk/darkplaces@12441 d7cf8633-e32d-0410-b094-e92efae38249 --- gl_backend.c | 33 ++++++++++++++++++++++++++++++++- glquake.h | 6 ++++++ vid.h | 1 + vid_sdl.c | 2 ++ vid_shared.c | 16 ++++++++++++++++ 5 files changed, 57 insertions(+), 1 deletion(-) diff --git a/gl_backend.c b/gl_backend.c index 73c01102..52e392dc 100644 --- a/gl_backend.c +++ b/gl_backend.c @@ -75,6 +75,7 @@ #define MAX_RENDERTARGETS 4 +cvar_t gl_debug = {0, "gl_debug", "0", "enables OpenGL debug output, 0 = off, 1 = HIGH severity only, 2 = also MEDIUM severity, 3 = also LOW severity messages. (note: enabling may not take effect until vid_restart on some drivers)"}; cvar_t gl_paranoid = {0, "gl_paranoid", "0", "enables OpenGL error checking and other tests"}; cvar_t gl_printcheckerror = {0, "gl_printcheckerror", "0", "prints all OpenGL error checks, useful to identify location of driver crashes"}; @@ -151,6 +152,36 @@ void GL_PrintError(int errornumber, const char *filename, int linenumber) break; } } + +static void GLAPIENTRY GL_DebugOutputCallback(GLenum source, GLenum type, GLuint id, GLenum severity, GLsizei length, const GLchar* message, const GLvoid* userParam) +{ + const char *sev = "ENUM?", *typ = "ENUM?", *src = "ENUM?"; + switch (severity) + { + case GL_DEBUG_SEVERITY_LOW_ARB: sev = "LOW"; break; + case GL_DEBUG_SEVERITY_MEDIUM_ARB: sev = "MED"; break; + case GL_DEBUG_SEVERITY_HIGH_ARB: sev = "HIGH"; break; + } + switch (type) + { + case GL_DEBUG_TYPE_ERROR_ARB: typ = "ERROR"; break; + case GL_DEBUG_TYPE_DEPRECATED_BEHAVIOR_ARB: typ = "DEPRECATED"; break; + case GL_DEBUG_TYPE_UNDEFINED_BEHAVIOR_ARB: typ = "UNDEFINED"; break; + case GL_DEBUG_TYPE_PORTABILITY_ARB: typ = "PORTABILITY"; break; + case GL_DEBUG_TYPE_PERFORMANCE_ARB: typ = "PERFORMANCE"; break; + case GL_DEBUG_TYPE_OTHER_ARB: typ = "OTHER"; break; + } + switch (source) + { + case GL_DEBUG_SOURCE_API_ARB: src = "API"; break; + case GL_DEBUG_SOURCE_SHADER_COMPILER_ARB: src = "SHADER"; break; + case GL_DEBUG_SOURCE_WINDOW_SYSTEM_ARB: src = "WIN"; break; + case GL_DEBUG_SOURCE_THIRD_PARTY_ARB: src = "THIRDPARTY"; break; + case GL_DEBUG_SOURCE_APPLICATION_ARB: src = "APP"; break; + case GL_DEBUG_SOURCE_OTHER_ARB: src = "OTHER"; break; + } + Con_Printf("GLDEBUG: %s %s %s: %u: %s\n", sev, typ, src, (unsigned int)id, message); +} #endif #define BACKENDACTIVECHECK if (!gl_state.active) Sys_Error("GL backend function called when backend is not active"); @@ -414,7 +445,7 @@ void gl_backend_init(void) Cvar_RegisterVariable(&r_waterwarp); Cvar_RegisterVariable(&gl_polyblend); Cvar_RegisterVariable(&v_flipped); - Cvar_RegisterVariable(&gl_dither); + Cvar_RegisterVariable(&gl_debug); Cvar_RegisterVariable(&gl_paranoid); Cvar_RegisterVariable(&gl_printcheckerror); diff --git a/glquake.h b/glquake.h index 4026c296..8b296f1e 100644 --- a/glquake.h +++ b/glquake.h @@ -1136,6 +1136,12 @@ void GL_PrintError(int errornumber, const char *filename, int linenumber); #define qglGetVertexAttribfv glGetVertexAttribfv #define qglGetVertexAttribiv glGetVertexAttribiv #define qglGetVertexAttribPointerv glGetVertexAttribPointerv + +extern GLuint(GLAPIENTRY *qglGetDebugMessageLogARB)(GLuint count, GLsizei bufSize, GLenum* sources, GLenum* types, GLuint* ids, GLenum* severities, GLsizei* lengths, GLchar* messageLog); +extern void (GLAPIENTRY *qglDebugMessageCallbackARB)(GLDEBUGPROCARB callback, const GLvoid* userParam); +extern void (GLAPIENTRY *qglDebugMessageControlARB)(GLenum source, GLenum type, GLenum severity, GLsizei count, const GLuint* ids, GLboolean enabled); +extern void (GLAPIENTRY *qglDebugMessageInsertARB)(GLenum source, GLenum type, GLuint id, GLenum severity, GLsizei length, const GLchar* buf); +typedef void (GLAPIENTRY *GLDEBUGPROCARB)(GLenum source, GLenum type, GLuint id, GLenum severity, GLsizei length, const GLchar* message, const GLvoid* userParam); #endif #endif diff --git a/vid.h b/vid.h index e1b14ef1..ac3e17f5 100644 --- a/vid.h +++ b/vid.h @@ -56,6 +56,7 @@ typedef struct viddef_support_s qboolean arb_half_float_pixel; qboolean arb_half_float_vertex; qboolean arb_multisample; + qboolean arb_debug_output; } viddef_support_t; diff --git a/vid_sdl.c b/vid_sdl.c index f01a4e85..d47ffdb0 100644 --- a/vid_sdl.c +++ b/vid_sdl.c @@ -2018,6 +2018,8 @@ static qboolean VID_InitModeGL(viddef_mode_t *mode) SDL_GL_SetAttribute (SDL_GL_CONTEXT_MAJOR_VERSION, 2); SDL_GL_SetAttribute (SDL_GL_CONTEXT_MINOR_VERSION, 0); SDL_GL_SetAttribute (SDL_GL_RETAINED_BACKING, 1); +#else + SDL_GL_SetAttribute(SDL_GL_CONTEXT_FLAGS, (gl_debug.integer > 0 ? SDL_GL_CONTEXT_DEBUG_FLAG : 0)); #endif video_bpp = mode->bitsperpixel; diff --git a/vid_shared.c b/vid_shared.c index f29eea2a..11709033 100644 --- a/vid_shared.c +++ b/vid_shared.c @@ -438,6 +438,11 @@ void (GLAPIENTRY *qglGetIntegeri_v)(GLenum target, GLuint index, GLint* data); void (GLAPIENTRY *qglUniformBlockBinding)(GLuint program, GLuint uniformBlockIndex, GLuint uniformBlockBinding); void (GLAPIENTRY *qglBlendFuncSeparate)(GLenum sfactorRGB, GLenum dfactorRGB, GLenum sfactorAlpha, GLenum dfactorAlpha); + +GLuint (GLAPIENTRY *qglGetDebugMessageLogARB)(GLuint count, GLsizei bufSize, GLenum* sources, GLenum* types, GLuint* ids, GLenum* severities, GLsizei* lengths, GLchar* messageLog); +void (GLAPIENTRY *qglDebugMessageCallbackARB)(GLDEBUGPROCARB callback, const GLvoid* userParam); +void (GLAPIENTRY *qglDebugMessageControlARB)(GLenum source, GLenum type, GLenum severity, GLsizei count, const GLuint* ids, GLboolean enabled); +void (GLAPIENTRY *qglDebugMessageInsertARB)(GLenum source, GLenum type, GLuint id, GLenum severity, GLsizei length, const GLchar* buf); #endif #if _MSC_VER >= 1400 @@ -758,6 +763,16 @@ static dllfunction_t blendfuncseparatefuncs[] = {NULL, NULL} }; +static dllfunction_t debugoutputfuncs[] = +{ + {"glDebugMessageControlARB", (void **)&qglDebugMessageControlARB}, + {"glDebugMessageInsertARB", (void **)&qglDebugMessageInsertARB}, + {"glDebugMessageCallbackARB", (void **)&qglDebugMessageCallbackARB}, + {"glGetDebugMessageLogARB", (void **)&qglGetDebugMessageLogARB}, + {"glGetPointerv", (void **)&qglGetPointerv}, + {NULL, NULL} +}; + #endif void VID_ClearExtensions(void) @@ -829,6 +844,7 @@ void VID_CheckExtensions(void) vid.support.arb_half_float_pixel = GL_CheckExtension("GL_ARB_half_float_pixel", NULL, "-nohalffloatpixel", false); vid.support.arb_half_float_vertex = GL_CheckExtension("GL_ARB_half_float_vertex", NULL, "-nohalffloatvertex", false); vid.support.arb_multisample = GL_CheckExtension("GL_ARB_multisample", multisamplefuncs, "-nomultisample", false); + vid.support.arb_debug_output = GL_CheckExtension("GL_ARB_debug_output", debugoutputfuncs, "-nogldebugoutput", false); vid.allowalphatocoverage = false; // COMMANDLINEOPTION: GL: -noshaders disables use of OpenGL 2.0 shaders (which allow pixel shader effects, can improve per pixel lighting performance and capabilities) -- 2.39.2