Use SkBitmapHeap for shaders in SkGPipe.

Required adding a new feature to SkBitmapHeap, allowing it to defer
adding owners, since sometimes we flatten a shader, but then do not
unflatten it, since we already had a copy in the heap, so the owners
never get removed.

Reviewed at https://codereview.appspot.com/6464053/

Review URL: https://codereview.appspot.com/6465047

git-svn-id: http://skia.googlecode.com/svn/trunk@5082 2bbb7eff-a529-9590-31e7-b0007b416f81
diff --git a/src/pipe/SkGPipeWrite.cpp b/src/pipe/SkGPipeWrite.cpp
index fbb67be..119a809 100644
--- a/src/pipe/SkGPipeWrite.cpp
+++ b/src/pipe/SkGPipeWrite.cpp
@@ -77,6 +77,10 @@
 
     virtual void unalloc(void* ptr) SK_OVERRIDE;
 
+    void setBitmapStorage(SkBitmapHeap* heap) {
+        this->setBitmapHeap(heap);
+    }
+    
     const SkFlatData* flatToReplace() const;
 
     // Mark an SkFlatData as one that should not be returned by flatToReplace.
@@ -170,6 +174,9 @@
                     // there is no circular reference, so the SharedHeap can be
                     // safely unreffed in the destructor.
                     fSharedHeap->unref();
+                    // This eliminates a similar circular reference (Canvas owns
+                    // the FlattenableHeap which holds a ref to fSharedHeap).
+                    fFlattenableHeap.setBitmapStorage(NULL);
                     fSharedHeap = NULL;
                 }
             }
@@ -345,13 +352,15 @@
     if (isCrossProcess(fFlags)) {
         writeBufferFlags =  SkFlattenableWriteBuffer::kCrossProcess_Flag;
     } else {
-        // Needed for bitmap shaders.
-        writeBufferFlags = SkFlattenableWriteBuffer::kForceFlattenBitmapPixels_Flag;
+        // TODO: See if we can safely move this into the controller
+        writeBufferFlags = 0;
     }
 
+    fSharedHeap->deferAddingOwners();
     bool added, replaced;
     const SkFlatData* flat = fFlatDictionary.findAndReplace(
             *obj, writeBufferFlags, fFlattenableHeap.flatToReplace(), &added, &replaced);
+    fSharedHeap->endAddingOwnersDeferral(added);
     int index = flat->index();
     if (added) {
         if (isCrossProcess(fFlags)) {
@@ -432,6 +441,7 @@
             fWriter.writePtr(static_cast<void*>(fSharedHeap));
         }
     }
+    fFlattenableHeap.setBitmapStorage(fSharedHeap);
     this->doNotify();
 }