diff options
author | 2016-05-02 11:54:13 -0700 | |
---|---|---|
committer | 2016-05-02 11:54:13 -0700 | |
commit | 0265707c191a31dfde08dd1cd7011c1fe5b8e643 (patch) | |
tree | 919635b2cf13cc3c639126c42e6098130e2e2c30 /src/ports/SkFontConfigInterface_direct.cpp | |
parent | c5091b5b6c4b8a7aef8c12db9ea2a85e907b01c4 (diff) |
Clean up SkFontConfigInterface implementation.
Renames some classes to avoid confusion with FontConfig.
Removed direct calls to FontConfig instead of calling FCI.
Moves the globals and factory to one (optional) file.
Moves font management code from typeface to font manager.
Adds index to fonts created from streams.
Associates FCI typefaces with the FCI instance which provides its identity.
Simplifies the singleton initialization.
Review-Url: https://codereview.chromium.org/1936213002
Diffstat (limited to 'src/ports/SkFontConfigInterface_direct.cpp')
-rw-r--r-- | src/ports/SkFontConfigInterface_direct.cpp | 56 |
1 files changed, 53 insertions, 3 deletions
diff --git a/src/ports/SkFontConfigInterface_direct.cpp b/src/ports/SkFontConfigInterface_direct.cpp index d384f707b1..d6fa96a46c 100644 --- a/src/ports/SkFontConfigInterface_direct.cpp +++ b/src/ports/SkFontConfigInterface_direct.cpp @@ -24,6 +24,56 @@ #include <fontconfig/fontconfig.h> #include <unistd.h> +#ifdef SK_DEBUG +# include "SkTLS.h" +#endif + +namespace { + +// Fontconfig is not threadsafe before 2.10.91. Before that, we lock with a global mutex. +// See https://bug.skia.org/1497 for background. +SK_DECLARE_STATIC_MUTEX(gFCMutex); + +#ifdef SK_DEBUG +void* CreateThreadFcLocked() { return new bool(false); } +void DeleteThreadFcLocked(void* v) { delete static_cast<bool*>(v); } +# define THREAD_FC_LOCKED \ + static_cast<bool*>(SkTLS::Get(CreateThreadFcLocked, DeleteThreadFcLocked)) +#endif + +struct FCLocker { + // Assume FcGetVersion() has always been thread safe. + + FCLocker() { + if (FcGetVersion() < 21091) { + gFCMutex.acquire(); + } else { + SkDEBUGCODE(bool* threadLocked = THREAD_FC_LOCKED); + SkASSERT(false == *threadLocked); + SkDEBUGCODE(*threadLocked = true); + } + } + + ~FCLocker() { + AssertHeld(); + if (FcGetVersion() < 21091) { + gFCMutex.release(); + } else { + SkDEBUGCODE(*THREAD_FC_LOCKED = false); + } + } + + static void AssertHeld() { SkDEBUGCODE( + if (FcGetVersion() < 21091) { + gFCMutex.assertHeld(); + } else { + SkASSERT(true == *THREAD_FC_LOCKED); + } + ) } +}; + +} // namespace + size_t SkFontConfigInterface::FontIdentity::writeToMemory(void* addr) const { size_t size = sizeof(fID) + sizeof(fTTCIndex); size += sizeof(int32_t) + sizeof(int32_t) + sizeof(uint8_t); // weight, width, italic @@ -448,7 +498,7 @@ static void fcpattern_from_skfontstyle(SkFontStyle style, FcPattern* pattern) { #define kMaxFontFamilyLength 2048 SkFontConfigInterfaceDirect::SkFontConfigInterfaceDirect() { - SkAutoMutexAcquire ac(mutex_); + FCLocker lock; FcInit(); @@ -532,7 +582,7 @@ bool SkFontConfigInterfaceDirect::matchFamilyName(const char familyName[], return false; } - SkAutoMutexAcquire ac(mutex_); + FCLocker lock; FcPattern* pattern = FcPatternCreate(); @@ -649,7 +699,7 @@ static bool find_name(const SkTDArray<const char*>& list, const char* str) { } SkDataTable* SkFontConfigInterfaceDirect::getFamilyNames() { - SkAutoMutexAcquire ac(mutex_); + FCLocker lock; FcPattern* pat = FcPatternCreate(); SkAutoTCallVProc<FcPattern, FcPatternDestroy> autoDestroyPat(pat); |