From 30256805784450b8bb9d4dabfb56226271ca9d24 Mon Sep 17 00:00:00 2001 From: Eric Anholt Date: Fri, 22 Feb 2013 10:43:40 -0800 Subject: [PATCH] mesa: Add support for GL_ARB_debug_output with dynamic ID allocation. We can emit messages now without always having to use the same ID for each, or having a giant table of all possible errors in mtypes.h. Reviewed-by: Jordan Justen --- src/mesa/main/errors.c | 54 +++++++++++++++++++++++++++++++++++++++++++++++--- src/mesa/main/errors.h | 10 +++++++++- 2 files changed, 60 insertions(+), 4 deletions(-) diff --git a/src/mesa/main/errors.c b/src/mesa/main/errors.c index 2954710f84a..3c720bc5500 100644 --- a/src/mesa/main/errors.c +++ b/src/mesa/main/errors.c @@ -36,8 +36,11 @@ #include "hash.h" #include "mtypes.h" #include "version.h" +#include "hash_table.h" +#include "glapi/glthread.h" - +_glthread_DECLARE_STATIC_MUTEX(DynamicIDMutex); +static GLuint NextDynamicID = 1; struct gl_debug_severity { @@ -107,6 +110,30 @@ gl_enum_to_debug_severity(GLenum e) return i; } +/** + * Handles generating a GL_ARB_debug_output message ID generated by the GL or + * GLSL compiler. + * + * The GL API has this "ID" mechanism, where the intention is to allow a + * client to filter in/out messages based on source, type, and ID. Of course, + * building a giant enum list of all debug output messages that Mesa might + * generate is ridiculous, so instead we have our caller pass us a pointer to + * static storage where the ID should get stored. This ID will be shared + * across all contexts for that message (which seems like a desirable + * property, even if it's not expected by the spec), but note that it won't be + * the same between executions if messages aren't generated in the same order. + */ +static void +debug_get_id(GLuint *id) +{ + if (!(*id)) { + _glthread_LOCK_MUTEX(DynamicIDMutex); + if (!(*id)) + *id = NextDynamicID++; + _glthread_UNLOCK_MUTEX(DynamicIDMutex); + } +} + /* * We store a bitfield in the hash table, with five possible values total. * @@ -682,8 +709,8 @@ _mesa_free_errors_data(struct gl_context *ctx) /* Tear down state for filtering debug messages. */ for (s = 0; s < MESA_DEBUG_SOURCE_COUNT; s++) for (t = 0; t < MESA_DEBUG_TYPE_COUNT; t++) { - _mesa_HashDeleteAll(ClientIDs->Namespaces[s][t].IDs, do_nothing, NULL); - _mesa_DeleteHashTable(ClientIDs->Namespaces[s][t].IDs); + _mesa_HashDeleteAll(ctx->Debug.Namespaces[s][t].IDs, do_nothing, NULL); + _mesa_DeleteHashTable(ctx->Debug.Namespaces[s][t].IDs); for (sev = 0; sev < MESA_DEBUG_SEVERITY_COUNT; sev++) { struct simple_node *node, *tmp; struct gl_debug_severity *entry; @@ -859,6 +886,27 @@ should_output(struct gl_context *ctx, GLenum error, const char *fmtString) return GL_FALSE; } +void +_mesa_gl_debug(struct gl_context *ctx, + GLuint *id, + enum mesa_debug_type type, + enum mesa_debug_severity severity, + const char *fmtString, ...) +{ + char s[MAX_DEBUG_MESSAGE_LENGTH]; + int len; + va_list args; + + debug_get_id(id); + + va_start(args, fmtString); + len = _mesa_vsnprintf(s, MAX_DEBUG_MESSAGE_LENGTH, fmtString, args); + va_end(args); + + _mesa_log_msg(ctx, MESA_DEBUG_SOURCE_API, type, + *id, severity, len, s); +} + /** * Record an OpenGL state error. These usually occur when the user diff --git a/src/mesa/main/errors.h b/src/mesa/main/errors.h index c92ee0a6ee2..aa69931a815 100644 --- a/src/mesa/main/errors.h +++ b/src/mesa/main/errors.h @@ -44,8 +44,9 @@ extern "C" { #endif +#include "mtypes.h" + struct _glapi_table; -struct gl_context; extern void _mesa_init_errors( struct gl_context *ctx ); @@ -66,6 +67,13 @@ extern void _mesa_debug( const struct gl_context *ctx, const char *fmtString, ... ) PRINTFLIKE(2, 3); extern void +_mesa_gl_debug(struct gl_context *ctx, + GLuint *id, + enum mesa_debug_type type, + enum mesa_debug_severity severity, + const char *fmtString, ...) PRINTFLIKE(5, 6); + +extern void _mesa_shader_debug( struct gl_context *ctx, GLenum type, GLuint id, const char *msg, int len ); void GLAPIENTRY -- 2.11.0