[SCM] WebKit Debian packaging branch, webkit-1.3, updated. upstream/1.3.7-4207-g178b198

aroben at apple.com aroben at apple.com
Sun Feb 20 23:08:11 UTC 2011


The following commit has been merged in the webkit-1.3 branch:
commit 7317c4592f62d7ea26f89f22de3f1d6cc02167b5
Author: aroben at apple.com <aroben at apple.com@268f45cc-cd09-0410-ab3c-d52691b4dbfc>
Date:   Tue Jan 18 01:44:40 2011 +0000

    Don't access the CACFLayerRef's sublayers directly from PlatformCALayer
    
    There might be a secret extra sublayer (the tile parent layer) that
    PlatformCALayer doesn't know about. When PlatformCALayer would
    encounter this, it would try to use the tile parent layer's
    PlatformCALayer wrapper, which was null, and then would crash. We now
    ask PlatformCALayerWinInternal for the sublayer list, since that class
    knows about the tile parent layer and can exclude it from the sublayer
    list.
    
    Covered by compositing/tiling/huge-layer-resize.html.
    
    Fixes <http://webkit.org/b/52597> Crash beneath
    PlatformCALayer::adoptSublayers when switching out of tiling mode
    (null-dereference of a PlatformCALayer)
    
    Reviewed by Darin Adler and Chris Marrin.
    
    LayoutTests:
    
    Make compositing/tiling/huge-layer-resize.html faster, more reliable,
    and more crashy (when there's a WebKit bug)
    
    This test was trying to cause a layout/paint to happen by returning to
    the event loop for a certain amount of time via setTimeout. But this
    didn't always result in a layout/paint (at least on Windows). We now
    force the layout/paint explicitly, which also lets us speed up the test
    by removing the setTimeouts.
    
    * compositing/tiling/huge-layer-resize.html:
    (testOnLoad): Changed to use recordLayerTree, which forces a
    layout/paint, instead of hoping that setTimeout will do the trick.
    (recordLayerTree): Forces a layout/paint, then dumps the layer tree.
    
    Source/WebCore:
    
    * platform/graphics/ca/win/PlatformCALayerWin.cpp:
    (PlatformCALayer::adoptSublayers):
    (printLayer):
    Changed to use PlatformCALayerWinInternal::getSublayers.
    
    * platform/graphics/ca/win/PlatformCALayerWinInternal.cpp:
    (PlatformCALayerWinInternal::getSublayers): Added. Retrieves the list
    of PlatformCALayers that represent our sublayers. Significantly, this
    code knows about the tile parent layer and can thus exclude it.
    
    * platform/graphics/ca/win/PlatformCALayerWinInternal.h: Added
    getSublayers.
    
    git-svn-id: http://svn.webkit.org/repository/webkit/trunk@75985 268f45cc-cd09-0410-ab3c-d52691b4dbfc

diff --git a/LayoutTests/ChangeLog b/LayoutTests/ChangeLog
index 7ac1e2e..2afe995 100644
--- a/LayoutTests/ChangeLog
+++ b/LayoutTests/ChangeLog
@@ -1,3 +1,25 @@
+2011-01-17  Adam Roben  <aroben at apple.com>
+
+        Make compositing/tiling/huge-layer-resize.html faster, more reliable,
+        and more crashy (when there's a WebKit bug)
+
+        This test was trying to cause a layout/paint to happen by returning to
+        the event loop for a certain amount of time via setTimeout. But this
+        didn't always result in a layout/paint (at least on Windows). We now
+        force the layout/paint explicitly, which also lets us speed up the test
+        by removing the setTimeouts.
+
+        Reviewed by Darin Adler and Chris Marrin.
+
+        Test for <http://webkit.org/b/52597> Crash beneath
+        PlatformCALayer::adoptSublayers when switching out of tiling mode
+        (null-dereference of a PlatformCALayer)
+
+        * compositing/tiling/huge-layer-resize.html:
+        (testOnLoad): Changed to use recordLayerTree, which forces a
+        layout/paint, instead of hoping that setTimeout will do the trick.
+        (recordLayerTree): Forces a layout/paint, then dumps the layer tree.
+
 2011-01-17  Dan Bernstein  <mitz at apple.com>
 
         Reviewed by Darin Adler.
diff --git a/LayoutTests/compositing/tiling/huge-layer-resize.html b/LayoutTests/compositing/tiling/huge-layer-resize.html
index 83bf4c4..82072ab 100644
--- a/LayoutTests/compositing/tiling/huge-layer-resize.html
+++ b/LayoutTests/compositing/tiling/huge-layer-resize.html
@@ -26,45 +26,36 @@
     }
     </style>
     <script type="text/javascript" charset="utf-8">
-        if (window.layoutTestController) {
+        if (window.layoutTestController)
             layoutTestController.dumpAsText();
-            layoutTestController.waitUntilDone();
-        }
         
-        result = "";
-
         function testOnLoad()
         {
             // Small layer first
-            window.setTimeout(function() {
-                if (window.layoutTestController)
-                    result = "First (small layer):<br>" + layoutTestController.layerTreeAsText();
-            }, 0);
-            
+            var result = recordLayerTree("First (small layer):<br>");
+
             // Huge layer second
-            window.setTimeout(function() {
-                document.getElementById('container').style.height = "5000px";
-                
-                // Let it render
-                window.setTimeout(function() {
-                    if (window.layoutTestController)
-                        result += "<br><br>Second (huge layer):<br>" + layoutTestController.layerTreeAsText();
-                }, 0);
-            }, 100);
-            
+            document.getElementById('container').style.height = "5000px";
+            result += recordLayerTree("<br><br>Second (huge layer):<br>");
+
             // Small layer third
-            window.setTimeout(function() {
-                document.getElementById('container').style.height = "500px";
-                
-                // Let it render
-                window.setTimeout(function() {
-                    if (window.layoutTestController) {
-                        result += "<br><br>Third (small layer):<br>" + layoutTestController.layerTreeAsText();
-                        document.getElementById('layers').innerHTML = result;
-                        layoutTestController.notifyDone();
-                    }
-                }, 0);
-            }, 200);
+            document.getElementById('container').style.height = "500px";
+            result += recordLayerTree("<br><br>Third (small layer):<br>");
+
+            document.getElementById('layers').innerHTML = result;
+        }
+
+        function recordLayerTree(messagePrefix)
+        {
+            if (!window.layoutTestController)
+                return "";
+
+            // Force a layout and a paint to make sure the compositing layers
+            // have been updated.
+            document.body.offsetLeft;
+            layoutTestController.display();
+
+            return messagePrefix + layoutTestController.layerTreeAsText();
         }
       
         window.addEventListener('load', testOnLoad, false);
diff --git a/Source/WebCore/ChangeLog b/Source/WebCore/ChangeLog
index 3302905..d71a309 100644
--- a/Source/WebCore/ChangeLog
+++ b/Source/WebCore/ChangeLog
@@ -1,3 +1,36 @@
+2011-01-17  Adam Roben  <aroben at apple.com>
+
+        Don't access the CACFLayerRef's sublayers directly from PlatformCALayer
+
+        There might be a secret extra sublayer (the tile parent layer) that
+        PlatformCALayer doesn't know about. When PlatformCALayer would
+        encounter this, it would try to use the tile parent layer's
+        PlatformCALayer wrapper, which was null, and then would crash. We now
+        ask PlatformCALayerWinInternal for the sublayer list, since that class
+        knows about the tile parent layer and can exclude it from the sublayer
+        list.
+
+        Covered by compositing/tiling/huge-layer-resize.html.
+
+        Fixes <http://webkit.org/b/52597> Crash beneath
+        PlatformCALayer::adoptSublayers when switching out of tiling mode
+        (null-dereference of a PlatformCALayer)
+
+        Reviewed by Darin Adler and Chris Marrin.
+
+        * platform/graphics/ca/win/PlatformCALayerWin.cpp:
+        (PlatformCALayer::adoptSublayers):
+        (printLayer):
+        Changed to use PlatformCALayerWinInternal::getSublayers.
+
+        * platform/graphics/ca/win/PlatformCALayerWinInternal.cpp:
+        (PlatformCALayerWinInternal::getSublayers): Added. Retrieves the list
+        of PlatformCALayers that represent our sublayers. Significantly, this
+        code knows about the tile parent layer and can thus exclude it.
+
+        * platform/graphics/ca/win/PlatformCALayerWinInternal.h: Added
+        getSublayers.
+
 2011-01-17  Naoki Takano  <takano.naoki at gmail.com>
 
         Reviewed by Kent Tamura.
diff --git a/Source/WebCore/platform/graphics/ca/win/PlatformCALayerWin.cpp b/Source/WebCore/platform/graphics/ca/win/PlatformCALayerWin.cpp
index 5e24cda..66d0732 100644
--- a/Source/WebCore/platform/graphics/ca/win/PlatformCALayerWin.cpp
+++ b/Source/WebCore/platform/graphics/ca/win/PlatformCALayerWin.cpp
@@ -253,15 +253,8 @@ size_t PlatformCALayer::sublayerCount() const
 
 void PlatformCALayer::adoptSublayers(PlatformCALayer* source)
 {
-    // Make a list of the sublayers from source
     PlatformCALayerList sublayers;
-    size_t n = source->sublayerCount();
-    CFArrayRef sourceSublayers = CACFLayerGetSublayers(source->platformLayer());
-
-    for (size_t i = 0; i < n; ++i) {
-        CACFLayerRef layer = static_cast<CACFLayerRef>(const_cast<void*>(CFArrayGetValueAtIndex(sourceSublayers, i)));
-        sublayers.append(platformCALayer(layer));
-    }
+    intern(source)->getSublayers(sublayers);
 
     // Use setSublayers() because it properly nulls out the superlayer pointers.
     setSublayers(sublayers);
@@ -690,11 +683,11 @@ static void printLayer(const PlatformCALayer* layer, int indent)
         printIndent(indent + 1);
         fprintf(stderr, "(sublayers\n");
 
-        CFArrayRef sublayers = CACFLayerGetSublayers(layer->platformLayer());
-        for (int i = 0; i < n; ++i) {
-            PlatformCALayer* sublayer = PlatformCALayer::platformCALayer(const_cast<void*>(CFArrayGetValueAtIndex(sublayers, i)));
-            printLayer(sublayer, indent + 2);
-        }
+        PlatformCALayerList sublayers;
+        intern(layer)->getSublayers(sublayers);
+        ASSERT(n == sublayers.size());
+        for (int i = 0; i < n; ++i)
+            printLayer(sublayers[i].get(), indent + 2);
 
         printIndent(indent + 1);
         fprintf(stderr, ")\n");
diff --git a/Source/WebCore/platform/graphics/ca/win/PlatformCALayerWinInternal.cpp b/Source/WebCore/platform/graphics/ca/win/PlatformCALayerWinInternal.cpp
index 0b7eea0..cdf90db 100644
--- a/Source/WebCore/platform/graphics/ca/win/PlatformCALayerWinInternal.cpp
+++ b/Source/WebCore/platform/graphics/ca/win/PlatformCALayerWinInternal.cpp
@@ -210,6 +210,27 @@ void PlatformCALayerWinInternal::setSublayers(const PlatformCALayerList& list)
     }
 }
 
