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

Unified Diff: src/gpu/GrResourceCache.h

Issue 91453002: Speed up GrResourceCache add and lookup by using TDynamicHash (Closed) Base URL: https://skia.googlecode.com/svn/trunk
Patch Set: 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: src/gpu/GrResourceCache.h
diff --git a/src/gpu/GrResourceCache.h b/src/gpu/GrResourceCache.h
index ca30732bbc176fed947b048779022412004fcc94..7ff05b72ed0a1209f475e3b3d6dde6e3aa0bfe68 100644
--- a/src/gpu/GrResourceCache.h
+++ b/src/gpu/GrResourceCache.h
@@ -13,22 +13,16 @@
#include "GrConfig.h"
#include "GrTypes.h"
-#include "GrTHashTable.h"
#include "GrBinHashKey.h"
+#include "GrResource.h"
#include "SkMessageBus.h"
+#include "SkTDynamicHash.h"
#include "SkTInternalLList.h"
-class GrResource;
class GrResourceEntry;
class GrResourceKey {
public:
- enum {
- kHashBits = 7,
- kHashCount = 1 << kHashBits,
- kHashMask = kHashCount - 1
- };
-
static GrCacheID::Domain ScratchDomain() {
static const GrCacheID::Domain gDomain = GrCacheID::GenerateDomain();
return gDomain;
@@ -61,9 +55,8 @@ public:
this->init(id.getDomain(), id.getKey(), type, flags);
}
- //!< returns hash value [0..kHashMask] for the key
- int getHash() const {
- return fKey.getHash() & kHashMask;
+ uint32_t getHash() const {
+ return fKey.getHash();
}
bool isScratch() const {
@@ -83,14 +76,6 @@ public:
}
bool operator==(const GrResourceKey& other) const { return fKey == other.fKey; }
- bool operator<(const GrResourceKey& other) const { return fKey < other.fKey; }
-
- static bool LessThan(const GrResourceEntry& entry, const GrResourceKey& key);
- static bool Equals(const GrResourceEntry& entry, const GrResourceKey& key);
-#ifdef SK_DEBUG
- static bool LessThan(const GrResourceEntry& a, const GrResourceEntry& b);
- static bool Equals(const GrResourceEntry& a, const GrResourceEntry& b);
-#endif
private:
enum {
@@ -130,69 +115,58 @@ struct GrResourceInvalidatedMessage {
///////////////////////////////////////////////////////////////////////////////
+/** GrResourceEntry represents one entry in lookup cache (hash). It might represent multiple entries
mtklein 2013/12/03 19:02:02 I think we need to rework this comment. /** GrRes
+ * (resources) in the GrResourceCache.
+ */
class GrResourceEntry {
+ SK_DECLARE_NAMED_INTERNAL_LLIST(GrResource, CacheEntryResources, fResources);
+
public:
- GrResource* resource() const { return fResource; }
const GrResourceKey& key() const { return fKey; }
-#ifdef SK_DEBUG
- void validate() const;
-#else
- void validate() const {}
-#endif
+ void addResource(GrResource* resource);
+ /** Returns true if entry should be deleted. */
mtklein 2013/12/03 19:02:02 For consistency with the other methods below, it'd
+ bool removeResource(GrResource* resource);
+ /** Returns true if entry should be deleted. */
+ bool removeExclusiveResource(GrResource* resource);
+
+ void makeExclusive(GrResource* resource);
+ void makeNonExclusive(GrResource* resource);
+
+ CacheEntryResourcesInternalLListType& resources() { return fResources; }
+
+ static const GrResourceKey& GetKey(const GrResourceEntry& e) { return e.key(); }
+ static uint32_t GetKeyHash(const GrResourceKey& key) { return key.getHash(); }
+ static bool EqualsKey(const GrResourceEntry& a, const GrResourceKey& b) {
+ return a.key() == b;
+ }
private:
- GrResourceEntry(const GrResourceKey& key, GrResource* resource);
+ GrResourceEntry(const GrResourceKey& key, GrResource* firstResource);
~GrResourceEntry();
- GrResourceKey fKey;
- GrResource* fResource;
+ bool isEmpty() const { return fExclusiveCount == 0 && fResources.isEmpty(); }
- // we're a linked list
- SK_DECLARE_INTERNAL_LLIST_INTERFACE(GrResourceEntry);
+ GrResourceKey fKey;
+ int fExclusiveCount;
friend class GrResourceCache;
- friend class GrDLinkedList;
};
-inline bool GrResourceKey::LessThan(const GrResourceEntry& entry, const GrResourceKey& key) {
- return entry.key() < key;
-}
-
-inline bool GrResourceKey::Equals(const GrResourceEntry& entry, const GrResourceKey& key) {
- return entry.key() == key;
-}
-
-#ifdef SK_DEBUG
-inline bool GrResourceKey::LessThan(const GrResourceEntry& a, const GrResourceEntry& b) {
- return a.key() < b.key();
-}
-
-inline bool GrResourceKey::Equals(const GrResourceEntry& a, const GrResourceEntry& b) {
- return a.key() == b.key();
-}
-#endif
-
///////////////////////////////////////////////////////////////////////////////
/**
* Cache of GrResource objects.
*
* These have a corresponding GrResourceKey, built from 128bits identifying the
- * resource.
+ * resource. Multiple resources can map to same GrResourceKey.
*
* The cache stores the entries in a double-linked list, which is its LRU.
* When an entry is "locked" (i.e. given to the caller), it is moved to the
* head of the list. If/when we must purge some of the entries, we walk the
* list backwards from the tail, since those are the least recently used.
*
- * For fast searches, we maintain a sorted array (based on the GrResourceKey)
- * which we can bsearch. When a new entry is added, it is inserted into this
- * array.
- *
- * For even faster searches, a hash is computed from the Key. If there is
- * a collision between two keys with the same hash, we fall back on the
- * bsearch, and update the hash to reflect the most recent Key requested.
+ * For fast searches, we maintain a hash map based on the GrResourceKey.
*
* It is a goal to make the GrResourceCache the central repository and bookkeeper
* of all resources. It should replace the linked list of GrResources that
@@ -291,23 +265,26 @@ public:
bool hasKey(const GrResourceKey& key) const { return NULL != fCache.find(key); }
/**
- * Hide 'entry' so that future searches will not find it. Such
- * hidden entries will not be purged. The entry still counts against
+ * Hide 'resource' so that future searches will not find it. Such
+ * hidden resources will not be purged. The resource still counts against
* the cache's budget and should be made non-exclusive when exclusive access
* is no longer needed.
*/
- void makeExclusive(GrResourceEntry* entry);
+ void makeExclusive(GrResource* resource);
/**
* Restore 'entry' so that it can be found by future searches. 'entry'
* will also be purgeable (provided its lock count is now 0.)
*/
- void makeNonExclusive(GrResourceEntry* entry);
+ void makeNonExclusive(GrResource*);
mtklein 2013/12/03 19:02:02 I don't mind not naming parameters when it's obvio
/**
- * Remove a resource from the cache and delete it!
+ * Delete a resource from the cache.
*/
- void deleteResource(GrResourceEntry* entry);
+ void deleteResource(GrResource* resource) {
+ SkASSERT(1 == resource->getRefCnt());
+ this->removeResource(resource);
+ }
/**
* Removes every resource in the cache that isn't locked.
@@ -343,20 +320,25 @@ private:
kIgnore_BudgetBehavior
};
- void internalDetach(GrResourceEntry*, BudgetBehaviors behavior = kAccountFor_BudgetBehavior);
- void attachToHead(GrResourceEntry*, BudgetBehaviors behavior = kAccountFor_BudgetBehavior);
+ /** Returns true if entry holding the resource is still valid. */
+ bool removeResource(GrResource* resource);
+
+ void internalDetach(GrResource*, BudgetBehaviors behavior = kAccountFor_BudgetBehavior);
+ void attachToHead(GrResource*, BudgetBehaviors behavior = kAccountFor_BudgetBehavior);
- void removeInvalidResource(GrResourceEntry* entry);
+ void removeInvalidResource(GrResource* resource);
- GrTHashTable<GrResourceEntry, GrResourceKey, 8> fCache;
+ SkTDynamicHash<GrResourceEntry,
+ GrResourceKey,
+ GrResourceEntry::GetKey,
+ GrResourceEntry::GetKeyHash,
+ GrResourceEntry::EqualsKey> fCache;
- // We're an internal doubly linked list
- typedef SkTInternalLList<GrResourceEntry> EntryList;
- EntryList fList;
+ SK_DECLARE_NAMED_INTERNAL_LLIST(GrResource, CacheLRU, fList);
#ifdef SK_DEBUG
// These objects cannot be returned by a search
- EntryList fExclusiveList;
+ CacheLRUInternalLListType fExclusiveList;
#endif
// our budget, used in purgeAsNeeded()
@@ -389,7 +371,7 @@ private:
void purgeInvalidated();
#ifdef SK_DEBUG
- static size_t countBytes(const SkTInternalLList<GrResourceEntry>& list);
+ static size_t countBytes(const CacheLRUInternalLListType& list);
#endif
};

Powered by Google App Engine
This is Rietveld 408576698