Have the remote and main strike caches return a StrikeRef

Change-Id: Ia42ff6ecec43063dbe873a62de67c90259a09bc3
Reviewed-on: https://skia-review.googlesource.com/c/skia/+/558541
Commit-Queue: Herb Derby <herb@google.com>
Reviewed-by: Robert Phillips <robertphillips@google.com>
This commit is contained in:
Herb Derby 2022-07-13 14:08:50 -04:00 committed by SkCQ
parent c28ff1f69a
commit 92c162532e
9 changed files with 91 additions and 64 deletions

View File

@ -480,6 +480,7 @@ skia_core_sources = [
"$_src/shaders/SkTransformShader.h",
"$_src/text/GlyphRun.cpp",
"$_src/text/GlyphRun.h",
"$_src/text/StrikeForGPU.cpp",
"$_src/text/StrikeForGPU.h",
# private

View File

@ -1633,6 +1633,7 @@ BASE_SRCS_ALL = [
"src/sksl/transform/SkSLTransform.h",
"src/text/GlyphRun.cpp",
"src/text/GlyphRun.h",
"src/text/StrikeForGPU.cpp",
"src/text/StrikeForGPU.h",
"src/text/gpu/DistanceFieldAdjustTable.cpp",
"src/text/gpu/DistanceFieldAdjustTable.h",

View File

@ -552,6 +552,7 @@ public:
void writeStrikeData(std::vector<uint8_t>* memory);
sktext::ScopedStrikeForGPU findOrCreateScopedStrike(const SkStrikeSpec& strikeSpec) override;
sktext::StrikeRef findOrCreateStrikeRef(const SkStrikeSpec& strikeSpec) override;
// Methods for testing
void setMaxEntriesInDescriptorMapForTesting(size_t count);
@ -669,6 +670,10 @@ sktext::ScopedStrikeForGPU SkStrikeServerImpl::findOrCreateScopedStrike(
return sktext::ScopedStrikeForGPU{this->getOrCreateCache(strikeSpec)};
}
sktext::StrikeRef SkStrikeServerImpl::findOrCreateStrikeRef(const SkStrikeSpec& strikeSpec) {
return sktext::StrikeRef{this->getOrCreateCache(strikeSpec)};
}
void SkStrikeServerImpl::checkForDeletedEntries() {
auto it = fDescToRemoteStrike.begin();
while (fDescToRemoteStrike.size() > fMaxEntriesInDescriptorMap &&

View File

@ -42,11 +42,14 @@ auto SkStrikeCache::findOrCreateStrike(const SkStrikeSpec& strikeSpec) -> sk_sp<
return strike;
}
sktext::ScopedStrikeForGPU SkStrikeCache::findOrCreateScopedStrike(
const SkStrikeSpec& strikeSpec) {
sktext::ScopedStrikeForGPU SkStrikeCache::findOrCreateScopedStrike(const SkStrikeSpec& strikeSpec) {
return sktext::ScopedStrikeForGPU{this->findOrCreateStrike(strikeSpec).release()};
}
sktext::StrikeRef SkStrikeCache::findOrCreateStrikeRef(const SkStrikeSpec& strikeSpec) {
return sktext::StrikeRef{this->findOrCreateStrike(strikeSpec)};
}
void SkStrikeCache::PurgeAll() {
GlobalStrikeCache()->purgeAll();
}

View File

@ -207,6 +207,9 @@ public:
sktext::ScopedStrikeForGPU findOrCreateScopedStrike(
const SkStrikeSpec& strikeSpec) override SK_EXCLUDES(fLock);
sktext::StrikeRef findOrCreateStrikeRef(
const SkStrikeSpec& strikeSpec) override SK_EXCLUDES(fLock);
static void PurgeAll();
static void Dump();

View File

@ -7,6 +7,7 @@ exports_files_legacy()
TEXT_FILES = [
"GlyphRun.cpp",
"GlyphRun.h",
"StrikeForGPU.cpp",
"StrikeForGPU.h",
]

72
src/text/StrikeForGPU.cpp Normal file
View File

@ -0,0 +1,72 @@
/*
* 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/text/StrikeForGPU.h"
#include "include/private/chromium/SkChromeRemoteGlyphCache.h"
#include "src/core/SkReadBuffer.h"
#include "src/core/SkStrikeCache.h"
#include "src/core/SkWriteBuffer.h"
namespace sktext {
// -- StrikeRef ------------------------------------------------------------------------------------
StrikeRef::StrikeRef(sk_sp<SkStrike>&& strike) : fStrike{std::move(strike)} {
SkASSERT(std::get<sk_sp<SkStrike>>(fStrike) != nullptr);
}
StrikeRef::StrikeRef(StrikeForGPU* strike) : fStrike {strike} {
SkASSERT(std::get<StrikeForGPU*>(fStrike) != nullptr);
}
StrikeRef::StrikeRef(StrikeRef&&) = default;
StrikeRef& StrikeRef::operator=(StrikeRef&&) = default;
void StrikeRef::flatten(SkWriteBuffer& buffer) const {
if (std::holds_alternative<std::monostate>(fStrike)) {
SK_ABORT("Can't flatten. getStrikeAndSetToNullptr has already been called.");
}
if (const sk_sp<SkStrike>* strikePtr = std::get_if<sk_sp<SkStrike>>(&fStrike)) {
(*strikePtr)->getDescriptor().flatten(buffer);
} else if (StrikeForGPU*const* GPUstrikePtr = std::get_if<StrikeForGPU*>(&fStrike)) {
(*GPUstrikePtr)->getDescriptor().flatten(buffer);
}
}
std::optional<StrikeRef> StrikeRef::MakeFromBuffer(SkReadBuffer& buffer,
const SkStrikeClient* client) {
auto descriptor = SkAutoDescriptor::MakeFromBuffer(buffer);
if (!buffer.validate(descriptor.has_value())) {
return std::nullopt;
}
// If there is a client, then this from a different process. Translate the typeface id from
// that process to this process.
if (client != nullptr) {
if (!client->translateTypefaceID(&descriptor.value())) {
return std::nullopt;
}
}
sk_sp<SkStrike> strike = SkStrikeCache::GlobalStrikeCache()->findStrike(*descriptor->getDesc());
if (!buffer.validate(strike != nullptr)) {
return std::nullopt;
}
return StrikeRef{std::move(strike)};
}
sk_sp<SkStrike> StrikeRef::getStrikeAndSetToNullptr() {
if (std::holds_alternative<sk_sp<SkStrike>>(fStrike)) {
// Force a copy out of the variant because there is no more efficient way to do it.
sk_sp<SkStrike> strike = std::get<sk_sp<SkStrike>>(fStrike);
fStrike = std::monostate();
return strike;
}
return nullptr;
}
} // namespace sktext

View File

@ -108,6 +108,7 @@ class StrikeForGPUCacheInterface {
public:
virtual ~StrikeForGPUCacheInterface() = default;
virtual ScopedStrikeForGPU findOrCreateScopedStrike(const SkStrikeSpec& strikeSpec) = 0;
virtual StrikeRef findOrCreateStrikeRef(const SkStrikeSpec& strikeSpec) = 0;
};
} // namespace sktext
#endif // sktext_StrikeForGPU_DEFINED

View File

@ -7,77 +7,17 @@
#include "src/text/gpu/GlyphVector.h"
#include "include/private/chromium/SkChromeRemoteGlyphCache.h"
#include "src/core/SkReadBuffer.h"
#include "src/core/SkStrikeCache.h"
#include "src/core/SkWriteBuffer.h"
#include "src/text/StrikeForGPU.h"
#include <optional>
#include <variant>
class SkStrikeClient;
using MaskFormat = skgpu::MaskFormat;
namespace sktext {
// -- StrikeRef ------------------------------------------------------------------------------------
StrikeRef::StrikeRef(sk_sp<SkStrike>&& strike) : fStrike{std::move(strike)} {
SkASSERT(std::get<sk_sp<SkStrike>>(fStrike) != nullptr);
}
StrikeRef::StrikeRef(StrikeForGPU* strike) : fStrike {strike} {
SkASSERT(std::get<StrikeForGPU*>(fStrike) != nullptr);
}
StrikeRef::StrikeRef(StrikeRef&&) = default;
StrikeRef& StrikeRef::operator=(StrikeRef&&) = default;
void StrikeRef::flatten(SkWriteBuffer& buffer) const {
if (std::holds_alternative<std::monostate>(fStrike)) {
SK_ABORT("Can't flatten. getStrikeAndSetToNullptr has already been called.");
}
if (const sk_sp<SkStrike>* strikePtr = std::get_if<sk_sp<SkStrike>>(&fStrike)) {
(*strikePtr)->getDescriptor().flatten(buffer);
} else if (StrikeForGPU*const* GPUstrikePtr = std::get_if<StrikeForGPU*>(&fStrike)) {
(*GPUstrikePtr)->getDescriptor().flatten(buffer);
}
}
std::optional<StrikeRef> StrikeRef::MakeFromBuffer(SkReadBuffer& buffer,
const SkStrikeClient* client) {
auto descriptor = SkAutoDescriptor::MakeFromBuffer(buffer);
if (!buffer.validate(descriptor.has_value())) {
return std::nullopt;
}
// If there is a client, then this from a different process. Translate the typeface id from
// that process to this process.
if (client != nullptr) {
if (!client->translateTypefaceID(&descriptor.value())) {
return std::nullopt;
}
}
sk_sp<SkStrike> strike = SkStrikeCache::GlobalStrikeCache()->findStrike(*descriptor->getDesc());
if (!buffer.validate(strike != nullptr)) {
return std::nullopt;
}
return StrikeRef{std::move(strike)};
}
sk_sp<SkStrike> StrikeRef::getStrikeAndSetToNullptr() {
if (std::holds_alternative<sk_sp<SkStrike>>(fStrike)) {
// Force a copy out of the variant because there is no more efficient way to do it.
sk_sp<SkStrike> strike = std::get<sk_sp<SkStrike>>(fStrike);
fStrike = std::monostate();
return strike;
}
return nullptr;
}
} // namespace sktext
namespace sktext::gpu {
// -- GlyphVector ----------------------------------------------------------------------------------
GlyphVector::GlyphVector(StrikeRef&& strikeRef, SkSpan<Variant> glyphs)