summaryrefslogtreecommitdiffstats
path: root/src/video_core/renderer_vulkan
diff options
context:
space:
mode:
authorReinUsesLisp <reinuseslisp@airmail.cc>2021-06-06 03:10:02 +0200
committerameerj <52414509+ameerj@users.noreply.github.com>2021-07-23 03:51:35 +0200
commit48aad8dc05f027c21aa0e8a68d827006d9f7a196 (patch)
tree3e1fa35387e82636d2d00fd0f56b8bab30d6e385 /src/video_core/renderer_vulkan
parentvk_rasterizer: Flush work on clear and dispatches (diff)
downloadyuzu-48aad8dc05f027c21aa0e8a68d827006d9f7a196.tar
yuzu-48aad8dc05f027c21aa0e8a68d827006d9f7a196.tar.gz
yuzu-48aad8dc05f027c21aa0e8a68d827006d9f7a196.tar.bz2
yuzu-48aad8dc05f027c21aa0e8a68d827006d9f7a196.tar.lz
yuzu-48aad8dc05f027c21aa0e8a68d827006d9f7a196.tar.xz
yuzu-48aad8dc05f027c21aa0e8a68d827006d9f7a196.tar.zst
yuzu-48aad8dc05f027c21aa0e8a68d827006d9f7a196.zip
Diffstat (limited to 'src/video_core/renderer_vulkan')
-rw-r--r--src/video_core/renderer_vulkan/vk_graphics_pipeline.h6
-rw-r--r--src/video_core/renderer_vulkan/vk_pipeline_cache.cpp26
-rw-r--r--src/video_core/renderer_vulkan/vk_pipeline_cache.h4
3 files changed, 33 insertions, 3 deletions
diff --git a/src/video_core/renderer_vulkan/vk_graphics_pipeline.h b/src/video_core/renderer_vulkan/vk_graphics_pipeline.h
index 8c81c28a8..3f8895927 100644
--- a/src/video_core/renderer_vulkan/vk_graphics_pipeline.h
+++ b/src/video_core/renderer_vulkan/vk_graphics_pipeline.h
@@ -87,7 +87,7 @@ public:
configure_func(this, is_indexed);
}
- GraphicsPipeline* Next(const GraphicsPipelineCacheKey& current_key) noexcept {
+ [[nodiscard]] GraphicsPipeline* Next(const GraphicsPipelineCacheKey& current_key) noexcept {
if (key == current_key) {
return this;
}
@@ -96,6 +96,10 @@ public:
: nullptr;
}
+ [[nodiscard]] bool IsBuilt() const noexcept {
+ return is_built.load(std::memory_order::relaxed);
+ }
+
template <typename Spec>
static auto MakeConfigureSpecFunc() {
return [](GraphicsPipeline* pipeline, bool is_indexed) {
diff --git a/src/video_core/renderer_vulkan/vk_pipeline_cache.cpp b/src/video_core/renderer_vulkan/vk_pipeline_cache.cpp
index a7f3619a5..741ed1a98 100644
--- a/src/video_core/renderer_vulkan/vk_pipeline_cache.cpp
+++ b/src/video_core/renderer_vulkan/vk_pipeline_cache.cpp
@@ -240,6 +240,7 @@ PipelineCache::PipelineCache(RasterizerVulkan& rasterizer_, Tegra::Engines::Maxw
device{device_}, scheduler{scheduler_}, descriptor_pool{descriptor_pool_},
update_descriptor_queue{update_descriptor_queue_}, render_pass_cache{render_pass_cache_},
buffer_cache{buffer_cache_}, texture_cache{texture_cache_},
+ use_asynchronous_shaders{Settings::values.use_asynchronous_shaders.GetValue()},
workers(std::max(std::thread::hardware_concurrency(), 2U) - 1, "yuzu:PipelineBuilder"),
serialization_thread(1, "yuzu:PipelineSerialization") {
const auto& float_control{device.FloatControlProperties()};
@@ -303,7 +304,7 @@ GraphicsPipeline* PipelineCache::CurrentGraphicsPipeline() {
GraphicsPipeline* const next{current_pipeline->Next(graphics_key)};
if (next) {
current_pipeline = next;
- return current_pipeline;
+ return BuiltPipeline(current_pipeline);
}
}
const auto [pair, is_new]{graphics_cache.try_emplace(graphics_key)};
@@ -318,7 +319,7 @@ GraphicsPipeline* PipelineCache::CurrentGraphicsPipeline() {
current_pipeline->AddTransition(pipeline.get());
}
current_pipeline = pipeline.get();
- return current_pipeline;
+ return BuiltPipeline(current_pipeline);
}
ComputePipeline* PipelineCache::CurrentComputePipeline() {
@@ -415,6 +416,27 @@ void PipelineCache::LoadDiskResources(u64 title_id, std::stop_token stop_loading
workers.WaitForRequests();
}
+GraphicsPipeline* PipelineCache::BuiltPipeline(GraphicsPipeline* pipeline) const noexcept {
+ if (pipeline->IsBuilt()) {
+ return pipeline;
+ }
+ if (!use_asynchronous_shaders) {
+ return pipeline;
+ }
+ // If something is using depth, we can assume that games are not rendering anything which
+ // will be used one time.
+ if (maxwell3d.regs.zeta_enable) {
+ return nullptr;
+ }
+ // 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_array.count <= 6 || maxwell3d.regs.vertex_buffer.count <= 6) {
+ return pipeline;
+ }
+ return nullptr;
+}
+
std::unique_ptr<GraphicsPipeline> PipelineCache::CreateGraphicsPipeline(
ShaderPools& pools, const GraphicsPipelineCacheKey& key,
std::span<Shader::Environment* const> envs, bool build_in_parallel) try {
diff --git a/src/video_core/renderer_vulkan/vk_pipeline_cache.h b/src/video_core/renderer_vulkan/vk_pipeline_cache.h
index 4116cc73f..869c63baf 100644
--- a/src/video_core/renderer_vulkan/vk_pipeline_cache.h
+++ b/src/video_core/renderer_vulkan/vk_pipeline_cache.h
@@ -115,6 +115,8 @@ public:
const VideoCore::DiskResourceLoadCallback& callback);
private:
+ [[nodiscard]] GraphicsPipeline* BuiltPipeline(GraphicsPipeline* pipeline) const noexcept;
+
std::unique_ptr<GraphicsPipeline> CreateGraphicsPipeline();
std::unique_ptr<GraphicsPipeline> CreateGraphicsPipeline(
@@ -140,6 +142,8 @@ private:
GraphicsPipelineCacheKey graphics_key{};
GraphicsPipeline* current_pipeline{};
+ bool use_asynchronous_shaders{};
+
std::unordered_map<ComputePipelineCacheKey, std::unique_ptr<ComputePipeline>> compute_cache;
std::unordered_map<GraphicsPipelineCacheKey, std::unique_ptr<GraphicsPipeline>> graphics_cache;