+void PlatformCALayerWinInternal::getSublayers(PlatformCALayerList& list) const
+{
+    CFArrayRef sublayers = CACFLayerGetSublayers(owner()->platformLayer());
+    if (!sublayers) {
+        list.clear();
+        return;
+    }
+
+    size_t count = CFArrayGetCount(sublayers);
+
+    size_t layersToSkip = 0;
+    if (owner()->layerType() == PlatformCALayer::LayerTypeWebTiledLayer) {
+        // Exclude the tile parent layer.
+        layersToSkip = 1;
+    }
+
+    list.resize(count - layersToSkip);
+    for (size_t arrayIndex = layersToSkip; arrayIndex < count; ++arrayIndex)
+        list[arrayIndex - layersToSkip] = PlatformCALayer::platformCALayer(const_cast<void*>(CFArrayGetValueAtIndex(sublayers, arrayIndex)));
+}
+
 void PlatformCALayerWinInternal::removeAllSublayers()
 {
     CACFLayerSetSublayers(owner()->platformLayer(), 0);
diff --git a/Source/WebCore/platform/graphics/ca/win/PlatformCALayerWinInternal.h b/Source/WebCore/platform/graphics/ca/win/PlatformCALayerWinInternal.h
index 1be9d26..39ef3b3 100644
--- a/Source/WebCore/platform/graphics/ca/win/PlatformCALayerWinInternal.h
+++ b/Source/WebCore/platform/graphics/ca/win/PlatformCALayerWinInternal.h
@@ -52,6 +52,7 @@ public:
     PlatformCALayer* owner() const { return m_owner; }
 
     void setSublayers(const PlatformCALayerList&);
+    void getSublayers(PlatformCALayerList&) const;
     void removeAllSublayers();
     void insertSublayer(PlatformCALayer*, size_t);
     size_t sublayerCount() const;

-- 
WebKit Debian packaging



More information about the Pkg-webkit-commits mailing list