aboutsummaryrefslogtreecommitdiffhomepage
diff options
context:
space:
mode:
authorGravatar reed <reed@google.com>2014-09-16 10:39:55 -0700
committerGravatar Commit bot <commit-bot@chromium.org>2014-09-16 10:39:55 -0700
commit30ad5306be25565484a3dd76237984e071b7c4b3 (patch)
tree3a54680bf9bc826a5dba45da01a7637e5a17a2cb
parent4815fe5a0a497b676677fb4e4a0f05c511855490 (diff)
allow SkBitmapCache to operate on a local instance, for testability
BUG=skia: R=mtklein@google.com, danakj@chromium.org, piotaixr@chromium.org, junov@chromium.org Author: reed@google.com Review URL: https://codereview.chromium.org/576763002
-rw-r--r--src/core/SkBitmapCache.cpp30
-rw-r--r--src/core/SkBitmapCache.h12
-rw-r--r--src/core/SkResourceCache.cpp5
-rw-r--r--src/core/SkResourceCache.h6
-rw-r--r--tests/SkResourceCacheTest.cpp93
5 files changed, 96 insertions, 50 deletions
diff --git a/src/core/SkBitmapCache.cpp b/src/core/SkBitmapCache.cpp
index 84f10363f0..5044d30518 100644
--- a/src/core/SkBitmapCache.cpp
+++ b/src/core/SkBitmapCache.cpp
@@ -70,33 +70,41 @@ struct BitmapRec : public SkResourceCache::Rec {
}
};
-bool SkBitmapCache::Find(const SkBitmap& src, SkScalar invScaleX, SkScalar invScaleY,
- SkBitmap* result) {
+#define CHECK_LOCAL(localCache, localName, globalName, ...) \
+ (localCache) ? localCache->localName(__VA_ARGS__) : SkResourceCache::globalName(__VA_ARGS__)
+
+bool SkBitmapCache::Find(const SkBitmap& src, SkScalar invScaleX, SkScalar invScaleY, SkBitmap* result,
+ SkResourceCache* localCache) {
if (0 == invScaleX || 0 == invScaleY) {
// degenerate, and the key we use for mipmaps
return false;
}
BitmapKey key(src.getGenerationID(), invScaleX, invScaleY, get_bounds_from_bitmap(src));
- return SkResourceCache::Find(key, BitmapRec::Visitor, result);
+
+ return CHECK_LOCAL(localCache, find, Find, key, BitmapRec::Visitor, result);
}
void SkBitmapCache::Add(const SkBitmap& src, SkScalar invScaleX, SkScalar invScaleY,
- const SkBitmap& result) {
+ const SkBitmap& result, SkResourceCache* localCache) {
if (0 == invScaleX || 0 == invScaleY) {
// degenerate, and the key we use for mipmaps
return;
}
SkASSERT(result.isImmutable());
- SkResourceCache::Add(SkNEW_ARGS(BitmapRec, (src.getGenerationID(), invScaleX, invScaleY,
- get_bounds_from_bitmap(src), result)));
+ BitmapRec* rec = SkNEW_ARGS(BitmapRec, (src.getGenerationID(), invScaleX, invScaleY,
+ get_bounds_from_bitmap(src), result));
+ CHECK_LOCAL(localCache, add, Add, rec);
}
-bool SkBitmapCache::Find(uint32_t genID, const SkIRect& subset, SkBitmap* result) {
+bool SkBitmapCache::Find(uint32_t genID, const SkIRect& subset, SkBitmap* result,
+ SkResourceCache* localCache) {
BitmapKey key(genID, SK_Scalar1, SK_Scalar1, subset);
- return SkResourceCache::Find(key, BitmapRec::Visitor, result);
+
+ return CHECK_LOCAL(localCache, find, Find, key, BitmapRec::Visitor, result);
}
-bool SkBitmapCache::Add(uint32_t genID, const SkIRect& subset, const SkBitmap& result) {
+bool SkBitmapCache::Add(uint32_t genID, const SkIRect& subset, const SkBitmap& result,
+ SkResourceCache* localCache) {
SkASSERT(result.isImmutable());
if (subset.isEmpty()
@@ -106,9 +114,9 @@ bool SkBitmapCache::Add(uint32_t genID, const SkIRect& subset, const SkBitmap& r
|| result.height() != subset.height()) {
return false;
} else {
- SkResourceCache::Add(SkNEW_ARGS(BitmapRec, (genID, SK_Scalar1, SK_Scalar1,
- subset, result)));
+ BitmapRec* rec = SkNEW_ARGS(BitmapRec, (genID, SK_Scalar1, SK_Scalar1, subset, result));
+ CHECK_LOCAL(localCache, add, Add, rec);
return true;
}
}
diff --git a/src/core/SkBitmapCache.h b/src/core/SkBitmapCache.h
index aec7a7d41c..181c85812a 100644
--- a/src/core/SkBitmapCache.h
+++ b/src/core/SkBitmapCache.h
@@ -11,6 +11,7 @@
#include "SkScalar.h"
#include "SkBitmap.h"
+class SkResourceCache;
class SkMipMap;
class SkBitmapCache {
@@ -25,25 +26,28 @@ public:
* Search based on the src bitmap and inverse scales in X and Y. If found, returns true and
* result will be set to the matching bitmap with its pixels already locked.
*/
- static bool Find(const SkBitmap& src, SkScalar invScaleX, SkScalar invScaleY, SkBitmap* result);
+ static bool Find(const SkBitmap& src, SkScalar invScaleX, SkScalar invScaleY, SkBitmap* result,
+ SkResourceCache* localCache = NULL);
/*
* result must be marked isImmutable()
*/
static void Add(const SkBitmap& src, SkScalar invScaleX, SkScalar invScaleY,
- const SkBitmap& result);
+ const SkBitmap& result, SkResourceCache* localCache = NULL);
/**
* Search based on the bitmap's genID and subset. If found, returns true and
* result will be set to the matching bitmap with its pixels already locked.
*/
- static bool Find(uint32_t genID, const SkIRect& subset, SkBitmap* result);
+ static bool Find(uint32_t genID, const SkIRect& subset, SkBitmap* result,
+ SkResourceCache* localCache = NULL);
/**
* The width and the height of the provided subset must be the same as the result bitmap ones.
* result must be marked isImmutable()
*/
- static bool Add(uint32_t genID, const SkIRect& subset, const SkBitmap& result);
+ static bool Add(uint32_t genID, const SkIRect& subset, const SkBitmap& result,
+ SkResourceCache* localCache = NULL);
};
class SkMipMapCache {
diff --git a/src/core/SkResourceCache.cpp b/src/core/SkResourceCache.cpp
index 732557d0a5..3098a9a2a1 100644
--- a/src/core/SkResourceCache.cpp
+++ b/src/core/SkResourceCache.cpp
@@ -432,6 +432,11 @@ size_t SkResourceCache::SetTotalByteLimit(size_t newLimit) {
return get_cache()->setTotalByteLimit(newLimit);
}
+SkResourceCache::DiscardableFactory SkResourceCache::GetDiscardableFactory() {
+ SkAutoMutexAcquire am(gMutex);
+ return get_cache()->discardableFactory();
+}
+
SkBitmap::Allocator* SkResourceCache::GetAllocator() {
SkAutoMutexAcquire am(gMutex);
return get_cache()->allocator();
diff --git a/src/core/SkResourceCache.h b/src/core/SkResourceCache.h
index d4e1dfa376..52196985d3 100644
--- a/src/core/SkResourceCache.h
+++ b/src/core/SkResourceCache.h
@@ -126,6 +126,11 @@ public:
static void PurgeAll();
/**
+ * Returns the DiscardableFactory used by the global cache, or NULL.
+ */
+ static DiscardableFactory GetDiscardableFactory();
+
+ /**
* Use this allocator for bitmaps, so they can use ashmem when available.
* Returns NULL if the ResourceCache has not been initialized with a DiscardableFactory.
*/
@@ -189,6 +194,7 @@ public:
this->purgeAsNeeded(true);
}
+ DiscardableFactory discardableFactory() const { return fDiscardableFactory; }
SkBitmap::Allocator* allocator() const { return fAllocator; };
/**
diff --git a/tests/SkResourceCacheTest.cpp b/tests/SkResourceCacheTest.cpp
index 20c3f7f0a0..f13476a5a3 100644
--- a/tests/SkResourceCacheTest.cpp
+++ b/tests/SkResourceCacheTest.cpp
@@ -4,11 +4,13 @@
* Use of this source code is governed by a BSD-style license that can be
* found in the LICENSE file.
*/
+
#include "Test.h"
-#include "SkCanvas.h"
-#include "SkGraphics.h"
#include "SkBitmapCache.h"
+#include "SkCanvas.h"
#include "SkDiscardableMemoryPool.h"
+#include "SkGraphics.h"
+#include "SkResourceCache.h"
static const int kCanvasSize = 1;
static const int kBitmapSize = 16;
@@ -74,72 +76,93 @@ DEF_TEST(ResourceCache_SingleAllocationByteLimit, reporter) {
SkGraphics::SetResourceCacheTotalByteLimit(originalByteLimit);
}
-#if 0 // skia:2912
+////////////////////////////////////////////////////////////////////////////////////////
-static SkBitmap createAllocatedBitmap(const SkImageInfo& info) {
- SkBitmap cachedBitmap;
- cachedBitmap.setInfo(info);
- SkBitmap::Allocator* allocator = SkBitmapCache::GetAllocator();
+static void make_bitmap(SkBitmap* bitmap, const SkImageInfo& info, SkBitmap::Allocator* allocator) {
if (allocator) {
- allocator->allocPixelRef(&cachedBitmap, 0);
+ bitmap->setInfo(info);
+ allocator->allocPixelRef(bitmap, 0);
} else {
- cachedBitmap.allocPixels();
+ bitmap->allocPixels(info);
}
-
- return cachedBitmap;
}
// http://skbug.com/2894
DEF_TEST(BitmapCache_add_rect, reporter) {
+ SkResourceCache::DiscardableFactory factory = SkResourceCache::GetDiscardableFactory();
+ SkBitmap::Allocator* allocator = SkBitmapCache::GetAllocator();
+
+ SkAutoTDelete<SkResourceCache> cache;
+ if (factory) {
+ cache.reset(SkNEW_ARGS(SkResourceCache, (factory)));
+ } else {
+ const size_t byteLimit = 100 * 1024;
+ cache.reset(SkNEW_ARGS(SkResourceCache, (byteLimit)));
+ }
+ SkBitmap cachedBitmap;
+ make_bitmap(&cachedBitmap, SkImageInfo::MakeN32Premul(5, 5), allocator);
+ cachedBitmap.setImmutable();
+
SkBitmap bm;
SkIRect rect = SkIRect::MakeWH(5, 5);
- SkBitmap cachedBitmap = createAllocatedBitmap(SkImageInfo::MakeN32Premul(5, 5));
- cachedBitmap.setImmutable();
// Wrong subset size
- REPORTER_ASSERT(reporter, ! SkBitmapCache::Add(cachedBitmap.getGenerationID(), SkIRect::MakeWH(4, 6), cachedBitmap));
- REPORTER_ASSERT(reporter, ! SkBitmapCache::Find(cachedBitmap.getGenerationID(), rect, &bm));
+ REPORTER_ASSERT(reporter, !SkBitmapCache::Add(cachedBitmap.getGenerationID(), SkIRect::MakeWH(4, 6), cachedBitmap, cache));
+ REPORTER_ASSERT(reporter, !SkBitmapCache::Find(cachedBitmap.getGenerationID(), rect, &bm, cache));
// Wrong offset value
- REPORTER_ASSERT(reporter, ! SkBitmapCache::Add(cachedBitmap.getGenerationID(), SkIRect::MakeXYWH(-1, 0, 5, 5), cachedBitmap));
- REPORTER_ASSERT(reporter, ! SkBitmapCache::Find(cachedBitmap.getGenerationID(), rect, &bm));
+ REPORTER_ASSERT(reporter, !SkBitmapCache::Add(cachedBitmap.getGenerationID(), SkIRect::MakeXYWH(-1, 0, 5, 5), cachedBitmap, cache));
+ REPORTER_ASSERT(reporter, !SkBitmapCache::Find(cachedBitmap.getGenerationID(), rect, &bm, cache));
// Should not be in the cache
- REPORTER_ASSERT(reporter, !SkBitmapCache::Find(cachedBitmap.getGenerationID(), rect, &bm));
+ REPORTER_ASSERT(reporter, !SkBitmapCache::Find(cachedBitmap.getGenerationID(), rect, &bm, cache));
- REPORTER_ASSERT(reporter, SkBitmapCache::Add(cachedBitmap.getGenerationID(), rect, cachedBitmap));
+ REPORTER_ASSERT(reporter, SkBitmapCache::Add(cachedBitmap.getGenerationID(), rect, cachedBitmap, cache));
// Should be in the cache, we just added it
- REPORTER_ASSERT(reporter, SkBitmapCache::Find(cachedBitmap.getGenerationID(), rect, &bm));
+ REPORTER_ASSERT(reporter, SkBitmapCache::Find(cachedBitmap.getGenerationID(), rect, &bm, cache));
}
DEF_TEST(BitmapCache_discarded_bitmap, reporter) {
- SkBitmap bm;
- SkIRect rect = SkIRect::MakeWH(5, 5);
- SkBitmap cachedBitmap = createAllocatedBitmap(SkImageInfo::MakeN32Premul(5, 5));
+ SkResourceCache::DiscardableFactory factory = SkResourceCache::GetDiscardableFactory();
+ SkBitmap::Allocator* allocator = SkBitmapCache::GetAllocator();
+
+ SkAutoTDelete<SkResourceCache> cache;
+ if (factory) {
+ cache.reset(SkNEW_ARGS(SkResourceCache, (factory)));
+ } else {
+ const size_t byteLimit = 100 * 1024;
+ cache.reset(SkNEW_ARGS(SkResourceCache, (byteLimit)));
+ }
+ SkBitmap cachedBitmap;
+ make_bitmap(&cachedBitmap, SkImageInfo::MakeN32Premul(5, 5), allocator);
cachedBitmap.setImmutable();
cachedBitmap.unlockPixels();
+ SkBitmap bm;
+ SkIRect rect = SkIRect::MakeWH(5, 5);
+
// Add a bitmap to the cache.
- REPORTER_ASSERT(reporter, SkBitmapCache::Add(cachedBitmap.getGenerationID(), rect, cachedBitmap));
- REPORTER_ASSERT(reporter, SkBitmapCache::Find(cachedBitmap.getGenerationID(), rect, &bm));
+ REPORTER_ASSERT(reporter, SkBitmapCache::Add(cachedBitmap.getGenerationID(), rect, cachedBitmap, cache));
+ REPORTER_ASSERT(reporter, SkBitmapCache::Find(cachedBitmap.getGenerationID(), rect, &bm, cache));
// Finding more than once works fine.
- REPORTER_ASSERT(reporter, SkBitmapCache::Find(cachedBitmap.getGenerationID(), rect, &bm));
+ REPORTER_ASSERT(reporter, SkBitmapCache::Find(cachedBitmap.getGenerationID(), rect, &bm, cache));
bm.unlockPixels();
// Drop the pixels in the bitmap.
- REPORTER_ASSERT(reporter, SkGetGlobalDiscardableMemoryPool()->getRAMUsed() > 0);
- SkGetGlobalDiscardableMemoryPool()->dumpPool();
- REPORTER_ASSERT(reporter, SkGetGlobalDiscardableMemoryPool()->getRAMUsed() == 0);
+ if (factory) {
+ REPORTER_ASSERT(reporter, SkGetGlobalDiscardableMemoryPool()->getRAMUsed() > 0);
+ SkGetGlobalDiscardableMemoryPool()->dumpPool();
+ REPORTER_ASSERT(reporter, SkGetGlobalDiscardableMemoryPool()->getRAMUsed() == 0);
- // The bitmap is not in the cache since it has been dropped.
- REPORTER_ASSERT(reporter, !SkBitmapCache::Find(cachedBitmap.getGenerationID(), rect, &bm));
+ // The bitmap is not in the cache since it has been dropped.
+ REPORTER_ASSERT(reporter, !SkBitmapCache::Find(cachedBitmap.getGenerationID(), rect, &bm, cache));
+ }
- cachedBitmap = createAllocatedBitmap(SkImageInfo::MakeN32Premul(5, 5));
+ make_bitmap(&cachedBitmap, SkImageInfo::MakeN32Premul(5, 5), allocator);
cachedBitmap.setImmutable();
cachedBitmap.unlockPixels();
// We can add the bitmap back to the cache and find it again.
- REPORTER_ASSERT(reporter, SkBitmapCache::Add(cachedBitmap.getGenerationID(), rect, cachedBitmap));
- REPORTER_ASSERT(reporter, SkBitmapCache::Find(cachedBitmap.getGenerationID(), rect, &bm));
+ REPORTER_ASSERT(reporter, SkBitmapCache::Add(cachedBitmap.getGenerationID(), rect, cachedBitmap, cache));
+ REPORTER_ASSERT(reporter, SkBitmapCache::Find(cachedBitmap.getGenerationID(), rect, &bm, cache));
}
-#endif