diff options
Diffstat (limited to 'src')
| -rw-r--r-- | src/video_core/renderer_opengl/gl_rasterizer.cpp | 27 | ||||
| -rw-r--r-- | src/video_core/renderer_opengl/gl_rasterizer.h | 14 | ||||
| -rw-r--r-- | src/video_core/renderer_opengl/gl_shader_decompiler.cpp | 5 | ||||
| -rw-r--r-- | src/video_core/renderer_opengl/gl_shader_gen.h | 14 | ||||
| -rw-r--r-- | src/video_core/renderer_opengl/gl_shader_manager.h | 11 |
5 files changed, 59 insertions, 12 deletions
diff --git a/src/video_core/renderer_opengl/gl_rasterizer.cpp b/src/video_core/renderer_opengl/gl_rasterizer.cpp index a778dfc64..28abc563a 100644 --- a/src/video_core/renderer_opengl/gl_rasterizer.cpp +++ b/src/video_core/renderer_opengl/gl_rasterizer.cpp | |||
| @@ -193,6 +193,9 @@ void RasterizerOpenGL::SetupShaders(u8* buffer_ptr, GLintptr buffer_offset, size | |||
| 193 | auto& gpu = Core::System().GetInstance().GPU().Maxwell3D(); | 193 | auto& gpu = Core::System().GetInstance().GPU().Maxwell3D(); |
| 194 | ASSERT_MSG(!gpu.regs.shader_config[0].enable, "VertexA is unsupported!"); | 194 | ASSERT_MSG(!gpu.regs.shader_config[0].enable, "VertexA is unsupported!"); |
| 195 | 195 | ||
| 196 | // Next available bindpoint to use when uploading the const buffers to the GLSL shaders. | ||
| 197 | u32 current_constbuffer_bindpoint = 0; | ||
| 198 | |||
| 196 | for (unsigned index = 1; index < Maxwell::MaxShaderProgram; ++index) { | 199 | for (unsigned index = 1; index < Maxwell::MaxShaderProgram; ++index) { |
| 197 | ptr_pos += sizeof(GLShader::MaxwellUniformData); | 200 | ptr_pos += sizeof(GLShader::MaxwellUniformData); |
| 198 | 201 | ||
| @@ -244,9 +247,13 @@ void RasterizerOpenGL::SetupShaders(u8* buffer_ptr, GLintptr buffer_offset, size | |||
| 244 | UNREACHABLE(); | 247 | UNREACHABLE(); |
| 245 | } | 248 | } |
| 246 | 249 | ||
| 250 | GLuint gl_stage_program = shader_program_manager->GetCurrentProgramStage( | ||
| 251 | static_cast<Maxwell::ShaderStage>(stage)); | ||
| 252 | |||
| 247 | // Configure the const buffers for this shader stage. | 253 | // Configure the const buffers for this shader stage. |
| 248 | SetupConstBuffers(static_cast<Maxwell::ShaderStage>(stage), | 254 | current_constbuffer_bindpoint = |
| 249 | shader_resources.const_buffer_entries); | 255 | SetupConstBuffers(static_cast<Maxwell::ShaderStage>(stage), gl_stage_program, |
| 256 | current_constbuffer_bindpoint, shader_resources.const_buffer_entries); | ||
| 250 | } | 257 | } |
| 251 | 258 | ||
| 252 | shader_program_manager->UseTrivialGeometryShader(); | 259 | shader_program_manager->UseTrivialGeometryShader(); |
| @@ -543,8 +550,9 @@ void RasterizerOpenGL::SamplerInfo::SyncWithConfig(const Tegra::Texture::TSCEntr | |||
| 543 | } | 550 | } |
| 544 | } | 551 | } |
| 545 | 552 | ||
| 546 | void RasterizerOpenGL::SetupConstBuffers(Maxwell::ShaderStage stage, | 553 | u32 RasterizerOpenGL::SetupConstBuffers(Maxwell::ShaderStage stage, GLuint program, |
| 547 | const std::vector<GLShader::ConstBufferEntry>& entries) { | 554 | u32 current_bindpoint, |
| 555 | const std::vector<GLShader::ConstBufferEntry>& entries) { | ||
| 548 | auto& gpu = Core::System::GetInstance().GPU(); | 556 | auto& gpu = Core::System::GetInstance().GPU(); |
| 549 | auto& maxwell3d = gpu.Get3DEngine(); | 557 | auto& maxwell3d = gpu.Get3DEngine(); |
| 550 | 558 | ||
| @@ -568,7 +576,7 @@ void RasterizerOpenGL::SetupConstBuffers(Maxwell::ShaderStage stage, | |||
| 568 | 576 | ||
| 569 | ASSERT_MSG(buffer.enabled, "Attempted to upload disabled constbuffer"); | 577 | ASSERT_MSG(buffer.enabled, "Attempted to upload disabled constbuffer"); |
| 570 | buffer_draw_state.enabled = true; | 578 | buffer_draw_state.enabled = true; |
| 571 | buffer_draw_state.bindpoint = bindpoint; | 579 | buffer_draw_state.bindpoint = current_bindpoint + bindpoint; |
| 572 | 580 | ||
| 573 | VAddr addr = gpu.memory_manager->PhysicalToVirtualAddress(buffer.address); | 581 | VAddr addr = gpu.memory_manager->PhysicalToVirtualAddress(buffer.address); |
| 574 | std::vector<u8> data(used_buffer.GetSize() * sizeof(float)); | 582 | std::vector<u8> data(used_buffer.GetSize() * sizeof(float)); |
| @@ -577,9 +585,18 @@ void RasterizerOpenGL::SetupConstBuffers(Maxwell::ShaderStage stage, | |||
| 577 | glBindBuffer(GL_SHADER_STORAGE_BUFFER, buffer_draw_state.ssbo); | 585 | glBindBuffer(GL_SHADER_STORAGE_BUFFER, buffer_draw_state.ssbo); |
| 578 | glBufferData(GL_SHADER_STORAGE_BUFFER, data.size(), data.data(), GL_DYNAMIC_DRAW); | 586 | glBufferData(GL_SHADER_STORAGE_BUFFER, data.size(), data.data(), GL_DYNAMIC_DRAW); |
| 579 | glBindBuffer(GL_SHADER_STORAGE_BUFFER, 0); | 587 | glBindBuffer(GL_SHADER_STORAGE_BUFFER, 0); |
| 588 | |||
| 589 | // Now configure the bindpoint of the buffer inside the shader | ||
| 590 | std::string buffer_name = used_buffer.GetName(); | ||
| 591 | GLuint index = | ||
| 592 | glGetProgramResourceIndex(program, GL_SHADER_STORAGE_BLOCK, buffer_name.c_str()); | ||
| 593 | if (index != -1) | ||
| 594 | glShaderStorageBlockBinding(program, index, buffer_draw_state.bindpoint); | ||
| 580 | } | 595 | } |
| 581 | 596 | ||
| 582 | state.Apply(); | 597 | state.Apply(); |
| 598 | |||
| 599 | return current_bindpoint + entries.size(); | ||
| 583 | } | 600 | } |
| 584 | 601 | ||
| 585 | void RasterizerOpenGL::BindFramebufferSurfaces(const Surface& color_surface, | 602 | void RasterizerOpenGL::BindFramebufferSurfaces(const Surface& color_surface, |
diff --git a/src/video_core/renderer_opengl/gl_rasterizer.h b/src/video_core/renderer_opengl/gl_rasterizer.h index 1ea0dfa71..548ce0453 100644 --- a/src/video_core/renderer_opengl/gl_rasterizer.h +++ b/src/video_core/renderer_opengl/gl_rasterizer.h | |||
| @@ -87,9 +87,17 @@ private: | |||
| 87 | /// Binds the required textures to OpenGL before drawing a batch. | 87 | /// Binds the required textures to OpenGL before drawing a batch. |
| 88 | void BindTextures(); | 88 | void BindTextures(); |
| 89 | 89 | ||
| 90 | /// Configures the current constbuffers to use for the draw command. | 90 | /* |
| 91 | void SetupConstBuffers(Tegra::Engines::Maxwell3D::Regs::ShaderStage stage, | 91 | * Configures the current constbuffers to use for the draw command. |
| 92 | const std::vector<GLShader::ConstBufferEntry>& entries); | 92 | * @param stage The shader stage to configure buffers for. |
| 93 | * @param program The OpenGL program object that contains the specified stage. | ||
| 94 | * @param current_bindpoint The offset at which to start counting new buffer bindpoints. | ||
| 95 | * @param entries Vector describing the buffers that are actually used in the guest shader. | ||
| 96 | * @returns The next available bindpoint for use in the next shader stage. | ||
| 97 | */ | ||
| 98 | u32 SetupConstBuffers(Tegra::Engines::Maxwell3D::Regs::ShaderStage stage, GLuint program, | ||
| 99 | u32 current_bindpoint, | ||
| 100 | const std::vector<GLShader::ConstBufferEntry>& entries); | ||
| 93 | 101 | ||
| 94 | /// Syncs the viewport to match the guest state | 102 | /// Syncs the viewport to match the guest state |
| 95 | void SyncViewport(const MathUtil::Rectangle<u32>& surfaces_rect, u16 res_scale); | 103 | void SyncViewport(const MathUtil::Rectangle<u32>& surfaces_rect, u16 res_scale); |
diff --git a/src/video_core/renderer_opengl/gl_shader_decompiler.cpp b/src/video_core/renderer_opengl/gl_shader_decompiler.cpp index 9cf2c6a0c..e11711533 100644 --- a/src/video_core/renderer_opengl/gl_shader_decompiler.cpp +++ b/src/video_core/renderer_opengl/gl_shader_decompiler.cpp | |||
| @@ -192,7 +192,7 @@ private: | |||
| 192 | 192 | ||
| 193 | /// Generates code representing a uniform (C buffer) register. | 193 | /// Generates code representing a uniform (C buffer) register. |
| 194 | std::string GetUniform(const Uniform& reg) { | 194 | std::string GetUniform(const Uniform& reg) { |
| 195 | declr_const_buffers[reg.index].MarkAsUsed(reg.index, reg.offset); | 195 | declr_const_buffers[reg.index].MarkAsUsed(reg.index, reg.offset, stage); |
| 196 | return 'c' + std::to_string(reg.index) + '[' + std::to_string(reg.offset) + ']'; | 196 | return 'c' + std::to_string(reg.index) + '[' + std::to_string(reg.offset) + ']'; |
| 197 | } | 197 | } |
| 198 | 198 | ||
| @@ -478,8 +478,7 @@ private: | |||
| 478 | 478 | ||
| 479 | unsigned const_buffer_layout = 0; | 479 | unsigned const_buffer_layout = 0; |
| 480 | for (const auto& entry : GetConstBuffersDeclarations()) { | 480 | for (const auto& entry : GetConstBuffersDeclarations()) { |
| 481 | declarations.AddLine("layout(std430, binding = " + std::to_string(const_buffer_layout) + | 481 | declarations.AddLine("layout(std430) buffer " + entry.GetName()); |
| 482 | ") buffer c" + std::to_string(entry.GetIndex()) + "_buffer"); | ||
| 483 | declarations.AddLine("{"); | 482 | declarations.AddLine("{"); |
| 484 | declarations.AddLine(" float c" + std::to_string(entry.GetIndex()) + "[];"); | 483 | declarations.AddLine(" float c" + std::to_string(entry.GetIndex()) + "[];"); |
| 485 | declarations.AddLine("};"); | 484 | declarations.AddLine("};"); |
diff --git a/src/video_core/renderer_opengl/gl_shader_gen.h b/src/video_core/renderer_opengl/gl_shader_gen.h index 3d9aead74..458032b5c 100644 --- a/src/video_core/renderer_opengl/gl_shader_gen.h +++ b/src/video_core/renderer_opengl/gl_shader_gen.h | |||
| @@ -19,10 +19,13 @@ constexpr size_t MAX_PROGRAM_CODE_LENGTH{0x1000}; | |||
| 19 | using ProgramCode = std::array<u64, MAX_PROGRAM_CODE_LENGTH>; | 19 | using ProgramCode = std::array<u64, MAX_PROGRAM_CODE_LENGTH>; |
| 20 | 20 | ||
| 21 | class ConstBufferEntry { | 21 | class ConstBufferEntry { |
| 22 | using Maxwell = Tegra::Engines::Maxwell3D::Regs; | ||
| 23 | |||
| 22 | public: | 24 | public: |
| 23 | void MarkAsUsed(unsigned index, unsigned offset) { | 25 | void MarkAsUsed(unsigned index, unsigned offset, Maxwell::ShaderStage stage) { |
| 24 | is_used = true; | 26 | is_used = true; |
| 25 | this->index = index; | 27 | this->index = index; |
| 28 | this->stage = stage; | ||
| 26 | max_offset = std::max(max_offset, offset); | 29 | max_offset = std::max(max_offset, offset); |
| 27 | } | 30 | } |
| 28 | 31 | ||
| @@ -38,10 +41,19 @@ public: | |||
| 38 | return max_offset + 1; | 41 | return max_offset + 1; |
| 39 | } | 42 | } |
| 40 | 43 | ||
| 44 | std::string GetName() const { | ||
| 45 | return BufferBaseNames[static_cast<size_t>(stage)] + std::to_string(index); | ||
| 46 | } | ||
| 47 | |||
| 41 | private: | 48 | private: |
| 49 | static constexpr std::array<const char*, Maxwell::MaxShaderStage> BufferBaseNames = { | ||
| 50 | "buffer_vs_c", "buffer_tessc_c", "buffer_tesse_c", "buffer_gs_c", "buffer_fs_c", | ||
| 51 | }; | ||
| 52 | |||
| 42 | bool is_used{}; | 53 | bool is_used{}; |
| 43 | unsigned index{}; | 54 | unsigned index{}; |
| 44 | unsigned max_offset{}; | 55 | unsigned max_offset{}; |
| 56 | Maxwell::ShaderStage stage; | ||
| 45 | }; | 57 | }; |
| 46 | 58 | ||
| 47 | struct ShaderEntries { | 59 | struct ShaderEntries { |
diff --git a/src/video_core/renderer_opengl/gl_shader_manager.h b/src/video_core/renderer_opengl/gl_shader_manager.h index ecc92d986..be63320e0 100644 --- a/src/video_core/renderer_opengl/gl_shader_manager.h +++ b/src/video_core/renderer_opengl/gl_shader_manager.h | |||
| @@ -121,6 +121,17 @@ public: | |||
| 121 | return result; | 121 | return result; |
| 122 | } | 122 | } |
| 123 | 123 | ||
| 124 | GLuint GetCurrentProgramStage(Maxwell3D::Regs::ShaderStage stage) { | ||
| 125 | switch (stage) { | ||
| 126 | case Maxwell3D::Regs::ShaderStage::Vertex: | ||
| 127 | return current.vs; | ||
| 128 | case Maxwell3D::Regs::ShaderStage::Fragment: | ||
| 129 | return current.fs; | ||
| 130 | } | ||
| 131 | |||
| 132 | UNREACHABLE(); | ||
| 133 | } | ||
| 134 | |||
| 124 | void UseTrivialGeometryShader() { | 135 | void UseTrivialGeometryShader() { |
| 125 | current.gs = 0; | 136 | current.gs = 0; |
| 126 | } | 137 | } |