diff --git a/renderdoc/driver/gl/gl_common.h b/renderdoc/driver/gl/gl_common.h index 88de18314..9d11820bf 100644 --- a/renderdoc/driver/gl/gl_common.h +++ b/renderdoc/driver/gl/gl_common.h @@ -90,6 +90,7 @@ enum GLChunkType GEN_TEXTURE, BIND_TEXTURE, + BIND_IMAGE_TEXTURE, ACTIVE_TEXTURE, TEXSTORAGE1D, TEXSTORAGE2D, @@ -186,6 +187,7 @@ enum GLChunkType VERTEXDIVISOR, UNIFORM_MATRIX, UNIFORM_VECTOR, + DISPATCH_COMPUTE, DRAWARRAYS, DRAWARRAYS_INSTANCED, DRAWARRAYS_INSTANCEDBASEINSTANCE, diff --git a/renderdoc/driver/gl/gl_driver.cpp b/renderdoc/driver/gl/gl_driver.cpp index e7f1f16e9..1d97e2881 100644 --- a/renderdoc/driver/gl/gl_driver.cpp +++ b/renderdoc/driver/gl/gl_driver.cpp @@ -43,6 +43,7 @@ const char *GLChunkNames[] = "glGenTextures", "glBindTexture", + "glBindImageTexture", "glActiveTexture", "glTexStorage1D", "glTexStorage2D", @@ -139,6 +140,7 @@ const char *GLChunkNames[] = "glVertexBindingDivisor", "glUniformMatrix*", "glUniformVector*", + "glDispatchCompute", "glDrawArrays", "glDrawArraysInstanced", "glDrawArraysInstancedBaseInstance", @@ -1423,6 +1425,9 @@ void WrappedOpenGL::ProcessChunk(uint64_t offset, GLChunkType context) case BIND_TEXTURE: Serialise_glBindTexture(eGL_NONE, 0); break; + case BIND_IMAGE_TEXTURE: + Serialise_glBindImageTexture(0, 0, 0, 0, 0, eGL_NONE, eGL_NONE); + break; case TEXSTORAGE1D: Serialise_glTextureStorage1DEXT(0, eGL_NONE, 0, eGL_NONE, 0); break; @@ -1700,6 +1705,9 @@ void WrappedOpenGL::ProcessChunk(uint64_t offset, GLChunkType context) case UNIFORM_VECTOR: Serialise_glUniformVector(0, 0, NULL, UNIFORM_UNKNOWN); break; + case DISPATCH_COMPUTE: + Serialise_glDispatchCompute(0, 0, 0); + break; case DRAWARRAYS: Serialise_glDrawArrays(eGL_NONE, 0, 0); break; diff --git a/renderdoc/driver/gl/gl_driver.h b/renderdoc/driver/gl/gl_driver.h index be94d295f..4895fc965 100644 --- a/renderdoc/driver/gl/gl_driver.h +++ b/renderdoc/driver/gl/gl_driver.h @@ -520,6 +520,7 @@ class WrappedOpenGL IMPLEMENT_FUNCTION_SERIALISED(void *, glMapBufferRange(GLenum target, GLintptr offset, GLsizeiptr length, GLbitfield access)); IMPLEMENT_FUNCTION_SERIALISED(GLboolean, glUnmapBuffer(GLenum target)); + IMPLEMENT_FUNCTION_SERIALISED(void, glDispatchCompute(GLuint num_groups_x, GLuint num_groups_y, GLuint num_groups_z)); IMPLEMENT_FUNCTION_SERIALISED(void, glClearBufferfv(GLenum buffer, GLint drawbuffer, const GLfloat *value)); IMPLEMENT_FUNCTION_SERIALISED(void, glClearBufferiv(GLenum buffer, GLint drawbuffer, const GLint *value)); IMPLEMENT_FUNCTION_SERIALISED(void, glClearBufferuiv(GLenum buffer, GLint drawbuffer, const GLuint *value)); diff --git a/renderdoc/driver/gl/gl_hookset.h b/renderdoc/driver/gl/gl_hookset.h index abf71690e..9da727e94 100644 --- a/renderdoc/driver/gl/gl_hookset.h +++ b/renderdoc/driver/gl/gl_hookset.h @@ -219,6 +219,7 @@ struct GLHookSet PFNGLBINDVERTEXBUFFERPROC glBindVertexBuffer; PFNGLVERTEXBINDINGDIVISORPROC glVertexBindingDivisor; PFNGLGETCOMPRESSEDTEXIMAGEPROC glGetCompressedTexImage; + PFNGLBINDIMAGETEXTUREPROC glBindImageTexture; PFNGLGENSAMPLERSPROC glGenSamplers; PFNGLBINDSAMPLERPROC glBindSampler; PFNGLDELETESAMPLERSPROC glDeleteSamplers; @@ -230,6 +231,7 @@ struct GLHookSet PFNGLSAMPLERPARAMETERIUIVPROC glSamplerParameterIuiv; PFNGLPATCHPARAMETERIPROC glPatchParameteri; PFNGLPATCHPARAMETERFVPROC glPatchParameterfv; + PFNGLDISPATCHCOMPUTEPROC glDispatchCompute; PFNGLCLEARBUFFERFVPROC glClearBufferfv; PFNGLCLEARBUFFERIVPROC glClearBufferiv; PFNGLCLEARBUFFERUIVPROC glClearBufferuiv; diff --git a/renderdoc/driver/gl/gl_hookset_defs.h b/renderdoc/driver/gl/gl_hookset_defs.h index 05f230468..8356b83cc 100644 --- a/renderdoc/driver/gl/gl_hookset_defs.h +++ b/renderdoc/driver/gl/gl_hookset_defs.h @@ -152,7 +152,7 @@ HookExtension(PFNGLRELEASESHADERCOMPILERPROC, glReleaseShaderCompiler); \ HookExtension(PFNGLLINKPROGRAMPROC, glLinkProgram); \ HookExtension(PFNGLPROGRAMPARAMETERIPROC, glProgramParameteri); \ - HookExtension(PFNGLPROGRAMUNIFORMMATRIX4FVPROC, glProgramUniformMatrix4fv); \ + HookExtension(PFNGLPROGRAMUNIFORMMATRIX4FVPROC, glProgramUniformMatrix4fv); \ HookExtension(PFNGLPROGRAMUNIFORM1IPROC, glProgramUniform1i); \ HookExtension(PFNGLPROGRAMUNIFORM1FVPROC, glProgramUniform1fv); \ HookExtension(PFNGLPROGRAMUNIFORM1IVPROC, glProgramUniform1iv); \ @@ -233,6 +233,7 @@ HookExtension(PFNGLBINDVERTEXBUFFERPROC, glBindVertexBuffer); \ HookExtension(PFNGLVERTEXBINDINGDIVISORPROC, glVertexBindingDivisor); \ HookExtension(PFNGLGETCOMPRESSEDTEXIMAGEPROC, glGetCompressedTexImage); \ + HookExtension(PFNGLBINDIMAGETEXTUREPROC, glBindImageTexture); \ HookExtension(PFNGLGENSAMPLERSPROC, glGenSamplers); \ HookExtension(PFNGLBINDSAMPLERPROC, glBindSampler); \ HookExtension(PFNGLDELETESAMPLERSPROC, glDeleteSamplers); \ @@ -244,6 +245,7 @@ HookExtension(PFNGLSAMPLERPARAMETERIUIVPROC, glSamplerParameterIuiv); \ HookExtension(PFNGLPATCHPARAMETERIPROC, glPatchParameteri); \ HookExtension(PFNGLPATCHPARAMETERFVPROC, glPatchParameterfv); \ + HookExtension(PFNGLDISPATCHCOMPUTEPROC, glDispatchCompute); \ HookExtension(PFNGLCLEARBUFFERFVPROC, glClearBufferfv); \ HookExtension(PFNGLCLEARBUFFERIVPROC, glClearBufferiv); \ HookExtension(PFNGLCLEARBUFFERUIVPROC, glClearBufferuiv); \ @@ -395,7 +397,7 @@ HookWrapper1(void, glStencilMask, GLuint, mask); \ HookWrapper3(void, glStencilOp, GLenum, fail, GLenum, zfail, GLenum, zpass); \ HookWrapper1(void, glDisable, GLenum, cap); \ - HookWrapper1(void, glDrawBuffer, GLenum, mode); \ + HookWrapper1(void, glDrawBuffer, GLenum, buf); \ HookWrapper4(void, glDrawElements, GLenum, mode, GLsizei, count, GLenum, type, const void *, indices); \ HookWrapper3(void, glDrawArrays, GLenum, mode, GLint, first, GLsizei, count); \ HookWrapper1(void, glEnable, GLenum, cap); \ @@ -422,7 +424,7 @@ HookWrapper2(void, glPolygonMode, GLenum, face, GLenum, mode); \ HookWrapper2(void, glPolygonOffset, GLfloat, factor, GLfloat, units); \ HookWrapper7(void, glReadPixels, GLint, x, GLint, y, GLsizei, width, GLsizei, height, GLenum, format, GLenum, type, void *, pixels); \ - HookWrapper1(void, glReadBuffer, GLenum, mode); \ + HookWrapper1(void, glReadBuffer, GLenum, src); \ HookWrapper4(void, glScissor, GLint, x, GLint, y, GLsizei, width, GLsizei, height); \ HookWrapper8(void, glTexImage1D, GLenum, target, GLint, level, GLint, internalformat, GLsizei, width, GLint, border, GLenum, format, GLenum, type, const void *, pixels); \ HookWrapper9(void, glTexImage2D, GLenum, target, GLint, level, GLint, internalformat, GLsizei, width, GLsizei, height, GLint, border, GLenum, format, GLenum, type, const void *, pixels); \ @@ -503,7 +505,7 @@ HookWrapper0(void, glReleaseShaderCompiler); \ HookWrapper1(void, glLinkProgram, GLuint, program); \ HookWrapper3(void, glProgramParameteri, GLuint, program, GLenum, pname, GLint, value); \ - HookWrapper5(void, glProgramUniformMatrix4fv, GLuint, program, GLint, location, GLsizei, count, GLboolean, transpose, const GLfloat *, value); \ + HookWrapper5(void, glProgramUniformMatrix4fv, GLuint, program, GLint, location, GLsizei, count, GLboolean, transpose, const GLfloat *, value); \ HookWrapper3(void, glProgramUniform1i, GLuint, program, GLint, location, GLint, v0); \ HookWrapper4(void, glProgramUniform1fv, GLuint, program, GLint, location, GLsizei, count, const GLfloat *, value); \ HookWrapper4(void, glProgramUniform1iv, GLuint, program, GLint, location, GLsizei, count, const GLint *, value); \ @@ -583,6 +585,7 @@ HookWrapper4(void, glBindVertexBuffer, GLuint, bindingindex, GLuint, buffer, GLintptr, offset, GLsizei, stride); \ HookWrapper2(void, glVertexBindingDivisor, GLuint, bindingindex, GLuint, divisor); \ HookWrapper3(void, glGetCompressedTexImage, GLenum, target, GLint, level, void *, img); \ + HookWrapper7(void, glBindImageTexture, GLuint, unit, GLuint, texture, GLint, level, GLboolean, layered, GLint, layer, GLenum, access, GLenum, format); \ HookWrapper2(void, glGenSamplers, GLsizei, count, GLuint *, samplers); \ HookWrapper2(void, glBindSampler, GLuint, unit, GLuint, sampler); \ HookWrapper2(void, glDeleteSamplers, GLsizei, count, const GLuint *, samplers); \ @@ -594,6 +597,7 @@ HookWrapper3(void, glSamplerParameterIuiv, GLuint, sampler, GLenum, pname, const GLuint *, param); \ HookWrapper2(void, glPatchParameteri, GLenum, pname, GLint, value); \ HookWrapper2(void, glPatchParameterfv, GLenum, pname, const GLfloat *, values); \ + HookWrapper3(void, glDispatchCompute, GLuint, num_groups_x, GLuint, num_groups_y, GLuint, num_groups_z); \ HookWrapper3(void, glClearBufferfv, GLenum, buffer, GLint, drawbuffer, const GLfloat *, value); \ HookWrapper3(void, glClearBufferiv, GLenum, buffer, GLint, drawbuffer, const GLint *, value); \ HookWrapper3(void, glClearBufferuiv, GLenum, buffer, GLint, drawbuffer, const GLuint *, value); \ diff --git a/renderdoc/driver/gl/wrappers/gl_draw_funcs.cpp b/renderdoc/driver/gl/wrappers/gl_draw_funcs.cpp index 3ad4a8fcf..9dc2ef633 100644 --- a/renderdoc/driver/gl/wrappers/gl_draw_funcs.cpp +++ b/renderdoc/driver/gl/wrappers/gl_draw_funcs.cpp @@ -26,6 +26,54 @@ #include "common/string_utils.h" #include "../gl_driver.h" +bool WrappedOpenGL::Serialise_glDispatchCompute(GLuint num_groups_x, GLuint num_groups_y, GLuint num_groups_z) +{ + SERIALISE_ELEMENT(uint32_t, X, num_groups_x); + SERIALISE_ELEMENT(uint32_t, Y, num_groups_y); + SERIALISE_ELEMENT(uint32_t, Z, num_groups_z); + + if(m_State <= EXECUTING) + { + m_Real.glDispatchCompute(X, Y, Z); + } + + const string desc = m_pSerialiser->GetDebugStr(); + + vector debugMessages = Serialise_DebugMessages(); + + if(m_State == READING) + { + AddEvent(DISPATCH_COMPUTE, desc); + string name = "glDispatchCompute(" + + ToStr::Get(X) + ", " + + ToStr::Get(Y) + ", " + + ToStr::Get(Z) + ")"; + + FetchDrawcall draw; + draw.name = widen(name); + draw.flags |= eDraw_Dispatch; + + draw.debugMessages = debugMessages; + + AddDrawcall(draw, true); + } + + return true; +} + +void WrappedOpenGL::glDispatchCompute(GLuint num_groups_x, GLuint num_groups_y, GLuint num_groups_z) +{ + m_Real.glDispatchCompute(num_groups_x, num_groups_y, num_groups_z); + + if(m_State == WRITING_CAPFRAME) + { + SCOPED_SERIALISE_CONTEXT(DISPATCH_COMPUTE); + Serialise_glDispatchCompute(num_groups_x, num_groups_y, num_groups_z); + + m_ContextRecord->AddChunk(scope.Get()); + } +} + bool WrappedOpenGL::Serialise_glDrawArrays(GLenum mode, GLint first, GLsizei count) { SERIALISE_ELEMENT(GLenum, Mode, mode); diff --git a/renderdoc/driver/gl/wrappers/gl_texture_funcs.cpp b/renderdoc/driver/gl/wrappers/gl_texture_funcs.cpp index aae4f41df..6063a5018 100644 --- a/renderdoc/driver/gl/wrappers/gl_texture_funcs.cpp +++ b/renderdoc/driver/gl/wrappers/gl_texture_funcs.cpp @@ -176,6 +176,45 @@ void WrappedOpenGL::glBindTexture(GLenum target, GLuint texture) } } +bool WrappedOpenGL::Serialise_glBindImageTexture(GLuint unit, GLuint texture, GLint level, GLboolean layered, GLint layer, GLenum access, GLenum format) +{ + SERIALISE_ELEMENT(uint32_t, Unit, unit); + SERIALISE_ELEMENT(ResourceId, texid, GetResourceManager()->GetID(TextureRes(GetCtx(), texture))); + SERIALISE_ELEMENT(int32_t, Level, level); + SERIALISE_ELEMENT(bool, Layered, layered == GL_TRUE); + SERIALISE_ELEMENT(int32_t, Layer, layer); + SERIALISE_ELEMENT(GLenum, Access, access); + SERIALISE_ELEMENT(GLenum, Format, format); + + if(m_State <= EXECUTING) + { + GLResource tex = GetResourceManager()->GetLiveResource(texid); + + m_Real.glBindImageTexture(Unit, tex.name, Level, Layered, Layer, Access, Format); + } + + return true; +} + +void WrappedOpenGL::glBindImageTexture(GLuint unit, GLuint texture, GLint level, GLboolean layered, GLint layer, GLenum access, GLenum format) +{ + m_Real.glBindImageTexture(unit, texture, level, layered, layer, access, format); + + if(m_State >= WRITING) + { + Chunk *chunk = NULL; + + { + SCOPED_SERIALISE_CONTEXT(BIND_IMAGE_TEXTURE); + Serialise_glBindImageTexture(unit, texture, level, layered, layer, access, format); + + chunk = scope.Get(); + } + + m_ContextRecord->AddChunk(chunk); + } +} + bool WrappedOpenGL::Serialise_glTextureView(GLuint texture, GLenum target, GLuint origtexture, GLenum internalformat, GLuint minlevel, GLuint numlevels, GLuint minlayer, GLuint numlayers) { SERIALISE_ELEMENT(GLenum, Target, target);