diff --git a/src/mapi/glapi/gen/gl_API.xml b/src/mapi/glapi/gen/gl_API.xml index 7a02da38796..07589bca753 100644 --- a/src/mapi/glapi/gen/gl_API.xml +++ b/src/mapi/glapi/gen/gl_API.xml @@ -1156,7 +1156,7 @@ + marshal_call_after="_mesa_glthread_Begin(ctx);"> @@ -1371,7 +1371,7 @@ + marshal_call_after="_mesa_glthread_End(ctx);"> diff --git a/src/mesa/main/glthread.c b/src/mesa/main/glthread.c index c72a1fa0a0e..673134260e6 100644 --- a/src/mesa/main/glthread.c +++ b/src/mesa/main/glthread.c @@ -214,6 +214,8 @@ _mesa_glthread_init(struct gl_context *ctx) /* glthread takes over all L3 pinning */ ctx->st->pin_thread_counter = ST_L3_PINNING_DISABLED; + _mesa_glthread_update_draw_always_async(ctx); + /* Execute the thread initialization function in the thread. */ struct util_queue_fence fence; util_queue_fence_init(&fence); diff --git a/src/mesa/main/glthread.h b/src/mesa/main/glthread.h index b772d874697..c202e3c16a3 100644 --- a/src/mesa/main/glthread.h +++ b/src/mesa/main/glthread.h @@ -186,6 +186,7 @@ struct glthread_state /** Whether GLThread is enabled. */ bool enabled; bool inside_begin_end; + bool draw_always_async; /** Display lists. */ GLenum16 ListMode; /**< Zero if not inside display list, else list mode. */ diff --git a/src/mesa/main/glthread_draw.c b/src/mesa/main/glthread_draw.c index 9af7e296c68..c84f8394117 100644 --- a/src/mesa/main/glthread_draw.c +++ b/src/mesa/main/glthread_draw.c @@ -467,9 +467,7 @@ draw_arrays(GLenum mode, GLint first, GLsizei count, GLsizei instance_count, * for possible GL errors. */ if (!user_buffer_mask || count <= 0 || instance_count <= 0 || - /* This will just generate GL_INVALID_OPERATION, as it should. */ - ctx->GLThread.inside_begin_end || - (!compiled_into_dlist && ctx->GLThread.ListMode)) { + ctx->GLThread.draw_always_async) { draw_arrays_async(ctx, mode, first, count, instance_count, baseinstance); return; } @@ -543,7 +541,7 @@ _mesa_marshal_MultiDrawArrays(GLenum mode, const GLint *first, struct glthread_attrib_binding buffers[VERT_ATTRIB_MAX]; unsigned user_buffer_mask = ctx->API == API_OPENGL_CORE || draw_count <= 0 || - ctx->GLThread.inside_begin_end ? 0 : get_user_buffer_mask(ctx); + ctx->GLThread.draw_always_async ? 0 : get_user_buffer_mask(ctx); if (user_buffer_mask) { unsigned min_index = ~0; @@ -879,12 +877,9 @@ draw_elements(GLenum mode, GLsizei count, GLenum type, const GLvoid *indices, * This is also an error path. Zero counts should still call the driver * for possible GL errors. */ - if (count <= 0 || instance_count <= 0 || + if (ctx->GLThread.draw_always_async || count <= 0 || instance_count <= 0 || !is_index_type_valid(type) || - (!user_buffer_mask && !has_user_indices) || - /* This will just generate GL_INVALID_OPERATION, as it should. */ - ctx->GLThread.inside_begin_end || - (!compiled_into_dlist && ctx->GLThread.ListMode)) { + (!user_buffer_mask && !has_user_indices)) { draw_elements_async(ctx, mode, count, type, indices, instance_count, basevertex, baseinstance); return; @@ -1122,7 +1117,7 @@ _mesa_marshal_MultiDrawElementsBaseVertex(GLenum mode, const GLsizei *count, * a GL error, we don't upload anything. */ if (draw_count > 0 && is_index_type_valid(type) && - !ctx->GLThread.inside_begin_end) { + !ctx->GLThread.draw_always_async) { user_buffer_mask = ctx->API == API_OPENGL_CORE ? 0 : get_user_buffer_mask(ctx); has_user_indices = vao->CurrentElementBufferName == 0; } diff --git a/src/mesa/main/glthread_marshal.h b/src/mesa/main/glthread_marshal.h index 69f4f2a62cd..1aab57de21c 100644 --- a/src/mesa/main/glthread_marshal.h +++ b/src/mesa/main/glthread_marshal.h @@ -142,6 +142,16 @@ _mesa_glthread_has_non_vbo_vertices_or_indices_or_indirect(const struct gl_conte (vao->UserPointerMask & vao->BufferEnabled)); } +static inline void +_mesa_glthread_update_draw_always_async(struct gl_context *ctx) +{ + /* Executing erroneous cases will just generate GL_INVALID_OPERATION. */ + ctx->GLThread.draw_always_async = + ctx->API == API_OPENGL_CORE || + ctx->GLThread.inside_begin_end || + ctx->GLThread.ListMode; +} + static inline unsigned _mesa_buffer_enum_to_count(GLenum buffer) { @@ -879,8 +889,10 @@ _mesa_glthread_CallLists(struct gl_context *ctx, GLsizei n, GLenum type, static inline void _mesa_glthread_NewList(struct gl_context *ctx, GLuint list, GLenum mode) { - if (!ctx->GLThread.ListMode) + if (!ctx->GLThread.ListMode) { ctx->GLThread.ListMode = MIN2(mode, 0xffff); + _mesa_glthread_update_draw_always_async(ctx); + } } static inline void @@ -890,6 +902,7 @@ _mesa_glthread_EndList(struct gl_context *ctx) return; ctx->GLThread.ListMode = 0; + _mesa_glthread_update_draw_always_async(ctx); /* Track the last display list change. */ p_atomic_set(&ctx->GLThread.LastDListChangeBatchIndex, ctx->GLThread.next); @@ -938,4 +951,18 @@ _mesa_glthread_DeleteFramebuffers(struct gl_context *ctx, GLsizei n, } } +static inline void +_mesa_glthread_Begin(struct gl_context *ctx) +{ + ctx->GLThread.inside_begin_end = true; + _mesa_glthread_update_draw_always_async(ctx); +} + +static inline void +_mesa_glthread_End(struct gl_context *ctx) +{ + ctx->GLThread.inside_begin_end = false; + _mesa_glthread_update_draw_always_async(ctx); +} + #endif /* MARSHAL_H */