Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(1754)

Unified Diff: Source/core/platform/graphics/ImageDecodingStore.cpp

Issue 99103006: Moving GraphicsContext and dependencies from core to platform. (Closed) Base URL: svn://svn.chromium.org/blink/trunk
Patch Set: Final patch - fixes Android Created 7 years ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
Index: Source/core/platform/graphics/ImageDecodingStore.cpp
diff --git a/Source/core/platform/graphics/ImageDecodingStore.cpp b/Source/core/platform/graphics/ImageDecodingStore.cpp
deleted file mode 100644
index 036bf843e3ba70a284194dd299de8e8c562c7aaf..0000000000000000000000000000000000000000
--- a/Source/core/platform/graphics/ImageDecodingStore.cpp
+++ /dev/null
@@ -1,408 +0,0 @@
-/*
- * Copyright (C) 2012 Google Inc. All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions
- * are met:
- * 1. Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- * 2. Redistributions in binary form must reproduce the above copyright
- * notice, this list of conditions and the following disclaimer in the
- * documentation and/or other materials provided with the distribution.
- *
- * THIS SOFTWARE IS PROVIDED BY APPLE COMPUTER, INC. ``AS IS'' AND ANY
- * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
- * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
- * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE COMPUTER, INC. OR
- * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
- * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
- * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
- * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
- * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
- * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
- * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
- */
-
-#include "config.h"
-#include "core/platform/graphics/ImageDecodingStore.h"
-
-#include "platform/TraceEvent.h"
-
-namespace WebCore {
-
-namespace {
-
-// 32MB memory limit for cache.
-static const size_t defaultCacheLimitInBytes = 32768 * 1024;
-static ImageDecodingStore* s_instance = 0;
-
-static void setInstance(ImageDecodingStore* imageDecodingStore)
-{
- delete s_instance;
- s_instance = imageDecodingStore;
-}
-
-} // namespace
-
-ImageDecodingStore::ImageDecodingStore()
- : m_cacheLimitInBytes(defaultCacheLimitInBytes)
- , m_memoryUsageInBytes(0)
-{
-}
-
-ImageDecodingStore::~ImageDecodingStore()
-{
-#ifndef NDEBUG
- setCacheLimitInBytes(0);
- ASSERT(!m_imageCacheMap.size());
- ASSERT(!m_decoderCacheMap.size());
- ASSERT(!m_orderedCacheList.size());
- ASSERT(!m_imageCacheKeyMap.size());
- ASSERT(!m_decoderCacheKeyMap.size());
-#endif
-}
-
-ImageDecodingStore* ImageDecodingStore::instance()
-{
- return s_instance;
-}
-
-void ImageDecodingStore::initializeOnce()
-{
- setInstance(ImageDecodingStore::create().leakPtr());
-}
-
-void ImageDecodingStore::shutdown()
-{
- setInstance(0);
-}
-
-bool ImageDecodingStore::lockCache(const ImageFrameGenerator* generator, const SkISize& scaledSize, size_t index, const ScaledImageFragment** cachedImage)
-{
- ASSERT(cachedImage);
-
- Vector<OwnPtr<CacheEntry> > cacheEntriesToDelete;
- {
- MutexLocker lock(m_mutex);
- // Public access is restricted to complete images only.
- ImageCacheMap::iterator iter = m_imageCacheMap.find(ImageCacheEntry::makeCacheKey(generator, scaledSize, index, ScaledImageFragment::CompleteImage));
- if (iter == m_imageCacheMap.end())
- return false;
- return lockCacheEntryInternal(iter->value.get(), cachedImage, &cacheEntriesToDelete);
- }
-}
-
-void ImageDecodingStore::unlockCache(const ImageFrameGenerator* generator, const ScaledImageFragment* cachedImage)
-{
- MutexLocker lock(m_mutex);
- cachedImage->bitmap().unlockPixels();
- ImageCacheMap::iterator iter = m_imageCacheMap.find(ImageCacheEntry::makeCacheKey(generator, cachedImage->scaledSize(), cachedImage->index(), cachedImage->generation()));
- ASSERT_WITH_SECURITY_IMPLICATION(iter != m_imageCacheMap.end());
-
- CacheEntry* cacheEntry = iter->value.get();
- cacheEntry->decrementUseCount();
-
- // Put the entry to the end of list.
- m_orderedCacheList.remove(cacheEntry);
- m_orderedCacheList.append(cacheEntry);
-}
-
-const ScaledImageFragment* ImageDecodingStore::insertAndLockCache(const ImageFrameGenerator* generator, PassOwnPtr<ScaledImageFragment> image)
-{
- // Prune old cache entries to give space for the new one.
- prune();
-
- ScaledImageFragment* newImage = image.get();
- OwnPtr<ImageCacheEntry> newCacheEntry = ImageCacheEntry::createAndUse(generator, image);
- Vector<OwnPtr<CacheEntry> > cacheEntriesToDelete;
- {
- MutexLocker lock(m_mutex);
-
- ImageCacheMap::iterator iter = m_imageCacheMap.find(newCacheEntry->cacheKey());
-
- // It is rare but possible that the key of a new cache entry is found.
- // This happens if the generation ID of the image object wraps around.
- // In this case we will try to return the existing cached object and
- // discard the new cache object.
- if (iter != m_imageCacheMap.end()) {
- const ScaledImageFragment* oldImage;
- if (lockCacheEntryInternal(iter->value.get(), &oldImage, &cacheEntriesToDelete)) {
- newCacheEntry->decrementUseCount();
- return oldImage;
- }
- }
-
- // The new image is not locked yet so do it here.
- newImage->bitmap().lockPixels();
- insertCacheInternal(newCacheEntry.release(), &m_imageCacheMap, &m_imageCacheKeyMap);
- }
- return newImage;
-}
-
-bool ImageDecodingStore::lockDecoder(const ImageFrameGenerator* generator, const SkISize& scaledSize, ImageDecoder** decoder)
-{
- ASSERT(decoder);
-
- MutexLocker lock(m_mutex);
- DecoderCacheMap::iterator iter = m_decoderCacheMap.find(DecoderCacheEntry::makeCacheKey(generator, scaledSize));
- if (iter == m_decoderCacheMap.end())
- return false;
-
- DecoderCacheEntry* cacheEntry = iter->value.get();
-
- // There can only be one user of a decoder at a time.
- ASSERT(!cacheEntry->useCount());
- cacheEntry->incrementUseCount();
- *decoder = cacheEntry->cachedDecoder();
- return true;
-}
-
-void ImageDecodingStore::unlockDecoder(const ImageFrameGenerator* generator, const ImageDecoder* decoder)
-{
- MutexLocker lock(m_mutex);
- DecoderCacheMap::iterator iter = m_decoderCacheMap.find(DecoderCacheEntry::makeCacheKey(generator, decoder));
- ASSERT_WITH_SECURITY_IMPLICATION(iter != m_decoderCacheMap.end());
-
- CacheEntry* cacheEntry = iter->value.get();
- cacheEntry->decrementUseCount();
-
- // Put the entry to the end of list.
- m_orderedCacheList.remove(cacheEntry);
- m_orderedCacheList.append(cacheEntry);
-}
-
-void ImageDecodingStore::insertDecoder(const ImageFrameGenerator* generator, PassOwnPtr<ImageDecoder> decoder, bool isDiscardable)
-{
- // Prune old cache entries to give space for the new one.
- prune();
-
- OwnPtr<DecoderCacheEntry> newCacheEntry = DecoderCacheEntry::create(generator, decoder, isDiscardable);
-
- MutexLocker lock(m_mutex);
- ASSERT(!m_decoderCacheMap.contains(newCacheEntry->cacheKey()));
- insertCacheInternal(newCacheEntry.release(), &m_decoderCacheMap, &m_decoderCacheKeyMap);
-}
-
-void ImageDecodingStore::removeDecoder(const ImageFrameGenerator* generator, const ImageDecoder* decoder)
-{
- Vector<OwnPtr<CacheEntry> > cacheEntriesToDelete;
- {
- MutexLocker lock(m_mutex);
- DecoderCacheMap::iterator iter = m_decoderCacheMap.find(DecoderCacheEntry::makeCacheKey(generator, decoder));
- ASSERT_WITH_SECURITY_IMPLICATION(iter != m_decoderCacheMap.end());
-
- CacheEntry* cacheEntry = iter->value.get();
- ASSERT(cacheEntry->useCount());
- cacheEntry->decrementUseCount();
-
- // Delete only one decoder cache entry. Ownership of the cache entry
- // is transfered to cacheEntriesToDelete such that object can be deleted
- // outside of the lock.
- removeFromCacheInternal(cacheEntry, &cacheEntriesToDelete);
-
- // Remove from LRU list.
- removeFromCacheListInternal(cacheEntriesToDelete);
- }
-}
-
-bool ImageDecodingStore::isCached(const ImageFrameGenerator* generator, const SkISize& scaledSize, size_t index)
-{
- MutexLocker lock(m_mutex);
- ImageCacheMap::iterator iter = m_imageCacheMap.find(ImageCacheEntry::makeCacheKey(generator, scaledSize, index, ScaledImageFragment::CompleteImage));
- if (iter == m_imageCacheMap.end())
- return false;
- return true;
-}
-
-void ImageDecodingStore::removeCacheIndexedByGenerator(const ImageFrameGenerator* generator)
-{
- Vector<OwnPtr<CacheEntry> > cacheEntriesToDelete;
- {
- MutexLocker lock(m_mutex);
-
- // Remove image cache objects and decoder cache objects associated
- // with a ImageFrameGenerator.
- removeCacheIndexedByGeneratorInternal(&m_imageCacheMap, &m_imageCacheKeyMap, generator, &cacheEntriesToDelete);
- removeCacheIndexedByGeneratorInternal(&m_decoderCacheMap, &m_decoderCacheKeyMap, generator, &cacheEntriesToDelete);
-
- // Remove from LRU list as well.
- removeFromCacheListInternal(cacheEntriesToDelete);
- }
-}
-
-void ImageDecodingStore::clear()
-{
- size_t cacheLimitInBytes;
- {
- MutexLocker lock(m_mutex);
- cacheLimitInBytes = m_cacheLimitInBytes;
- m_cacheLimitInBytes = 0;
- }
-
- prune();
-
- {
- MutexLocker lock(m_mutex);
- m_cacheLimitInBytes = cacheLimitInBytes;
- }
-}
-
-void ImageDecodingStore::setCacheLimitInBytes(size_t cacheLimit)
-{
- {
- MutexLocker lock(m_mutex);
- m_cacheLimitInBytes = cacheLimit;
- }
- prune();
-}
-
-size_t ImageDecodingStore::memoryUsageInBytes()
-{
- MutexLocker lock(m_mutex);
- return m_memoryUsageInBytes;
-}
-
-int ImageDecodingStore::cacheEntries()
-{
- MutexLocker lock(m_mutex);
- return m_imageCacheMap.size() + m_decoderCacheMap.size();
-}
-
-int ImageDecodingStore::imageCacheEntries()
-{
- MutexLocker lock(m_mutex);
- return m_imageCacheMap.size();
-}
-
-int ImageDecodingStore::decoderCacheEntries()
-{
- MutexLocker lock(m_mutex);
- return m_decoderCacheMap.size();
-}
-
-void ImageDecodingStore::prune()
-{
- TRACE_EVENT0("webkit", "ImageDecodingStore::prune");
-
- Vector<OwnPtr<CacheEntry> > cacheEntriesToDelete;
- {
- MutexLocker lock(m_mutex);
-
- // Head of the list is the least recently used entry.
- const CacheEntry* cacheEntry = m_orderedCacheList.head();
-
- // Walk the list of cache entries starting from the least recently used
- // and then keep them for deletion later.
- while (cacheEntry && (m_memoryUsageInBytes > m_cacheLimitInBytes || !m_cacheLimitInBytes)) {
- // Cache is not used; Remove it.
- if (!cacheEntry->useCount())
- removeFromCacheInternal(cacheEntry, &cacheEntriesToDelete);
- cacheEntry = cacheEntry->next();
- }
-
- // Remove from cache list as well.
- removeFromCacheListInternal(cacheEntriesToDelete);
- }
-}
-
-bool ImageDecodingStore::lockCacheEntryInternal(ImageCacheEntry* cacheEntry, const ScaledImageFragment** cachedImage, Vector<OwnPtr<CacheEntry> >* deletionList)
-{
- ScaledImageFragment* image = cacheEntry->cachedImage();
-
- image->bitmap().lockPixels();
-
- // Memory for this image entry might be discarded already.
- // In this case remove the entry.
- if (!image->bitmap().getPixels()) {
- image->bitmap().unlockPixels();
- removeFromCacheInternal(cacheEntry, &m_imageCacheMap, &m_imageCacheKeyMap, deletionList);
- removeFromCacheListInternal(*deletionList);
- return false;
- }
- cacheEntry->incrementUseCount();
- *cachedImage = image;
- return true;
-}
-
-template<class T, class U, class V>
-void ImageDecodingStore::insertCacheInternal(PassOwnPtr<T> cacheEntry, U* cacheMap, V* identifierMap)
-{
- // Usage of discardable memory is not counted because we want to use more
- // than the cache limit allows. Cache limit only applies to non-discardable
- // objects.
- if (!cacheEntry->isDiscardable())
- incrementMemoryUsage(cacheEntry->memoryUsageInBytes());
-
- // m_orderedCacheList is used to support LRU operations to reorder cache
- // entries quickly.
- m_orderedCacheList.append(cacheEntry.get());
-
- typename U::KeyType key = cacheEntry->cacheKey();
- typename V::AddResult result = identifierMap->add(cacheEntry->generator(), typename V::MappedType());
- result.iterator->value.add(key);
- cacheMap->add(key, cacheEntry);
-
- TRACE_COUNTER1("webkit", "ImageDecodingStoreMemoryUsageBytes", m_memoryUsageInBytes);
- TRACE_COUNTER1("webkit", "ImageDecodingStoreNumOfImages", m_imageCacheMap.size());
- TRACE_COUNTER1("webkit", "ImageDecodingStoreNumOfDecoders", m_decoderCacheMap.size());
-}
-
-template<class T, class U, class V>
-void ImageDecodingStore::removeFromCacheInternal(const T* cacheEntry, U* cacheMap, V* identifierMap, Vector<OwnPtr<CacheEntry> >* deletionList)
-{
- if (!cacheEntry->isDiscardable())
- decrementMemoryUsage(cacheEntry->memoryUsageInBytes());
-
- // Remove entry from identifier map.
- typename V::iterator iter = identifierMap->find(cacheEntry->generator());
- ASSERT(iter != identifierMap->end());
- iter->value.remove(cacheEntry->cacheKey());
- if (!iter->value.size())
- identifierMap->remove(iter);
-
- // Remove entry from cache map.
- deletionList->append(cacheMap->take(cacheEntry->cacheKey()));
-
- TRACE_COUNTER1("webkit", "ImageDecodingStoreMemoryUsageBytes", m_memoryUsageInBytes);
- TRACE_COUNTER1("webkit", "ImageDecodingStoreNumOfImages", m_imageCacheMap.size());
- TRACE_COUNTER1("webkit", "ImageDecodingStoreNumOfDecoders", m_decoderCacheMap.size());
-}
-
-void ImageDecodingStore::removeFromCacheInternal(const CacheEntry* cacheEntry, Vector<OwnPtr<CacheEntry> >* deletionList)
-{
- if (cacheEntry->type() == CacheEntry::TypeImage) {
- removeFromCacheInternal(static_cast<const ImageCacheEntry*>(cacheEntry), &m_imageCacheMap, &m_imageCacheKeyMap, deletionList);
- } else if (cacheEntry->type() == CacheEntry::TypeDecoder) {
- removeFromCacheInternal(static_cast<const DecoderCacheEntry*>(cacheEntry), &m_decoderCacheMap, &m_decoderCacheKeyMap, deletionList);
- } else {
- ASSERT(false);
- }
-}
-
-template<class U, class V>
-void ImageDecodingStore::removeCacheIndexedByGeneratorInternal(U* cacheMap, V* identifierMap, const ImageFrameGenerator* generator, Vector<OwnPtr<CacheEntry> >* deletionList)
-{
- typename V::iterator iter = identifierMap->find(generator);
- if (iter == identifierMap->end())
- return;
-
- // Get all cache identifiers associated with generator.
- Vector<typename U::KeyType> cacheIdentifierList;
- copyToVector(iter->value, cacheIdentifierList);
-
- // For each cache identifier find the corresponding CacheEntry and remove it.
- for (size_t i = 0; i < cacheIdentifierList.size(); ++i) {
- ASSERT(cacheMap->contains(cacheIdentifierList[i]));
- const typename U::MappedType::PtrType cacheEntry = cacheMap->get(cacheIdentifierList[i]);
- ASSERT(!cacheEntry->useCount());
- removeFromCacheInternal(cacheEntry, cacheMap, identifierMap, deletionList);
- }
-}
-
-void ImageDecodingStore::removeFromCacheListInternal(const Vector<OwnPtr<CacheEntry> >& deletionList)
-{
- for (size_t i = 0; i < deletionList.size(); ++i)
- m_orderedCacheList.remove(deletionList[i].get());
-}
-
-} // namespace WebCore
« no previous file with comments | « Source/core/platform/graphics/ImageDecodingStore.h ('k') | Source/core/platform/graphics/ImageDecodingStoreTest.cpp » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698