Fixing crash in cloning empty SkPicture object

BUG=https://code.google.com/p/chromium/issues/detail?id=172062
TEST=Pictures unit test, test_clone_empty
Review URL: https://codereview.appspot.com/7223048

git-svn-id: http://skia.googlecode.com/svn/trunk@7430 2bbb7eff-a529-9590-31e7-b0007b416f81
diff --git a/src/core/SkPicturePlayback.cpp b/src/core/SkPicturePlayback.cpp
index 21fa034..7cd25cc 100644
--- a/src/core/SkPicturePlayback.cpp
+++ b/src/core/SkPicturePlayback.cpp
@@ -181,6 +181,7 @@
     SkSafeRef(fStateTree);
 
     if (deepCopyInfo) {
+        int paintCount = SafeCount(src.fPaints);
 
         if (src.fBitmaps) {
             fBitmaps = SkTRefArray<SkBitmap>::Create(src.fBitmaps->begin(), src.fBitmaps->count());
@@ -192,7 +193,7 @@
              * this point we would need to pass the SkBitmapHeap so that we don't unnecessarily
              * flatten the pixels in a bitmap shader.
              */
-            deepCopyInfo->paintData.setCount(src.fPaints->count());
+            deepCopyInfo->paintData.setCount(paintCount);
 
             /* Use an SkBitmapHeap to avoid flattening bitmaps in shaders. If there already is one,
              * use it. If this SkPicturePlayback was created from a stream, fBitmapHeap will be
@@ -209,7 +210,7 @@
             }
 
             SkDEBUGCODE(int heapSize = SafeCount(fBitmapHeap.get());)
-            for (int i = 0; i < src.fPaints->count(); i++) {
+            for (int i = 0; i < paintCount; i++) {
                 if (needs_deep_copy(src.fPaints->at(i))) {
                     deepCopyInfo->paintData[i] = SkFlatData::Create(&deepCopyInfo->controller,
                                                                     &src.fPaints->at(i), 0,
@@ -226,11 +227,11 @@
             deepCopyInfo->initialized = true;
         }
 
-        fPaints = SkTRefArray<SkPaint>::Create(src.fPaints->count());
-        SkASSERT(deepCopyInfo->paintData.count() == src.fPaints->count());
+        fPaints = SkTRefArray<SkPaint>::Create(paintCount);
+        SkASSERT(deepCopyInfo->paintData.count() == paintCount);
         SkBitmapHeap* bmHeap = deepCopyInfo->controller.getBitmapHeap();
         SkTypefacePlayback* tfPlayback = deepCopyInfo->controller.getTypefacePlayback();
-        for (int i = 0; i < src.fPaints->count(); i++) {
+        for (int i = 0; i < paintCount; i++) {
             if (deepCopyInfo->paintData[i]) {
                 deepCopyInfo->paintData[i]->unflatten(&fPaints->writableAt(i),
                                                       &SkUnflattenObjectProc<SkPaint>,
diff --git a/tests/PictureTest.cpp b/tests/PictureTest.cpp
index 395ce4a..f6a18c1 100644
--- a/tests/PictureTest.cpp
+++ b/tests/PictureTest.cpp
@@ -395,6 +395,28 @@
     REPORTER_ASSERT(reporter, picture1->equals(picture2));
 }
 
+static void test_clone_empty(skiatest::Reporter* reporter) {
+    // This is a regression test for crbug.com/172062
+    // Before the fix, we used to crash accessing a null pointer when we
+    // had a picture with no paints. This test passes by not crashing.
+    {
+        SkPicture picture;
+        picture.beginRecording(1, 1);
+        picture.endRecording();
+        SkPicture* destPicture = picture.clone();
+        REPORTER_ASSERT(reporter, NULL != destPicture);
+        destPicture->unref();
+    }
+    {
+        // Test without call to endRecording
+        SkPicture picture;
+        picture.beginRecording(1, 1);
+        SkPicture* destPicture = picture.clone();
+        REPORTER_ASSERT(reporter, NULL != destPicture);
+        destPicture->unref();
+    }
+}
+
 static void TestPicture(skiatest::Reporter* reporter) {
 #ifdef SK_DEBUG
     test_deleting_empty_playback();
@@ -405,6 +427,7 @@
     test_peephole(reporter);
     test_gatherpixelrefs(reporter);
     test_bitmap_with_encoded_data(reporter);
+    test_clone_empty(reporter);
 }
 
 #include "TestClassDef.h"