From bf0b957c05013f33855e67c31a48e61b1e86d356 Mon Sep 17 00:00:00 2001 From: Feng Chen Date: Tue, 6 Dec 2022 13:45:26 +0800 Subject: video_core: Implement maxwell3d draw manager and split draw logic --- .../renderer_vulkan/fixed_pipeline_state.cpp | 6 ++++-- src/video_core/renderer_vulkan/vk_pipeline_cache.cpp | 3 ++- src/video_core/renderer_vulkan/vk_rasterizer.cpp | 18 ++++++++++-------- 3 files changed, 16 insertions(+), 11 deletions(-) (limited to 'src/video_core/renderer_vulkan') diff --git a/src/video_core/renderer_vulkan/fixed_pipeline_state.cpp b/src/video_core/renderer_vulkan/fixed_pipeline_state.cpp index f3f08b42c..24529c80f 100644 --- a/src/video_core/renderer_vulkan/fixed_pipeline_state.cpp +++ b/src/video_core/renderer_vulkan/fixed_pipeline_state.cpp @@ -8,6 +8,7 @@ #include "common/cityhash.h" #include "common/common_types.h" #include "common/polyfill_ranges.h" +#include "video_core/engines/draw_manager.h" #include "video_core/renderer_vulkan/fixed_pipeline_state.h" #include "video_core/renderer_vulkan/vk_state_tracker.h" @@ -50,12 +51,13 @@ void RefreshXfbState(VideoCommon::TransformFeedbackState& state, const Maxwell& void FixedPipelineState::Refresh(Tegra::Engines::Maxwell3D& maxwell3d, bool has_extended_dynamic_state, bool has_dynamic_vertex_input) { const Maxwell& regs = maxwell3d.regs; + const auto topology_ = maxwell3d.draw_manager->GetDrawState().topology; const std::array enabled_lut{ regs.polygon_offset_point_enable, regs.polygon_offset_line_enable, regs.polygon_offset_fill_enable, }; - const u32 topology_index = static_cast(regs.draw.topology.Value()); + const u32 topology_index = static_cast(topology_); raw1 = 0; extended_dynamic_state.Assign(has_extended_dynamic_state ? 1 : 0); @@ -78,7 +80,7 @@ void FixedPipelineState::Refresh(Tegra::Engines::Maxwell3D& maxwell3d, Maxwell::Tessellation::OutputPrimitives::Triangles_CW); logic_op_enable.Assign(regs.logic_op.enable != 0 ? 1 : 0); logic_op.Assign(PackLogicOp(regs.logic_op.op)); - topology.Assign(regs.draw.topology); + topology.Assign(topology_); msaa_mode.Assign(regs.anti_alias_samples_mode); raw2 = 0; diff --git a/src/video_core/renderer_vulkan/vk_pipeline_cache.cpp b/src/video_core/renderer_vulkan/vk_pipeline_cache.cpp index 38a6b7488..81f5f3e11 100644 --- a/src/video_core/renderer_vulkan/vk_pipeline_cache.cpp +++ b/src/video_core/renderer_vulkan/vk_pipeline_cache.cpp @@ -507,7 +507,8 @@ GraphicsPipeline* PipelineCache::BuiltPipeline(GraphicsPipeline* pipeline) const // If games are using a small index count, we can assume these are full screen quads. // Usually these shaders are only used once for building textures so we can assume they // can't be built async - if (maxwell3d->regs.index_buffer.count <= 6 || maxwell3d->regs.vertex_buffer.count <= 6) { + const auto& draw_state = maxwell3d->draw_manager->GetDrawState(); + if (draw_state.index_buffer.count <= 6 || draw_state.vertex_buffer.count <= 6) { return pipeline; } return nullptr; diff --git a/src/video_core/renderer_vulkan/vk_rasterizer.cpp b/src/video_core/renderer_vulkan/vk_rasterizer.cpp index d8ad8815c..8d7a5e400 100644 --- a/src/video_core/renderer_vulkan/vk_rasterizer.cpp +++ b/src/video_core/renderer_vulkan/vk_rasterizer.cpp @@ -12,6 +12,7 @@ #include "common/scope_exit.h" #include "common/settings.h" #include "video_core/control/channel_state.h" +#include "video_core/engines/draw_manager.h" #include "video_core/engines/kepler_compute.h" #include "video_core/engines/maxwell_3d.h" #include "video_core/renderer_vulkan/blit_image.h" @@ -36,6 +37,7 @@ namespace Vulkan { using Maxwell = Tegra::Engines::Maxwell3D::Regs; +using MaxwellDrawState = Tegra::Engines::DrawManager::State; using VideoCommon::ImageViewId; using VideoCommon::ImageViewType; @@ -127,16 +129,16 @@ VkRect2D GetScissorState(const Maxwell& regs, size_t index, u32 up_scale = 1, u3 return scissor; } -DrawParams MakeDrawParams(const Maxwell& regs, u32 num_instances, bool is_indexed) { +DrawParams MakeDrawParams(const MaxwellDrawState& draw_state, u32 num_instances, bool is_indexed) { DrawParams params{ - .base_instance = regs.global_base_instance_index, + .base_instance = draw_state.base_instance, .num_instances = num_instances, - .base_vertex = is_indexed ? regs.global_base_vertex_index : regs.vertex_buffer.first, - .num_vertices = is_indexed ? regs.index_buffer.count : regs.vertex_buffer.count, - .first_index = is_indexed ? regs.index_buffer.first : 0, + .base_vertex = is_indexed ? draw_state.base_index : draw_state.vertex_buffer.first, + .num_vertices = is_indexed ? draw_state.index_buffer.count : draw_state.vertex_buffer.count, + .first_index = is_indexed ? draw_state.index_buffer.first : 0, .is_indexed = is_indexed, }; - if (regs.draw.topology == Maxwell::PrimitiveTopology::Quads) { + if (draw_state.topology == Maxwell::PrimitiveTopology::Quads) { // 6 triangle vertices per quad, base vertex is part of the index // See BindQuadArrayIndexBuffer for more details params.num_vertices = (params.num_vertices / 4) * 6; @@ -195,9 +197,9 @@ void RasterizerVulkan::Draw(bool is_indexed, u32 instance_count) { UpdateDynamicStates(); - const auto& regs{maxwell3d->regs}; + const auto& draw_state = maxwell3d->draw_manager->GetDrawState(); const u32 num_instances{instance_count}; - const DrawParams draw_params{MakeDrawParams(regs, num_instances, is_indexed)}; + const DrawParams draw_params{MakeDrawParams(draw_state, num_instances, is_indexed)}; scheduler.Record([draw_params](vk::CommandBuffer cmdbuf) { if (draw_params.is_indexed) { cmdbuf.DrawIndexed(draw_params.num_vertices, draw_params.num_instances, -- cgit v1.2.3