| /* |
| * Copyright 2022 Google LLC |
| * |
| * Use of this source code is governed by a BSD-style license that can be |
| * found in the LICENSE file. |
| */ |
| |
| #include "src/gpu/graphite/GlobalCache.h" |
| |
| #include "src/gpu/graphite/ComputePipeline.h" |
| #include "src/gpu/graphite/ContextUtils.h" |
| #include "src/gpu/graphite/GraphicsPipeline.h" |
| #include "src/gpu/graphite/Resource.h" |
| |
| namespace skgpu::graphite { |
| |
| GlobalCache::GlobalCache() |
| : fGraphicsPipelineCache(256) // TODO: find a good value for these limits |
| , fComputePipelineCache(256) {} |
| |
| GlobalCache::~GlobalCache() { |
| // These should have been cleared out earlier by deleteResources(). |
| SkDEBUGCODE(SkAutoSpinlock lock{ fSpinLock }); |
| SkASSERT(fGraphicsPipelineCache.count() == 0); |
| SkASSERT(fComputePipelineCache.count() == 0); |
| SkASSERT(fStaticResource.size() == 0); |
| } |
| |
| void GlobalCache::deleteResources() { |
| SkAutoSpinlock lock{ fSpinLock }; |
| |
| fGraphicsPipelineCache.reset(); |
| fComputePipelineCache.reset(); |
| fStaticResource.clear(); |
| } |
| |
| sk_sp<GraphicsPipeline> GlobalCache::findGraphicsPipeline(const UniqueKey& key) { |
| SkAutoSpinlock lock{fSpinLock}; |
| |
| sk_sp<GraphicsPipeline>* entry = fGraphicsPipelineCache.find(key); |
| return entry ? *entry : nullptr; |
| } |
| |
| sk_sp<GraphicsPipeline> GlobalCache::addGraphicsPipeline(const UniqueKey& key, |
| sk_sp<GraphicsPipeline> pipeline) { |
| SkAutoSpinlock lock{fSpinLock}; |
| |
| sk_sp<GraphicsPipeline>* entry = fGraphicsPipelineCache.find(key); |
| if (!entry) { |
| // No equivalent pipeline was stored in the cache between a previous call to |
| // findGraphicsPipeline() that returned null (triggering the pipeline creation) and this |
| // later adding to the cache. |
| entry = fGraphicsPipelineCache.insert(key, std::move(pipeline)); |
| } // else there was a race creating the same pipeline and this thread lost, so return the winner |
| return *entry; |
| } |
| |
| #if defined(GRAPHITE_TEST_UTILS) |
| int GlobalCache::numGraphicsPipelines() const { |
| SkAutoSpinlock lock{fSpinLock}; |
| |
| return fGraphicsPipelineCache.count(); |
| } |
| |
| void GlobalCache::resetGraphicsPipelines() { |
| SkAutoSpinlock lock{fSpinLock}; |
| |
| fGraphicsPipelineCache.reset(); |
| } |
| |
| void GlobalCache::forEachGraphicsPipeline( |
| const std::function<void(const UniqueKey&, const GraphicsPipeline*)>& fn) { |
| SkAutoSpinlock lock{fSpinLock}; |
| |
| fGraphicsPipelineCache.foreach([&](const UniqueKey* k, const sk_sp<GraphicsPipeline>* v) { |
| fn(*k, v->get()); |
| }); |
| } |
| #endif // defined(GRAPHITE_TEST_UTILS) |
| |
| sk_sp<ComputePipeline> GlobalCache::findComputePipeline(const UniqueKey& key) { |
| SkAutoSpinlock lock{fSpinLock}; |
| sk_sp<ComputePipeline>* entry = fComputePipelineCache.find(key); |
| return entry ? *entry : nullptr; |
| } |
| |
| sk_sp<ComputePipeline> GlobalCache::addComputePipeline(const UniqueKey& key, |
| sk_sp<ComputePipeline> pipeline) { |
| SkAutoSpinlock lock{fSpinLock}; |
| sk_sp<ComputePipeline>* entry = fComputePipelineCache.find(key); |
| if (!entry) { |
| entry = fComputePipelineCache.insert(key, std::move(pipeline)); |
| } |
| return *entry; |
| } |
| |
| void GlobalCache::addStaticResource(sk_sp<Resource> resource) { |
| SkAutoSpinlock lock{fSpinLock}; |
| fStaticResource.push_back(std::move(resource)); |
| } |
| |
| } // namespace skgpu::graphite |