From 928f352c94dfa083679f50dfd9e9b93114fc8764 Mon Sep 17 00:00:00 2001 From: GPUCode <47210458+GPUCode@users.noreply.github.com> Date: Thu, 7 Sep 2023 21:42:22 +0300 Subject: [PATCH] renderer_gl: Use explicit bindings (#6940) * renderer_gl: Use explicit bindings * gl_state: Match shadow order with vulkan --- .../renderer_opengl/gl_shader_gen.cpp | 34 ++++---- .../renderer_opengl/gl_shader_manager.cpp | 78 ------------------- src/video_core/renderer_opengl/gl_state.h | 14 ++-- 3 files changed, 24 insertions(+), 102 deletions(-) diff --git a/src/video_core/renderer_opengl/gl_shader_gen.cpp b/src/video_core/renderer_opengl/gl_shader_gen.cpp index 71c571d6f..df1f32ca0 100644 --- a/src/video_core/renderer_opengl/gl_shader_gen.cpp +++ b/src/video_core/renderer_opengl/gl_shader_gen.cpp @@ -26,7 +26,7 @@ using VSOutputAttributes = RasterizerRegs::VSOutputAttributes; namespace OpenGL { -const std::string UniformBlockDef = Pica::Shader::BuildShaderUniformDefinitions(); +const std::string UniformBlockDef = Pica::Shader::BuildShaderUniformDefinitions("binding = 0,"); static std::string GetVertexInterfaceDeclaration(bool is_output, bool separable_shader) { std::string out; @@ -1375,22 +1375,22 @@ in vec4 gl_FragCoord; layout(location = 0) out vec4 color; -uniform sampler2D tex0; -uniform sampler2D tex1; -uniform sampler2D tex2; -uniform sampler2D tex_normal; //< Used for custom normal maps -uniform samplerCube tex_cube; -uniform samplerBuffer texture_buffer_lut_lf; -uniform samplerBuffer texture_buffer_lut_rg; -uniform samplerBuffer texture_buffer_lut_rgba; +layout(binding = 0) uniform sampler2D tex0; +layout(binding = 1) uniform sampler2D tex1; +layout(binding = 2) uniform sampler2D tex2; +layout(binding = 3) uniform samplerBuffer texture_buffer_lut_lf; +layout(binding = 4) uniform samplerBuffer texture_buffer_lut_rg; +layout(binding = 5) uniform samplerBuffer texture_buffer_lut_rgba; +layout(binding = 6) uniform samplerCube tex_cube; +layout(binding = 7) uniform sampler2D tex_normal; -layout(r32ui) uniform readonly uimage2D shadow_texture_px; -layout(r32ui) uniform readonly uimage2D shadow_texture_nx; -layout(r32ui) uniform readonly uimage2D shadow_texture_py; -layout(r32ui) uniform readonly uimage2D shadow_texture_ny; -layout(r32ui) uniform readonly uimage2D shadow_texture_pz; -layout(r32ui) uniform readonly uimage2D shadow_texture_nz; -layout(r32ui) uniform uimage2D shadow_buffer; +layout(binding = 0, r32ui) uniform readonly uimage2D shadow_texture_px; +layout(binding = 1, r32ui) uniform readonly uimage2D shadow_texture_nx; +layout(binding = 2, r32ui) uniform readonly uimage2D shadow_texture_py; +layout(binding = 3, r32ui) uniform readonly uimage2D shadow_texture_ny; +layout(binding = 4, r32ui) uniform readonly uimage2D shadow_texture_pz; +layout(binding = 5, r32ui) uniform readonly uimage2D shadow_texture_nz; +layout(binding = 6, r32ui) uniform uimage2D shadow_buffer; )"; out += UniformBlockDef; @@ -1773,7 +1773,7 @@ std::optional GenerateVertexShader( out += R"( #define uniforms vs_uniforms -layout (std140) uniform vs_config { +layout (binding = 1, std140) uniform vs_config { pica_uniforms uniforms; }; diff --git a/src/video_core/renderer_opengl/gl_shader_manager.cpp b/src/video_core/renderer_opengl/gl_shader_manager.cpp index 10904a5ed..ba0b992e0 100644 --- a/src/video_core/renderer_opengl/gl_shader_manager.cpp +++ b/src/video_core/renderer_opengl/gl_shader_manager.cpp @@ -87,72 +87,6 @@ static std::tuple BuildVSConfigFromRaw( return {PicaVSConfig{raw.GetRawShaderConfig().vs, setup}, setup}; } -static void SetShaderUniformBlockBinding(GLuint shader, const char* name, - Pica::Shader::UniformBindings binding, - std::size_t expected_size) { - const GLuint ub_index = glGetUniformBlockIndex(shader, name); - if (ub_index == GL_INVALID_INDEX) { - return; - } - GLint ub_size = 0; - glGetActiveUniformBlockiv(shader, ub_index, GL_UNIFORM_BLOCK_DATA_SIZE, &ub_size); - ASSERT_MSG(static_cast(ub_size) == expected_size, - "Uniform block size did not match! Got {}, expected {}", static_cast(ub_size), - expected_size); - glUniformBlockBinding(shader, ub_index, static_cast(binding)); -} - -static void SetShaderUniformBlockBindings(GLuint shader) { - SetShaderUniformBlockBinding(shader, "shader_data", Pica::Shader::UniformBindings::Common, - sizeof(Pica::Shader::UniformData)); - SetShaderUniformBlockBinding(shader, "vs_config", Pica::Shader::UniformBindings::VS, - sizeof(Pica::Shader::VSUniformData)); -} - -static void SetShaderSamplerBinding(GLuint shader, const char* name, - TextureUnits::TextureUnit binding) { - GLint uniform_tex = glGetUniformLocation(shader, name); - if (uniform_tex != -1) { - glUniform1i(uniform_tex, binding.id); - } -} - -static void SetShaderImageBinding(GLuint shader, const char* name, GLuint binding) { - GLint uniform_tex = glGetUniformLocation(shader, name); - if (uniform_tex != -1) { - glUniform1i(uniform_tex, static_cast(binding)); - } -} - -static void SetShaderSamplerBindings(GLuint shader) { - OpenGLState cur_state = OpenGLState::GetCurState(); - GLuint old_program = std::exchange(cur_state.draw.shader_program, shader); - cur_state.Apply(); - - // Set the texture samplers to correspond to different texture units - SetShaderSamplerBinding(shader, "tex0", TextureUnits::PicaTexture(0)); - SetShaderSamplerBinding(shader, "tex1", TextureUnits::PicaTexture(1)); - SetShaderSamplerBinding(shader, "tex2", TextureUnits::PicaTexture(2)); - SetShaderSamplerBinding(shader, "tex_cube", TextureUnits::TextureCube); - SetShaderSamplerBinding(shader, "tex_normal", TextureUnits::TextureNormalMap); - - // Set the texture samplers to correspond to different lookup table texture units - SetShaderSamplerBinding(shader, "texture_buffer_lut_lf", TextureUnits::TextureBufferLUT_LF); - SetShaderSamplerBinding(shader, "texture_buffer_lut_rg", TextureUnits::TextureBufferLUT_RG); - SetShaderSamplerBinding(shader, "texture_buffer_lut_rgba", TextureUnits::TextureBufferLUT_RGBA); - - SetShaderImageBinding(shader, "shadow_buffer", ImageUnits::ShadowBuffer); - SetShaderImageBinding(shader, "shadow_texture_px", ImageUnits::ShadowTexturePX); - SetShaderImageBinding(shader, "shadow_texture_nx", ImageUnits::ShadowTextureNX); - SetShaderImageBinding(shader, "shadow_texture_py", ImageUnits::ShadowTexturePY); - SetShaderImageBinding(shader, "shadow_texture_ny", ImageUnits::ShadowTextureNY); - SetShaderImageBinding(shader, "shadow_texture_pz", ImageUnits::ShadowTexturePZ); - SetShaderImageBinding(shader, "shadow_texture_nz", ImageUnits::ShadowTextureNZ); - - cur_state.draw.shader_program = old_program; - cur_state.Apply(); -} - /** * An object representing a shader program staging. It can be either a shader object or a program * object, depending on whether separable program is used. @@ -175,11 +109,6 @@ public: shader.Create(source, type); OGLProgram& program = std::get(shader_or_program); program.Create(true, std::array{shader.handle}); - SetShaderUniformBlockBindings(program.handle); - - if (type == GL_FRAGMENT_SHADER) { - SetShaderSamplerBindings(program.handle); - } } } @@ -192,8 +121,6 @@ public: } void Inject(OGLProgram&& program) { - SetShaderUniformBlockBindings(program.handle); - SetShaderSamplerBindings(program.handle); shader_or_program = std::move(program); } @@ -455,9 +382,6 @@ void ShaderProgramManager::ApplyTo(OpenGLState& state) { auto& disk_cache = impl->disk_cache; disk_cache.SaveDumpToFile(unique_identifier, cached_program.handle, VideoCore::g_hw_shader_accurate_mul); - - SetShaderUniformBlockBindings(cached_program.handle); - SetShaderSamplerBindings(cached_program.handle); } state.draw.shader_program = cached_program.handle; } @@ -586,8 +510,6 @@ void ShaderProgramManager::LoadDiskCache(const std::atomic_bool& stop_loading, OGLProgram shader = GeneratePrecompiledProgram(dump.second, supported_formats, impl->separable); if (shader.handle != 0) { - SetShaderUniformBlockBindings(shader.handle); - SetShaderSamplerBindings(shader.handle); impl->program_cache.emplace(unique_identifier, std::move(shader)); } else { LOG_ERROR(Frontend, "Failed to link Precompiled program!"); diff --git a/src/video_core/renderer_opengl/gl_state.h b/src/video_core/renderer_opengl/gl_state.h index a9cccce34..6a3fb2ea0 100644 --- a/src/video_core/renderer_opengl/gl_state.h +++ b/src/video_core/renderer_opengl/gl_state.h @@ -32,13 +32,13 @@ constexpr TextureUnit TextureColorBuffer{10}; } // namespace TextureUnits namespace ImageUnits { -constexpr GLuint ShadowBuffer = 0; -constexpr GLuint ShadowTexturePX = 1; -constexpr GLuint ShadowTextureNX = 2; -constexpr GLuint ShadowTexturePY = 3; -constexpr GLuint ShadowTextureNY = 4; -constexpr GLuint ShadowTexturePZ = 5; -constexpr GLuint ShadowTextureNZ = 6; +constexpr GLuint ShadowTexturePX = 0; +constexpr GLuint ShadowTextureNX = 1; +constexpr GLuint ShadowTexturePY = 2; +constexpr GLuint ShadowTextureNY = 3; +constexpr GLuint ShadowTexturePZ = 4; +constexpr GLuint ShadowTextureNZ = 5; +constexpr GLuint ShadowBuffer = 6; } // namespace ImageUnits class OpenGLState {