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

Unified Diff: src/gpu/GrResourceCache.cpp

Issue 2361093002: Change implementation of flush-count based GrGpuResource purging (Closed)
Patch Set: fix var spelling Created 4 years, 3 months 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
« no previous file with comments | « src/gpu/GrResourceCache.h ('k') | tests/ResourceCacheTest.cpp » ('j') | no next file with comments »
Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
Index: src/gpu/GrResourceCache.cpp
diff --git a/src/gpu/GrResourceCache.cpp b/src/gpu/GrResourceCache.cpp
index 529f87c124880bbefd0c724bd2e48016841d4cd9..9462a7384d73d45d3a5a857060ab7755d7082903 100644
--- a/src/gpu/GrResourceCache.cpp
+++ b/src/gpu/GrResourceCache.cpp
@@ -74,49 +74,23 @@ GrResourceCache::GrResourceCache(const GrCaps* caps)
, fBudgetedCount(0)
, fBudgetedBytes(0)
, fRequestFlush(false)
- , fFlushTimestamps(nullptr)
- , fLastFlushTimestampIndex(0)
+ , fExternalFlushCnt(0)
, fPreferVRAMUseOverFlushes(caps->preferVRAMUseOverFlushes()) {
SkDEBUGCODE(fCount = 0;)
SkDEBUGCODE(fNewlyPurgeableResourceForValidation = nullptr;)
- this->resetFlushTimestamps();
}
GrResourceCache::~GrResourceCache() {
this->releaseAll();
- delete[] fFlushTimestamps;
}
void GrResourceCache::setLimits(int count, size_t bytes, int maxUnusedFlushes) {
fMaxCount = count;
fMaxBytes = bytes;
fMaxUnusedFlushes = maxUnusedFlushes;
- this->resetFlushTimestamps();
this->purgeAsNeeded();
}
-void GrResourceCache::resetFlushTimestamps() {
- delete[] fFlushTimestamps;
-
- // We assume this number is a power of two when wrapping indices into the timestamp array.
- fMaxUnusedFlushes = SkNextPow2(fMaxUnusedFlushes);
-
- // Since our implementation is to store the timestamps of the last fMaxUnusedFlushes flush calls
- // we just turn the feature off if that array would be large.
- static const int kMaxSupportedTimestampHistory = 128;
-
- if (fMaxUnusedFlushes > kMaxSupportedTimestampHistory) {
- fFlushTimestamps = nullptr;
- return;
- }
-
- fFlushTimestamps = new uint32_t[fMaxUnusedFlushes];
- fLastFlushTimestampIndex = 0;
- // Set all the historical flush timestamps to initially be at the beginning of time (timestamp
- // 0).
- sk_bzero(fFlushTimestamps, fMaxUnusedFlushes * sizeof(uint32_t));
-}
-
void GrResourceCache::insertResource(GrGpuResource* resource) {
SkASSERT(resource);
SkASSERT(!this->isInCache(resource));
@@ -390,6 +364,7 @@ void GrResourceCache::notifyCntReachedZero(GrGpuResource* resource, uint32_t fla
SkASSERT(resource->isPurgeable());
this->removeFromNonpurgeableArray(resource);
fPurgeableQueue.insert(resource);
+ resource->cacheAccess().setFlushCntWhenResourceBecamePurgeable(fExternalFlushCnt);
if (SkBudgeted::kNo == resource->resourcePriv().isBudgeted()) {
// Check whether this resource could still be used as a scratch resource.
@@ -474,20 +449,29 @@ void GrResourceCache::purgeAsNeeded() {
this->processInvalidUniqueKeys(invalidKeyMsgs);
}
- if (fFlushTimestamps) {
- // Assuming kNumFlushesToDeleteUnusedResource is a power of 2.
- SkASSERT(SkIsPow2(fMaxUnusedFlushes));
- int oldestFlushIndex = (fLastFlushTimestampIndex + 1) & (fMaxUnusedFlushes - 1);
-
- uint32_t oldestAllowedTimestamp = fFlushTimestamps[oldestFlushIndex];
- while (fPurgeableQueue.count()) {
- uint32_t oldestResourceTimestamp = fPurgeableQueue.peek()->cacheAccess().timestamp();
- if (oldestAllowedTimestamp < oldestResourceTimestamp) {
- break;
+ if (fMaxUnusedFlushes > 0) {
+ // We want to know how many complete flushes have occurred without the resource being used.
+ // If the resource was tagged when fExternalFlushCnt was N then this means it became
+ // purgeable during activity that became the N+1th flush. So when the flush count is N+2
+ // it has sat in the purgeable queue for one entire flush.
+ uint32_t oldestAllowedFlushCnt = fExternalFlushCnt - fMaxUnusedFlushes - 1;
+ // check for underflow
+ if (oldestAllowedFlushCnt < fExternalFlushCnt) {
+ while (fPurgeableQueue.count()) {
+ uint32_t flushWhenResourceBecamePurgeable =
+ fPurgeableQueue.peek()->cacheAccess().flushCntWhenResourceBecamePurgeable();
+ if (oldestAllowedFlushCnt < flushWhenResourceBecamePurgeable) {
+ // Resources were given both LRU timestamps and tagged with a flush cnt when
+ // they first became purgeable. The LRU timestamp won't change again until the
+ // resource is made non-purgeable again. So, at this point all the remaining
+ // resources in the timestamp-sorted queue will have a flush count >= to this
+ // one.
+ break;
+ }
+ GrGpuResource* resource = fPurgeableQueue.peek();
+ SkASSERT(resource->isPurgeable());
+ resource->cacheAccess().release();
}
- GrGpuResource* resource = fPurgeableQueue.peek();
- SkASSERT(resource->isPurgeable());
- resource->cacheAccess().release();
}
}
@@ -566,13 +550,8 @@ uint32_t GrResourceCache::getNextTimestamp() {
fPurgeableQueue.pop();
}
- struct Less {
- bool operator()(GrGpuResource* a, GrGpuResource* b) {
- return CompareTimestamp(a,b);
- }
- };
- Less less;
- SkTQSort(fNonpurgeableResources.begin(), fNonpurgeableResources.end() - 1, less);
+ SkTQSort(fNonpurgeableResources.begin(), fNonpurgeableResources.end() - 1,
+ CompareTimestamp);
// Pick resources out of the purgeable and non-purgeable arrays based on lowest
// timestamp and assign new timestamps.
@@ -611,9 +590,6 @@ uint32_t GrResourceCache::getNextTimestamp() {
// count should be the next timestamp we return.
SkASSERT(fTimestamp == SkToU32(count));
-
- // The historical timestamps of flushes are now invalid.
- this->resetFlushTimestamps();
}
}
return fTimestamp++;
@@ -628,13 +604,12 @@ void GrResourceCache::notifyFlushOccurred(FlushType type) {
fRequestFlush = false;
break;
case FlushType::kExternal:
- if (fFlushTimestamps) {
- SkASSERT(SkIsPow2(fMaxUnusedFlushes));
- fLastFlushTimestampIndex = (fLastFlushTimestampIndex + 1) & (fMaxUnusedFlushes - 1);
- // get the timestamp before accessing fFlushTimestamps because getNextTimestamp will
- // reallocate fFlushTimestamps on timestamp overflow.
- uint32_t timestamp = this->getNextTimestamp();
- fFlushTimestamps[fLastFlushTimestampIndex] = timestamp;
+ ++fExternalFlushCnt;
+ if (0 == fExternalFlushCnt) {
+ // When this wraps just reset all the purgeable resources' last used flush state.
+ for (int i = 0; i < fPurgeableQueue.count(); ++i) {
+ fPurgeableQueue.at(i)->cacheAccess().setFlushCntWhenResourceBecamePurgeable(0);
+ }
}
break;
}
« no previous file with comments | « src/gpu/GrResourceCache.h ('k') | tests/ResourceCacheTest.cpp » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698