Index: src/gpu/GrTexture.cpp |
diff --git a/src/gpu/GrTexture.cpp b/src/gpu/GrTexture.cpp |
index 36ed8232d7fe2861a4177682a824d22584177baf..e1188f961b110f63cdb7f9652eac9ff4c38994e1 100644 |
--- a/src/gpu/GrTexture.cpp |
+++ b/src/gpu/GrTexture.cpp |
@@ -21,6 +21,27 @@ |
} |
} |
+/** |
+ * This method allows us to interrupt the normal deletion process and place |
+ * textures back in the texture cache when their ref count goes to zero. |
+ */ |
+void GrTexture::internal_dispose() const { |
+ if (this->texturePriv().isSetFlag((GrTextureFlags) GrTexture::kReturnToCache_FlagBit) && |
+ this->INHERITED::getContext()) { |
+ GrTexture* nonConstThis = const_cast<GrTexture *>(this); |
+ this->ref(); // restore ref count to initial setting |
+ |
+ nonConstThis->texturePriv().resetFlag((GrTextureFlags) kReturnToCache_FlagBit); |
+ nonConstThis->INHERITED::getContext()->addExistingTextureToCache(nonConstThis); |
+ |
+ // Note: "this" texture might be freed inside addExistingTextureToCache |
+ // if it is purged. |
+ return; |
+ } |
+ |
+ this->INHERITED::internal_dispose(); |
+} |
+ |
void GrTexture::dirtyMipMaps(bool mipMapsDirty) { |
if (mipMapsDirty) { |
if (kValid_MipMapsStatus == fMipMapsStatus) { |
@@ -81,12 +102,27 @@ |
pixelOpsFlags); |
} |
+void GrTexture::abandonReleaseCommon() { |
+ // In debug builds the resource cache tracks removed/exclusive textures and has an unref'ed ptr. |
+ // After abandon() or release() the resource cache will be unreachable (getContext() == NULL). |
+ // So we readd the texture to the cache here so that it is removed from the exclusive list and |
+ // there is no longer an unref'ed ptr to the texture in the cache. |
+ if (this->texturePriv().isSetFlag((GrTextureFlags)kReturnToCache_FlagBit)) { |
+ SkASSERT(!this->wasDestroyed()); |
+ this->ref(); // restores the ref the resource cache gave up when it marked this exclusive. |
+ this->texturePriv().resetFlag((GrTextureFlags) kReturnToCache_FlagBit); |
+ this->getContext()->addExistingTextureToCache(this); |
+ } |
+} |
+ |
void GrTexture::onRelease() { |
+ this->abandonReleaseCommon(); |
SkASSERT(!this->texturePriv().isSetFlag((GrTextureFlags) kReturnToCache_FlagBit)); |
INHERITED::onRelease(); |
} |
void GrTexture::onAbandon() { |
+ this->abandonReleaseCommon(); |
if (fRenderTarget.get()) { |
fRenderTarget->abandon(); |
} |