Bug 1241163 - Replace DrawTarget::CreateSourceSurfaceFromNativeSurface(CAIRO_CONTEXT) with Factory::CreateSourceSurfaceForCairoSurface. r=jrmuizel
authorLee Salzman <lsalzman@mozilla.com>
Wed, 20 Jan 2016 13:31:44 -0500
changeset 280754 417708054b36fcc7fc50156303b2221775dfb6f9
parent 280753 b8dfc7fb1398fbc20994ba73fee89a1a9fe9935c
child 280755 a1c1d5cf87ce86dcfeb414967e16ab37b7772bf4
push id70569
push userlsalzman@mozilla.com
push dateWed, 20 Jan 2016 18:32:13 +0000
treeherdermozilla-inbound@417708054b36 [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewersjrmuizel
bugs1241163
milestone46.0a1
first release with
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
last release without
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
Bug 1241163 - Replace DrawTarget::CreateSourceSurfaceFromNativeSurface(CAIRO_CONTEXT) with Factory::CreateSourceSurfaceForCairoSurface. r=jrmuizel
gfx/2d/2D.h
gfx/2d/DrawTargetCairo.cpp
gfx/2d/DrawTargetSkia.cpp
gfx/2d/Factory.cpp
gfx/layers/basic/X11TextureSourceBasic.cpp
gfx/thebes/gfxPlatform.cpp
gfx/thebes/gfxXlibNativeRenderer.cpp
--- a/gfx/2d/2D.h
+++ b/gfx/2d/2D.h
@@ -1234,16 +1234,18 @@ public:
    * within 8k limit.  The 8k value is chosen a bit randomly.
    */
   static bool ReasonableSurfaceSize(const IntSize &aSize);
 
   static bool AllowedSurfaceSize(const IntSize &aSize);
 
   static already_AddRefed<DrawTarget> CreateDrawTargetForCairoSurface(cairo_surface_t* aSurface, const IntSize& aSize, SurfaceFormat* aFormat = nullptr);
 
+  static already_AddRefed<SourceSurface> CreateSourceSurfaceForCairoSurface(cairo_surface_t* aSurface, const IntSize& aSize, SurfaceFormat aFormat);
+
   static already_AddRefed<DrawTarget>
     CreateDrawTarget(BackendType aBackend, const IntSize &aSize, SurfaceFormat aFormat);
 
   static already_AddRefed<DrawTarget>
     CreateRecordingDrawTarget(DrawEventRecorder *aRecorder, DrawTarget *aDT);
 
   static already_AddRefed<DrawTarget>
     CreateDrawTargetForData(BackendType aBackend, unsigned char* aData, const IntSize &aSize, int32_t aStride, SurfaceFormat aFormat);
--- a/gfx/2d/DrawTargetCairo.cpp
+++ b/gfx/2d/DrawTargetCairo.cpp
@@ -1725,26 +1725,16 @@ DrawTargetCairo::OptimizeSourceSurface(S
 #endif
 
   return surface.forget();
 }
 
 already_AddRefed<SourceSurface>
 DrawTargetCairo::CreateSourceSurfaceFromNativeSurface(const NativeSurface &aSurface) const
 {
-  if (aSurface.mType == NativeSurfaceType::CAIRO_CONTEXT) {
-    if (aSurface.mSize.width <= 0 ||
-        aSurface.mSize.height <= 0) {
-      gfxWarning() << "Can't create a SourceSurface without a valid size";
-      return nullptr;
-    }
-    cairo_surface_t* surf = static_cast<cairo_surface_t*>(aSurface.mSurface);
-    return MakeAndAddRef<SourceSurfaceCairo>(surf, aSurface.mSize, aSurface.mFormat);
-  }
-
   return nullptr;
 }
 
 already_AddRefed<DrawTarget>
 DrawTargetCairo::CreateSimilarDrawTarget(const IntSize &aSize, SurfaceFormat aFormat) const
 {
   if (cairo_surface_status(mSurface)) {
     RefPtr<DrawTargetCairo> target = new DrawTargetCairo();
--- a/gfx/2d/DrawTargetSkia.cpp
+++ b/gfx/2d/DrawTargetSkia.cpp
@@ -744,34 +744,26 @@ DrawTargetSkia::OptimizeSourceSurface(So
                                                              dataSurf->GetFormat());
   dataSurf->Unmap();
   return result.forget();
 }
 
 already_AddRefed<SourceSurface>
 DrawTargetSkia::CreateSourceSurfaceFromNativeSurface(const NativeSurface &aSurface) const
 {
-  if (aSurface.mType == NativeSurfaceType::CAIRO_CONTEXT) {
-    if (aSurface.mSize.width <= 0 ||
-        aSurface.mSize.height <= 0) {
-      gfxWarning() << "Can't create a SourceSurface without a valid size";
-      return nullptr;
-    }
-    cairo_surface_t* surf = static_cast<cairo_surface_t*>(aSurface.mSurface);
-    return MakeAndAddRef<SourceSurfaceCairo>(surf, aSurface.mSize, aSurface.mFormat);
 #if USE_SKIA_GPU
-  } else if (aSurface.mType == NativeSurfaceType::OPENGL_TEXTURE && UsingSkiaGPU()) {
+  if (aSurface.mType == NativeSurfaceType::OPENGL_TEXTURE && UsingSkiaGPU()) {
     RefPtr<SourceSurfaceSkia> newSurf = new SourceSurfaceSkia();
     unsigned int texture = (unsigned int)((uintptr_t)aSurface.mSurface);
     if (newSurf->InitFromTexture((DrawTargetSkia*)this, texture, aSurface.mSize, aSurface.mFormat)) {
       return newSurf.forget();
     }
     return nullptr;
+  }
 #endif
-  }
 
   return nullptr;
 }
 
 void
 DrawTargetSkia::CopySurface(SourceSurface *aSurface,
                             const IntRect& aSourceRect,
                             const IntPoint &aDestination)
--- a/gfx/2d/Factory.cpp
+++ b/gfx/2d/Factory.cpp
@@ -3,16 +3,17 @@
  * License, v. 2.0. If a copy of the MPL was not distributed with this
  * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
 
 #include "2D.h"
 
 #ifdef USE_CAIRO
 #include "DrawTargetCairo.h"
 #include "ScaledFontCairo.h"
+#include "SourceSurfaceCairo.h"
 #endif
 
 #ifdef USE_SKIA
 #include "DrawTargetSkia.h"
 #include "ScaledFontBase.h"
 #ifdef MOZ_ENABLE_FREETYPE
 #define USE_SKIA_FREETYPE
 #include "ScaledFontCairo.h"
@@ -845,16 +846,31 @@ Factory::CreateDrawTargetForCairoSurface
 
   if (mRecorder && retVal) {
     return MakeAndAddRef<DrawTargetRecording>(mRecorder, retVal, true);
   }
 #endif
   return retVal.forget();
 }
 
+already_AddRefed<SourceSurface>
+Factory::CreateSourceSurfaceForCairoSurface(cairo_surface_t* aSurface, const IntSize& aSize, SurfaceFormat aFormat)
+{
+  if (aSize.width <= 0 || aSize.height <= 0) {
+    gfxWarning() << "Can't create a SourceSurface without a valid size";
+    return nullptr;
+  }
+
+#ifdef USE_CAIRO
+  return MakeAndAddRef<SourceSurfaceCairo>(aSurface, aSize, aFormat);
+#else
+  return nullptr;
+#endif
+}
+
 #ifdef XP_DARWIN
 already_AddRefed<DrawTarget>
 Factory::CreateDrawTargetForCairoCGContext(CGContextRef cg, const IntSize& aSize)
 {
   RefPtr<DrawTarget> retVal;
 
   RefPtr<DrawTargetCG> newTarget = new DrawTargetCG();
 
--- a/gfx/layers/basic/X11TextureSourceBasic.cpp
+++ b/gfx/layers/basic/X11TextureSourceBasic.cpp
@@ -30,22 +30,19 @@ X11TextureSourceBasic::GetFormat() const
   gfxContentType type = mSurface->GetContentType();
   return X11TextureSourceBasic::ContentTypeToSurfaceFormat(type);
 }
 
 SourceSurface*
 X11TextureSourceBasic::GetSurface(DrawTarget* aTarget)
 {
   if (!mSourceSurface) {
-    NativeSurface surf;
-    surf.mFormat = GetFormat();
-    surf.mType = NativeSurfaceType::CAIRO_CONTEXT;
-    surf.mSurface = mSurface->CairoSurface();
-    surf.mSize = GetSize();
-    mSourceSurface = aTarget->CreateSourceSurfaceFromNativeSurface(surf);
+    mSourceSurface =
+        Factory::CreateSourceSurfaceForCairoSurface(mSurface->CairoSurface(),
+                                                    GetSize(), GetFormat());
   }
   return mSourceSurface;
 }
 
 void
 X11TextureSourceBasic::SetCompositor(Compositor* aCompositor)
 {
   MOZ_ASSERT(aCompositor->GetBackendType() == LayersBackend::LAYERS_BASIC);
--- a/gfx/thebes/gfxPlatform.cpp
+++ b/gfx/thebes/gfxPlatform.cpp
@@ -901,34 +901,31 @@ gfxPlatform::GetSourceSurfaceForSurface(
 
   if (aTarget->GetBackendType() == BackendType::CAIRO) {
     // If we're going to be used with a CAIRO DrawTarget, then just create a
     // SourceSurfaceCairo since we don't know the underlying type of the CAIRO
     // DrawTarget and can't pick a better surface type. Doing this also avoids
     // readback of aSurface's surface into memory if, for example, aSurface
     // wraps an xlib cairo surface (which can be important to avoid a major
     // slowdown).
-    NativeSurface surf;
-    surf.mFormat = format;
-    surf.mType = NativeSurfaceType::CAIRO_CONTEXT;
-    surf.mSurface = aSurface->CairoSurface();
-    surf.mSize = aSurface->GetSize();
+    //
     // We return here regardless of whether CreateSourceSurfaceFromNativeSurface
     // succeeds or not since we don't expect to be able to do any better below
     // if it fails.
     //
     // Note that the returned SourceSurfaceCairo holds a strong reference to
     // the cairo_surface_t* that it wraps, which essencially means it holds a
     // strong reference to aSurface since aSurface shares its
     // cairo_surface_t*'s reference count variable. As a result we can't cache
     // srcBuffer on aSurface (see below) since aSurface would then hold a
     // strong reference back to srcBuffer, creating a reference loop and a
     // memory leak. Not caching is fine since wrapping is cheap enough (no
     // copying) so we can just wrap again next time we're called.
-    return aTarget->CreateSourceSurfaceFromNativeSurface(surf);
+    return Factory::CreateSourceSurfaceForCairoSurface(aSurface->CairoSurface(),
+                                                       aSurface->GetSize(), format);
   }
 
   RefPtr<SourceSurface> srcBuffer;
 
   // Currently no other DrawTarget types implement CreateSourceSurfaceFromNativeSurface
 
   if (!srcBuffer) {
     // If aSurface wraps data, we can create a SourceSurfaceRawData that wraps
@@ -959,28 +956,18 @@ gfxPlatform::GetSourceSurfaceForSurface(
                "DrawTargetCairo above");
     // We've run out of performant options. We now try creating a SourceSurface
     // using a temporary DrawTargetCairo and then optimizing it to aTarget's
     // actual type. The CreateSourceSurfaceFromNativeSurface() call will
     // likely create a DataSourceSurface (possibly involving copying and/or
     // readback), and the OptimizeSourceSurface may well copy again and upload
     // to the GPU. So, while this code path is rarely hit, hitting it may be
     // very slow.
-    NativeSurface surf;
-    surf.mFormat = format;
-    surf.mType = NativeSurfaceType::CAIRO_CONTEXT;
-    surf.mSurface = aSurface->CairoSurface();
-    surf.mSize = aSurface->GetSize();
-    RefPtr<DrawTarget> drawTarget =
-      Factory::CreateDrawTarget(BackendType::CAIRO, IntSize(1, 1), format);
-    if (!drawTarget) {
-      gfxWarning() << "gfxPlatform::GetSourceSurfaceForSurface failed in CreateDrawTarget";
-      return nullptr;
-    }
-    srcBuffer = drawTarget->CreateSourceSurfaceFromNativeSurface(surf);
+    srcBuffer = Factory::CreateSourceSurfaceForCairoSurface(aSurface->CairoSurface(),
+                                                            aSurface->GetSize(), format);
     if (srcBuffer) {
       srcBuffer = aTarget->OptimizeSourceSurface(srcBuffer);
     }
   }
 
   if (!srcBuffer) {
     return nullptr;
   }
--- a/gfx/thebes/gfxXlibNativeRenderer.cpp
+++ b/gfx/thebes/gfxXlibNativeRenderer.cpp
@@ -570,23 +570,18 @@ gfxXlibNativeRenderer::Draw(gfxContext* 
         return;
     }
 
     SurfaceFormat moz2DFormat =
         cairo_surface_get_content(tempXlibSurface) == CAIRO_CONTENT_COLOR ?
             SurfaceFormat::B8G8R8A8 : SurfaceFormat::B8G8R8X8;
     if (method != eAlphaExtraction) {
         if (drawTarget) {
-            NativeSurface native;
-            native.mFormat = moz2DFormat;
-            native.mType = NativeSurfaceType::CAIRO_CONTEXT;
-            native.mSurface = tempXlibSurface;
-            native.mSize = size;
             RefPtr<SourceSurface> sourceSurface =
-                drawTarget->CreateSourceSurfaceFromNativeSurface(native);
+                Factory::CreateSourceSurfaceForCairoSurface(tempXlibSurface, size, moz2DFormat);
             if (sourceSurface) {
                 drawTarget->DrawSurface(sourceSurface,
                     Rect(offset.x, offset.y, size.width, size.height),
                     Rect(0, 0, size.width, size.height));
             }
         } else {
             RefPtr<gfxASurface> tmpSurf = gfxASurface::Wrap(tempXlibSurface);
             ctx->SetSource(tmpSurf, offset);
@@ -612,23 +607,19 @@ gfxXlibNativeRenderer::Draw(gfxContext* 
         whiteImage->CairoStatus() == CAIRO_STATUS_SUCCESS) {
         if (!gfxAlphaRecovery::RecoverAlpha(blackImage, whiteImage)) {
             cairo_surface_destroy(tempXlibSurface);
             return;
         }
 
         gfxASurface* paintSurface = blackImage;
         if (drawTarget) {
-            NativeSurface native;
-            native.mFormat = moz2DFormat;
-            native.mType = NativeSurfaceType::CAIRO_CONTEXT;
-            native.mSurface = paintSurface->CairoSurface();
-            native.mSize = size;
             RefPtr<SourceSurface> sourceSurface =
-                drawTarget->CreateSourceSurfaceFromNativeSurface(native);
+                Factory::CreateSourceSurfaceForCairoSurface(paintSurface->CairoSurface(),
+                                                            size, moz2DFormat);
             if (sourceSurface) {
                 drawTarget->DrawSurface(sourceSurface,
                     Rect(offset.x, offset.y, size.width, size.height),
                     Rect(0, 0, size.width, size.height));
             }
         } else {
             ctx->SetSource(paintSurface, offset);
             ctx->Paint();