forked from Mirrors/openclonk
wGL: Allow OpenGL debugging
This introduces a new command line parameter "--debug-opengl", which will create special debug OpenGL contexts and attach a callback that the driver will invoke when it detects a problem. The callback will then write the error message to the logfile, and break into the debugger if one is attached. Currently only works on Windows.issue1247
parent
00a24846cc
commit
cac94659d0
|
@ -116,6 +116,7 @@ public:
|
|||
int32_t NoOffscreenBlits; // if set, all blits to non-primary-surfaces are emulated
|
||||
int32_t MultiSampling; // multisampling samples
|
||||
int32_t AutoFrameSkip; // if true, gfx frames are skipped when they would slow down the game
|
||||
int32_t DebugOpenGL; // if true, enables OpenGL debugging
|
||||
|
||||
void CompileFunc(StdCompiler *pComp);
|
||||
};
|
||||
|
|
|
@ -259,6 +259,8 @@ void C4Application::ParseCommandLine(int argc, char * argv[])
|
|||
{"record", no_argument, 0, 'r'},
|
||||
|
||||
{"lobby", required_argument, 0, 'l'},
|
||||
|
||||
{"debug-opengl", no_argument, &Config.Graphics.DebugOpenGL, 1},
|
||||
{0, 0, 0, 0}
|
||||
};
|
||||
int option_index = 0;
|
||||
|
|
|
@ -36,6 +36,61 @@
|
|||
#include <stdio.h>
|
||||
#include <math.h>
|
||||
|
||||
namespace
|
||||
{
|
||||
const char *MsgSourceToStr(GLenum source)
|
||||
{
|
||||
switch (source)
|
||||
{
|
||||
case GL_DEBUG_SOURCE_API_ARB: return "API";
|
||||
case GL_DEBUG_SOURCE_WINDOW_SYSTEM_ARB: return "window system";
|
||||
case GL_DEBUG_SOURCE_SHADER_COMPILER_ARB: return "shader compiler";
|
||||
case GL_DEBUG_SOURCE_THIRD_PARTY_ARB: return "third party";
|
||||
case GL_DEBUG_SOURCE_APPLICATION_ARB: return "application";
|
||||
case GL_DEBUG_SOURCE_OTHER_ARB: return "other";
|
||||
default: return "<unknown>";
|
||||
}
|
||||
}
|
||||
|
||||
const char *MsgTypeToStr(GLenum type)
|
||||
{
|
||||
switch (type)
|
||||
{
|
||||
case GL_DEBUG_TYPE_ERROR_ARB: return "error";
|
||||
case GL_DEBUG_TYPE_DEPRECATED_BEHAVIOR_ARB: return "deprecation warning";
|
||||
case GL_DEBUG_TYPE_UNDEFINED_BEHAVIOR_ARB: return "undefined behavior warning";
|
||||
case GL_DEBUG_TYPE_PORTABILITY_ARB: return "portability warning";
|
||||
case GL_DEBUG_TYPE_PERFORMANCE_ARB: return "performance warning";
|
||||
case GL_DEBUG_TYPE_OTHER_ARB: return "other message";
|
||||
default: return "unknown message";
|
||||
}
|
||||
}
|
||||
|
||||
const char *MsgSeverityToStr(GLenum severity)
|
||||
{
|
||||
switch (severity)
|
||||
{
|
||||
case GL_DEBUG_SEVERITY_HIGH_ARB: return "high";
|
||||
case GL_DEBUG_SEVERITY_MEDIUM_ARB: return "medium";
|
||||
case GL_DEBUG_SEVERITY_LOW_ARB: return "low";
|
||||
default: return "<unknown>";
|
||||
}
|
||||
}
|
||||
|
||||
void APIENTRY OpenGLDebugProc(GLenum source, GLenum type, GLuint id, GLenum severity, GLsizei length, const char* message, const void* userParam)
|
||||
{
|
||||
const char *msg_source = MsgSourceToStr(source);
|
||||
const char *msg_type = MsgTypeToStr(type);
|
||||
const char *msg_severity = MsgSeverityToStr(severity);
|
||||
|
||||
DebugLogF(" gl: %s severity %s %s: %s", msg_severity, msg_source, msg_type, message);
|
||||
#ifdef USE_WIN32_WINDOWS
|
||||
if (IsDebuggerPresent() && severity == GL_DEBUG_SEVERITY_HIGH_ARB)
|
||||
BREAKPOINT_HERE;
|
||||
#endif
|
||||
}
|
||||
}
|
||||
|
||||
CStdGL::CStdGL():
|
||||
pMainCtx(0)
|
||||
{
|
||||
|
@ -153,6 +208,11 @@ CStdGLCtx *CStdGL::CreateContext(C4Window * pWindow, C4AbstractApp *pApp)
|
|||
bool first_ctx = !pMainCtx;
|
||||
if (first_ctx) pMainCtx = pCtx;
|
||||
bool success = pCtx->Init(pWindow, pApp);
|
||||
if (Config.Graphics.DebugOpenGL && glDebugMessageCallbackARB)
|
||||
{
|
||||
glDebugMessageCallbackARB(&OpenGLDebugProc, nullptr);
|
||||
glEnable(GL_DEBUG_OUTPUT_SYNCHRONOUS_ARB);
|
||||
}
|
||||
// First context: Log some information about hardware/drivers
|
||||
// Must log after context creation to get valid results
|
||||
if (first_ctx)
|
||||
|
@ -186,6 +246,11 @@ CStdGLCtx *CStdGL::CreateContext(HWND hWindow, C4AbstractApp *pApp)
|
|||
{
|
||||
delete pCtx; Error(" gl: Error creating secondary context!"); return NULL;
|
||||
}
|
||||
if (Config.Graphics.DebugOpenGL && glDebugMessageCallbackARB)
|
||||
{
|
||||
glDebugMessageCallbackARB(&OpenGLDebugProc, nullptr);
|
||||
glEnable(GL_DEBUG_OUTPUT_SYNCHRONOUS_ARB);
|
||||
}
|
||||
if (!pMainCtx)
|
||||
{
|
||||
pMainCtx = pCtx;
|
||||
|
|
|
@ -306,7 +306,20 @@ bool CStdGLCtx::Init(C4Window * pWindow, C4AbstractApp *pApp, HWND hWindow)
|
|||
else
|
||||
{
|
||||
// create context
|
||||
hrc = wglCreateContext(hDC);
|
||||
if (Config.Graphics.DebugOpenGL && wglCreateContextAttribsARB)
|
||||
{
|
||||
const int attribs[] = {
|
||||
WGL_CONTEXT_FLAGS_ARB, WGL_CONTEXT_DEBUG_BIT_ARB,
|
||||
0
|
||||
};
|
||||
DebugLog(" gl: Creating debug context.");
|
||||
hrc = wglCreateContextAttribsARB(hDC, 0, attribs);
|
||||
}
|
||||
else
|
||||
{
|
||||
hrc = wglCreateContext(hDC);
|
||||
}
|
||||
|
||||
if(!hrc)
|
||||
{
|
||||
pGL->Error(" gl: Error creating gl context");
|
||||
|
|
Loading…
Reference in New Issue