diff options
author | Herb Derby <herb@google.com> | 2017-02-13 20:04:00 +0000 |
---|---|---|
committer | Skia Commit-Bot <skia-commit-bot@chromium.org> | 2017-02-13 20:04:16 +0000 |
commit | 07f665efb918f68e406b76a78d0b76d5c714f16c (patch) | |
tree | d58a5d4849f779e9504aa69dda0414777770eafb /src | |
parent | d2d6d726fa3e401da73befa649266bc5589da7e5 (diff) |
Revert "Always make SkImageShaders in heap."
This reverts commit ff590a12441002d281254ec6a86070ac0a19263f.
Reason for revert: This breaks the android roll because they are using
a private call. Updating android tests to use new api.
Original change's description:
> Always make SkImageShaders in heap.
>
> I made a couple of measurments, and it looks like any differences is
> well below the noise threshold.
>
> Just for the record run1: .9991 of baseline and run2 .9988 of baseline.
> I was using top25 .skps as workload.
>
> TBR=mtklein@google.com
>
> Change-Id: If4fa06e5d5df72fb67dbb4bbb99c926f05765897
> Reviewed-on: https://skia-review.googlesource.com/8341
> Reviewed-by: Herb Derby <herb@google.com>
> Commit-Queue: Herb Derby <herb@google.com>
>
TBR=mtklein@chromium.org,mtklein@google.com,herb@google.com,reviews@skia.org
NOPRESUBMIT=true
NOTREECHECKS=true
NOTRY=true
Change-Id: Ibdaafc796702e250933b62e5f4abb5e2ce8d40c0
Reviewed-on: https://skia-review.googlesource.com/8393
Commit-Queue: Herb Derby <herb@google.com>
Reviewed-by: Herb Derby <herb@google.com>
Diffstat (limited to 'src')
-rw-r--r-- | src/core/SkBitmapDevice.cpp | 6 | ||||
-rw-r--r-- | src/core/SkDraw.cpp | 19 | ||||
-rw-r--r-- | src/core/SkImagePriv.h | 6 | ||||
-rw-r--r-- | src/core/SkShader.cpp | 2 | ||||
-rw-r--r-- | src/image/SkImageShader.cpp | 29 | ||||
-rw-r--r-- | src/image/SkImageShader.h | 2 | ||||
-rw-r--r-- | src/image/SkImage_Raster.cpp | 15 | ||||
-rw-r--r-- | src/xps/SkXPSDevice.cpp | 2 |
8 files changed, 62 insertions, 19 deletions
diff --git a/src/core/SkBitmapDevice.cpp b/src/core/SkBitmapDevice.cpp index 45ec2b70ae..2b5c37fa2e 100644 --- a/src/core/SkBitmapDevice.cpp +++ b/src/core/SkBitmapDevice.cpp @@ -334,13 +334,15 @@ void SkBitmapDevice::drawBitmapRect(const SkDraw& draw, const SkBitmap& bitmap, // Since the shader need only live for our stack-frame, pass in a custom allocator. This // can save malloc calls, and signals to SkMakeBitmapShader to not try to copy the bitmap // if its mutable, since that precaution is not needed (give the short lifetime of the shader). - + SkTBlitterAllocator allocator; // construct a shader, so we can call drawRect with the dst auto s = SkMakeBitmapShader(*bitmapPtr, SkShader::kClamp_TileMode, SkShader::kClamp_TileMode, - &matrix, kNever_SkCopyPixelsMode); + &matrix, kNever_SkCopyPixelsMode, &allocator); if (!s) { return; } + // we deliberately add a ref, since the allocator wants to be the last owner + s.get()->ref(); SkPaint paintWithShader(paint); paintWithShader.setStyle(SkPaint::kFill_Style); diff --git a/src/core/SkDraw.cpp b/src/core/SkDraw.cpp index 4d1c5a4998..4308000457 100644 --- a/src/core/SkDraw.cpp +++ b/src/core/SkDraw.cpp @@ -85,10 +85,23 @@ public: SkAutoBitmapShaderInstall(const SkBitmap& src, const SkPaint& paint, const SkMatrix* localMatrix = nullptr) : fPaint(paint) /* makes a copy of the paint */ { - + // TODO(herb): Move this over to SkArenaAlloc when arena alloc has a + // facility to return sk_sps. fPaint.setShader(SkMakeBitmapShader(src, SkShader::kClamp_TileMode, SkShader::kClamp_TileMode, localMatrix, - kNever_SkCopyPixelsMode)); + kNever_SkCopyPixelsMode, + &fAllocator)); + // we deliberately left the shader with an owner-count of 2 + fPaint.getShader()->ref(); + SkASSERT(2 == fPaint.getShader()->getRefCnt()); + } + + ~SkAutoBitmapShaderInstall() { + // since fAllocator will destroy shader, we insist that owners == 2 + SkASSERT(2 == fPaint.getShader()->getRefCnt()); + + fPaint.setShader(nullptr); // unref the shader by 1 + } // return the new paint that has the shader applied @@ -97,6 +110,8 @@ public: private: // copy of caller's paint (which we then modify) SkPaint fPaint; + // Stores the shader. + SkTBlitterAllocator fAllocator; }; #define SkAutoBitmapShaderInstall(...) SK_REQUIRE_LOCAL_VAR(SkAutoBitmapShaderInstall) diff --git a/src/core/SkImagePriv.h b/src/core/SkImagePriv.h index d6e58d3c11..601108665d 100644 --- a/src/core/SkImagePriv.h +++ b/src/core/SkImagePriv.h @@ -30,7 +30,8 @@ typedef SkSmallAllocator<3, kSkBlitterContextSize> SkTBlitterAllocator; // If alloc is non-nullptr, it will be used to allocate the returned SkShader, and MUST outlive // the SkShader. sk_sp<SkShader> SkMakeBitmapShader(const SkBitmap& src, SkShader::TileMode, SkShader::TileMode, - const SkMatrix* localMatrix, SkCopyPixelsMode); + const SkMatrix* localMatrix, SkCopyPixelsMode, + SkTBlitterAllocator* alloc); /** * Examines the bitmap to decide if it can share the existing pixelRef, or @@ -50,7 +51,8 @@ sk_sp<SkShader> SkMakeBitmapShader(const SkBitmap& src, SkShader::TileMode, SkSh * SkImageInfo, or the bitmap's pixels cannot be accessed, this will return * nullptr. */ -extern sk_sp<SkImage> SkMakeImageFromRasterBitmap(const SkBitmap&, SkCopyPixelsMode); +extern sk_sp<SkImage> SkMakeImageFromRasterBitmap(const SkBitmap&, SkCopyPixelsMode, + SkTBlitterAllocator* = nullptr); // Given an image created from SkNewImageFromBitmap, return its pixelref. This // may be called to see if the surface and the image share the same pixelref, diff --git a/src/core/SkShader.cpp b/src/core/SkShader.cpp index cfdd8b946e..81aae116d5 100644 --- a/src/core/SkShader.cpp +++ b/src/core/SkShader.cpp @@ -232,7 +232,7 @@ sk_sp<SkShader> SkShader::MakeBitmapShader(const SkBitmap& src, TileMode tmx, Ti if (localMatrix && !localMatrix->invert(nullptr)) { return nullptr; } - return SkMakeBitmapShader(src, tmx, tmy, localMatrix, kIfMutable_SkCopyPixelsMode); + return SkMakeBitmapShader(src, tmx, tmy, localMatrix, kIfMutable_SkCopyPixelsMode, nullptr); } sk_sp<SkShader> SkShader::MakePictureShader(sk_sp<SkPicture> src, TileMode tmx, TileMode tmy, diff --git a/src/image/SkImageShader.cpp b/src/image/SkImageShader.cpp index 7e3874891c..64a09dd2dc 100644 --- a/src/image/SkImageShader.cpp +++ b/src/image/SkImageShader.cpp @@ -97,12 +97,23 @@ static bool bitmap_is_too_big(int w, int h) { } sk_sp<SkShader> SkImageShader::Make(sk_sp<SkImage> image, TileMode tx, TileMode ty, - const SkMatrix* localMatrix) { + const SkMatrix* localMatrix, + SkTBlitterAllocator* allocator) { + SkShader* shader; if (!image || bitmap_is_too_big(image->width(), image->height())) { - return sk_make_sp<SkEmptyShader>(); + if (nullptr == allocator) { + shader = new SkEmptyShader; + } else { + shader = allocator->createT<SkEmptyShader>(); + } } else { - return sk_make_sp<SkImageShader>(image, tx, ty, localMatrix); + if (nullptr == allocator) { + shader = new SkImageShader(image, tx, ty, localMatrix); + } else { + shader = allocator->createT<SkImageShader>(image, tx, ty, localMatrix); + } } + return sk_sp<SkShader>(shader); } #ifndef SK_IGNORE_TO_STRING @@ -186,9 +197,15 @@ sk_sp<GrFragmentProcessor> SkImageShader::asFragmentProcessor(const AsFPArgs& ar sk_sp<SkShader> SkMakeBitmapShader(const SkBitmap& src, SkShader::TileMode tmx, SkShader::TileMode tmy, const SkMatrix* localMatrix, - SkCopyPixelsMode cpm) { - return SkImageShader::Make(SkMakeImageFromRasterBitmap(src, cpm), - tmx, tmy, localMatrix); + SkCopyPixelsMode cpm, SkTBlitterAllocator* allocator) { + // Until we learn otherwise, it seems that any caller that is passing an allocator must be + // assuming that the returned shader will have a stack-frame lifetime, so we assert that + // they are also asking for kNever_SkCopyPixelsMode. If that proves otherwise, we can remove + // or modify this assert. + SkASSERT(!allocator || (kNever_SkCopyPixelsMode == cpm)); + + return SkImageShader::Make(SkMakeImageFromRasterBitmap(src, cpm, allocator), + tmx, tmy, localMatrix, allocator); } static sk_sp<SkFlattenable> SkBitmapProcShader_CreateProc(SkReadBuffer& buffer) { diff --git a/src/image/SkImageShader.h b/src/image/SkImageShader.h index 8960812a06..ef5e87c66d 100644 --- a/src/image/SkImageShader.h +++ b/src/image/SkImageShader.h @@ -15,7 +15,7 @@ class SkImageShader : public SkShader { public: static sk_sp<SkShader> Make(sk_sp<SkImage>, TileMode tx, TileMode ty, - const SkMatrix* localMatrix); + const SkMatrix* localMatrix, SkTBlitterAllocator* = nullptr); bool isOpaque() const override; diff --git a/src/image/SkImage_Raster.cpp b/src/image/SkImage_Raster.cpp index 0364fc6b2a..b287789ea8 100644 --- a/src/image/SkImage_Raster.cpp +++ b/src/image/SkImage_Raster.cpp @@ -301,7 +301,8 @@ sk_sp<SkImage> SkImage::MakeFromRaster(const SkPixmap& pmap, RasterReleaseProc p return sk_make_sp<SkImage_Raster>(pmap.info(), std::move(data), pmap.rowBytes(), pmap.ctable()); } -sk_sp<SkImage> SkMakeImageFromRasterBitmap(const SkBitmap& bm, SkCopyPixelsMode cpm) { +sk_sp<SkImage> SkMakeImageFromRasterBitmap(const SkBitmap& bm, SkCopyPixelsMode cpm, + SkTBlitterAllocator* allocator) { bool hasColorTable = false; if (kIndex_8_SkColorType == bm.colorType()) { SkAutoLockPixels autoLockPixels(bm); @@ -312,17 +313,23 @@ sk_sp<SkImage> SkMakeImageFromRasterBitmap(const SkBitmap& bm, SkCopyPixelsMode return nullptr; } + sk_sp<SkImage> image; if (kAlways_SkCopyPixelsMode == cpm || (!bm.isImmutable() && kNever_SkCopyPixelsMode != cpm)) { SkBitmap tmp(bm); tmp.lockPixels(); SkPixmap pmap; if (tmp.getPixels() && tmp.peekPixels(&pmap)) { - return SkImage::MakeRasterCopy(pmap); + image = SkImage::MakeRasterCopy(pmap); } } else { - return sk_make_sp<SkImage_Raster>(bm, kNever_SkCopyPixelsMode == cpm); + if (allocator) { + image.reset(allocator->createT<SkImage_Raster>(bm, kNever_SkCopyPixelsMode == cpm)); + image.get()->ref(); // account for the allocator being an owner + } else { + image = sk_make_sp<SkImage_Raster>(bm, kNever_SkCopyPixelsMode == cpm); + } } - return sk_sp<SkImage>(); + return image; } const SkPixelRef* SkBitmapImageGetPixelRef(const SkImage* image) { diff --git a/src/xps/SkXPSDevice.cpp b/src/xps/SkXPSDevice.cpp index f32ca86d92..8dca7f0156 100644 --- a/src/xps/SkXPSDevice.cpp +++ b/src/xps/SkXPSDevice.cpp @@ -2274,7 +2274,7 @@ void SkXPSDevice::drawBitmapRect(const SkDraw& draw, auto bitmapShader = SkMakeBitmapShader(bitmap, SkShader::kClamp_TileMode, SkShader::kClamp_TileMode, &matrix, - kNever_SkCopyPixelsMode); + kNever_SkCopyPixelsMode, nullptr); SkASSERT(bitmapShader); if (!bitmapShader) { return; } SkPaint paintWithShader(paint); |