From 4a3cd69257900483ce3bef290a3d3631702ec502 Mon Sep 17 00:00:00 2001 From: Billy Laws Date: Sat, 10 Dec 2022 15:50:17 +0000 Subject: [PATCH] Populate graphics pipeline manager from cache at launch-time --- .../maxwell_3d/pipeline_manager.cpp | 32 +++++++++++++++++++ .../maxwell_3d/pipeline_manager.h | 11 ++----- 2 files changed, 34 insertions(+), 9 deletions(-) diff --git a/app/src/main/cpp/skyline/gpu/interconnect/maxwell_3d/pipeline_manager.cpp b/app/src/main/cpp/skyline/gpu/interconnect/maxwell_3d/pipeline_manager.cpp index ff847313..c8da7771 100644 --- a/app/src/main/cpp/skyline/gpu/interconnect/maxwell_3d/pipeline_manager.cpp +++ b/app/src/main/cpp/skyline/gpu/interconnect/maxwell_3d/pipeline_manager.cpp @@ -849,5 +849,37 @@ namespace skyline::gpu::interconnect::maxwell3d { .descriptorSetIndex = 0, }); } + + PipelineManager::PipelineManager(GPU &gpu) { + std::ifstream stream{gpu.graphicsPipelineCacheManager->OpenReadStream()}; + i64 lastKnownGoodOffset{stream.tellg()}; + try { + auto startTime{util::GetTimeNs()}; + PipelineStateBundle bundle; + + while (bundle.Deserialise(stream)) { + lastKnownGoodOffset = stream.tellg(); + auto accessor{FilePipelineStateAccessor{bundle}}; + map.emplace(bundle.GetKey(), std::make_unique(gpu, accessor, bundle.GetKey())); + } + + Logger::Info("Loaded {} graphics pipelines in {}ms", map.size(), (util::GetTimeNs() - startTime) / constant::NsInMillisecond); + } catch (const exception &e) { + Logger::Warn("Pipeline cache corrupted at: 0x{:X}, error: {}", lastKnownGoodOffset, e.what()); + gpu.graphicsPipelineCacheManager->InvalidateAllAfter(static_cast(lastKnownGoodOffset)); + return; + } + } + + Pipeline *PipelineManager::FindOrCreate(InterconnectContext &ctx, Textures &textures, ConstantBufferSet &constantBuffers, const PackedPipelineState &packedState, const std::array &shaderBinaries) { + auto it{map.find(packedState)}; + if (it != map.end()) + return it->second.get(); + + auto bundle{std::make_unique()}; + bundle->Reset(packedState); + auto accessor{RuntimeGraphicsPipelineStateAccessor{std::move(bundle), ctx, textures, constantBuffers, shaderBinaries}}; + return map.emplace(packedState, std::make_unique(ctx.gpu, accessor, packedState)).first->second.get(); + } } diff --git a/app/src/main/cpp/skyline/gpu/interconnect/maxwell_3d/pipeline_manager.h b/app/src/main/cpp/skyline/gpu/interconnect/maxwell_3d/pipeline_manager.h index 5727bdfc..806ed315 100644 --- a/app/src/main/cpp/skyline/gpu/interconnect/maxwell_3d/pipeline_manager.h +++ b/app/src/main/cpp/skyline/gpu/interconnect/maxwell_3d/pipeline_manager.h @@ -129,18 +129,11 @@ namespace skyline::gpu::interconnect::maxwell3d { */ class PipelineManager { private: - PipelineStateBundle bundle; tsl::robin_map, PackedPipelineStateHash> map; public: - Pipeline *FindOrCreate(InterconnectContext &ctx, Textures &textures, ConstantBufferSet &constantBuffers, const PackedPipelineState &packedState, const std::array &shaderBinaries) { - auto it{map.find(packedState)}; - if (it != map.end()) - return it->second.get(); + PipelineManager(GPU &gpu); - bundle.Reset(packedState); - auto accessor{RuntimeGraphicsPipelineStateAccessor{bundle, ctx, textures, constantBuffers, shaderBinaries}}; - return map.emplace(packedState, std::make_unique(ctx, accessor, packedState)).first->second.get(); - } + Pipeline *FindOrCreate(InterconnectContext &ctx, Textures &textures, ConstantBufferSet &constantBuffers, const PackedPipelineState &packedState, const std::array &shaderBinaries); }; }