Upstream version 9.38.198.0
[platform/framework/web/crosswalk.git] / src / third_party / skia / src / core / SkXfermode.cpp
index 182d3b7..0811808 100644 (file)
@@ -11,8 +11,8 @@
 #include "SkXfermode_opts_SSE2.h"
 #include "SkXfermode_proccoeff.h"
 #include "SkColorPriv.h"
+#include "SkLazyPtr.h"
 #include "SkMathPriv.h"
-#include "SkOnce.h"
 #include "SkReadBuffer.h"
 #include "SkString.h"
 #include "SkUtilsArm.h"
@@ -676,12 +676,12 @@ bool SkXfermode::asMode(Mode* mode) const {
     return false;
 }
 
-bool SkXfermode::asNewEffect(GrEffectRef** effect, GrTexture* background) const {
+bool SkXfermode::asNewEffect(GrEffect** effect, GrTexture* background) const {
     return false;
 }
 
 bool SkXfermode::AsNewEffectOrCoeff(SkXfermode* xfermode,
-                                    GrEffectRef** effect,
+                                    GrEffect** effect,
                                     Coeff* src,
                                     Coeff* dst,
                                     GrTexture* background) {
@@ -783,6 +783,7 @@ void SkXfermode::xferA8(SkAlpha* SK_RESTRICT dst,
 #include "GrEffectUnitTest.h"
 #include "GrTBackendEffectFactory.h"
 #include "gl/GrGLEffect.h"
+#include "gl/GrGLShaderBuilder.h"
 
 /**
  * GrEffect that implements the all the separable xfer modes that cannot be expressed as Coeffs.
@@ -793,12 +794,11 @@ public:
         return mode > SkXfermode::kLastCoeffMode && mode <= SkXfermode::kLastMode;
     }
 
-    static GrEffectRef* Create(SkXfermode::Mode mode, GrTexture* background) {
+    static GrEffect* Create(SkXfermode::Mode mode, GrTexture* background) {
         if (!IsSupportedMode(mode)) {
             return NULL;
         } else {
-            AutoEffectUnref effect(SkNEW_ARGS(XferEffect, (mode, background)));
-            return CreateEffectRef(effect);
+            return SkNEW_ARGS(XferEffect, (mode, background));
         }
     }
 
@@ -823,7 +823,7 @@ public:
         }
         virtual void emitCode(GrGLShaderBuilder* builder,
                               const GrDrawEffect& drawEffect,
-                              EffectKey key,
+                              const GrEffectKey& key,
                               const char* outputColor,
                               const char* inputColor,
                               const TransformedCoordsArray& coords,
@@ -969,11 +969,13 @@ public:
             }
         }
 
-        static inline EffectKey GenKey(const GrDrawEffect& drawEffect, const GrGLCaps&) {
+        static inline void GenKey(const GrDrawEffect& drawEffect, const GrGLCaps&,
+                                  GrEffectKeyBuilder* b) {
             // The background may come from the dst or from a texture.
-            int numTextures = (*drawEffect.effect())->numTextures();
-            SkASSERT(numTextures <= 1);
-            return (drawEffect.castEffect<XferEffect>().mode() << 1) | numTextures;
+            uint32_t key = drawEffect.effect()->numTextures();
+            SkASSERT(key <= 1);
+            key |= drawEffect.castEffect<XferEffect>().mode() << 1;
+            b->add32(key);
         }
 
     private:
@@ -1224,14 +1226,13 @@ private:
 };
 
 GR_DEFINE_EFFECT_TEST(XferEffect);
-GrEffectRef* XferEffect::TestCreate(SkRandom* rand,
-                                    GrContext*,
-                                    const GrDrawTargetCaps&,
-                                    GrTexture*[]) {
+GrEffect* XferEffect::TestCreate(SkRandom* rand,
+                                 GrContext*,
+                                 const GrDrawTargetCaps&,
+                                 GrTexture*[]) {
     int mode = rand->nextRangeU(SkXfermode::kLastCoeffMode + 1, SkXfermode::kLastSeparableMode);
 
-    AutoEffectUnref gEffect(SkNEW_ARGS(XferEffect, (static_cast<SkXfermode::Mode>(mode), NULL)));
-    return CreateEffectRef(gEffect);
+    return SkNEW_ARGS(XferEffect, (static_cast<SkXfermode::Mode>(mode), NULL));
 }
 
 #endif
@@ -1363,8 +1364,7 @@ void SkProcCoeffXfermode::xferA8(SkAlpha* SK_RESTRICT dst,
 }
 
 #if SK_SUPPORT_GPU
-bool SkProcCoeffXfermode::asNewEffect(GrEffectRef** effect,
-                                      GrTexture* background) const {
+bool SkProcCoeffXfermode::asNewEffect(GrEffect** effect, GrTexture* background) const {
     if (XferEffect::IsSupportedMode(fMode)) {
         if (NULL != effect) {
             *effect = XferEffect::Create(fMode, background);
@@ -1651,26 +1651,13 @@ void SkDstOutXfermode::toString(SkString* str) const {
 
 ///////////////////////////////////////////////////////////////////////////////
 
-SK_DECLARE_STATIC_MUTEX(gCachedXfermodesMutex);
-static SkXfermode* gCachedXfermodes[SkXfermode::kLastMode + 1];  // All NULL to start.
-static bool gXfermodeCached[SK_ARRAY_COUNT(gCachedXfermodes)];  // All false to start.
-
-void SkXfermode::Term() {
-    SkAutoMutexAcquire ac(gCachedXfermodesMutex);
-
-    for (size_t i = 0; i < SK_ARRAY_COUNT(gCachedXfermodes); ++i) {
-        SkSafeUnref(gCachedXfermodes[i]);
-        gCachedXfermodes[i] = NULL;
-    }
-}
-
-extern SkProcCoeffXfermode* SkPlatformXfermodeFactory(const ProcCoeff& rec,
-                                                      SkXfermode::Mode mode);
+extern SkProcCoeffXfermode* SkPlatformXfermodeFactory(const ProcCoeff& rec, SkXfermode::Mode mode);
 extern SkXfermodeProc SkPlatformXfermodeProcFactory(SkXfermode::Mode mode);
 
-
-static void create_mode(SkXfermode::Mode mode) {
-    SkASSERT(NULL == gCachedXfermodes[mode]);
+// Technically, can't be static and passed as a template parameter.  So we use anonymous namespace.
+namespace {
+SkXfermode* create_mode(int iMode) {
+    SkXfermode::Mode mode = (SkXfermode::Mode)iMode;
 
     ProcCoeff rec = gProcCoeffs[mode];
     SkXfermodeProc pp = SkPlatformXfermodeProcFactory(mode);
@@ -1709,28 +1696,27 @@ static void create_mode(SkXfermode::Mode mode) {
                 break;
         }
     }
-    gCachedXfermodes[mode] = xfer;
+    return xfer;
 }
+}  // namespace
+
 
 SkXfermode* SkXfermode::Create(Mode mode) {
     SkASSERT(SK_ARRAY_COUNT(gProcCoeffs) == kModeCount);
-    SkASSERT(SK_ARRAY_COUNT(gCachedXfermodes) == kModeCount);
 
     if ((unsigned)mode >= kModeCount) {
         // report error
         return NULL;
     }
 
-    // Skia's "defaut" mode is srcover. NULL in SkPaint is interpreted as srcover
+    // Skia's "default" mode is srcover. NULL in SkPaint is interpreted as srcover
     // so we can just return NULL from the factory.
     if (kSrcOver_Mode == mode) {
         return NULL;
     }
 
-    SkOnce(&gXfermodeCached[mode], &gCachedXfermodesMutex, create_mode, mode);
-    SkXfermode* xfer = gCachedXfermodes[mode];
-    SkASSERT(xfer != NULL);
-    return SkSafeRef(xfer);
+    SK_DECLARE_STATIC_LAZY_PTR_ARRAY(SkXfermode, cached, kModeCount, create_mode);
+    return SkSafeRef(cached[mode]);
 }
 
 SkXfermodeProc SkXfermode::GetProc(Mode mode) {