Fix race condition in parallel font initialization.
authortomhudson <tomhudson@chromium.org>
Tue, 1 Jul 2014 15:06:14 +0000 (08:06 -0700)
committerCommit bot <commit-bot@chromium.org>
Tue, 1 Jul 2014 15:06:14 +0000 (08:06 -0700)
Uses a mutex to guard construction of the singleton, which initialies
the non-threadsafe libfontconfig.  Without this change, the parallel
path ops test runner crashes 6/10 and hangs 2/10 on startup; with this
change, 0/10 problems.

BUG=skia:2693
R=mtklein@google.com, bungeman@google.com, reed@google.com, tomhudson@google.com

Committed: https://skia.googlesource.com/skia/+/df022f5972ae6a2a1d96d15c50eca52cade3abd8

Author: tomhudson@chromium.org

Review URL: https://codereview.chromium.org/355573006

include/ports/SkFontConfigInterface.h
src/ports/SkFontConfigInterface_android.cpp
src/ports/SkFontConfigInterface_direct.cpp
src/ports/SkFontHost_fontconfig.cpp

index 8c12a56..f548f37 100644 (file)
@@ -14,6 +14,8 @@
 #include "SkTArray.h"
 #include "SkTypeface.h"
 
+struct SkBaseMutex;
+
 /**
  *  \class SkFontConfigInterface
  *
@@ -95,8 +97,9 @@ public:
     /**
      *  Return a singleton instance of a direct subclass that calls into
      *  libfontconfig. This does not affect the refcnt of the returned instance.
+     *  The mutex may be used to guarantee the singleton is only constructed once.
      */
-    static SkFontConfigInterface* GetSingletonDirectInterface();
+    static SkFontConfigInterface* GetSingletonDirectInterface(SkBaseMutex* mutex);
 
     // New APIS, which have default impls for now (which do nothing)
 
index 20e6c5e..1f901b9 100644 (file)
@@ -155,7 +155,8 @@ static SkFontConfigInterfaceAndroid* getSingletonInterface() {
     return gFontConfigInterface;
 }
 
-SkFontConfigInterface* SkFontConfigInterface::GetSingletonDirectInterface() {
+SkFontConfigInterface* SkFontConfigInterface::GetSingletonDirectInterface(SkBaseMutex*) {
+    // Doesn't need passed-in mutex because getSingletonInterface() uses one
     return getSingletonInterface();
 }
 
index dc9afba..c0cfd8f 100644 (file)
@@ -124,9 +124,13 @@ private:
     SkMutex mutex_;
 };
 
-SkFontConfigInterface* SkFontConfigInterface::GetSingletonDirectInterface() {
-    SK_DECLARE_STATIC_LAZY_PTR(SkFontConfigInterfaceDirect, direct);
-    return direct.get();
+SkFontConfigInterface* SkFontConfigInterface::GetSingletonDirectInterface(SkBaseMutex* mutex) {
+    SkAutoMutexAcquire ac(mutex);
+    static SkFontConfigInterfaceDirect* singleton = NULL;
+    if (singleton == NULL) {
+        singleton = SkNEW(SkFontConfigInterfaceDirect);
+    }
+    return singleton;
 }
 
 ///////////////////////////////////////////////////////////////////////////////
index 07bfbd0..8abf5cf 100644 (file)
@@ -50,7 +50,7 @@ static SkFontConfigInterface* RefFCI() {
         if (fci) {
             return fci;
         }
-        fci = SkFontConfigInterface::GetSingletonDirectInterface();
+        fci = SkFontConfigInterface::GetSingletonDirectInterface(&gFontConfigInterfaceMutex);
         SkFontConfigInterface::SetGlobal(fci);
     }
 }