[SCM] WebKit Debian packaging branch, debian/experimental, updated. upstream/1.3.3-9427-gc2be6fc

ap at apple.com ap at apple.com
Wed Dec 22 15:42:45 UTC 2010


The following commit has been merged in the debian/experimental branch:
commit 1fe90891a7afa251130a67ed5818e9ce6a3757d8
Author: ap at apple.com <ap at apple.com@268f45cc-cd09-0410-ab3c-d52691b4dbfc>
Date:   Wed Nov 10 21:12:39 2010 +0000

            Reviewed by Darin Adler.
    
            https://bugs.webkit.org/show_bug.cgi?id=45205
            <rdar://problem/8391455> Detached elements shouldn't have style sheets.
    
            Tests: fast/dom/StyleSheet/detached-style-2.html
                   fast/dom/StyleSheet/detached-style-pi.xhtml
                   fast/dom/StyleSheet/detached-style.html
                   fast/dom/StyleSheet/detached-style-pi-2.xhtml
    
            * bindings/js/JSStyleSheetCustom.cpp: (WebCore::JSStyleSheet::markChildren):
            There is no longer a need to mark owner nodes - StyleSheet->ownerNode() is only non-null when
            the node is in document.
    
            * css/StyleSheet.cpp: (WebCore::StyleSheet::StyleSheet): Added an assertion checking that
            all nodes that can be StyleSheet parents have been verified.
    
            * css/StyleSheet.h: (WebCore::StyleSheet::clearOwnerNode): Added.
    
            * dom/ProcessingInstruction.cpp:
            (WebCore::ProcessingInstruction::~ProcessingInstruction): Clear stylesheet's owner node. This
            shouldn't have observable effect, since a processing instruction that is in document can only
            be destroyed with document, and a reachable stylsheet keeps document alive.
            (WebCore::ProcessingInstruction::removedFromDocument): Clear the relationship between node and style sheet when removed.
            (WebCore::ProcessingInstruction::setCSSStyleSheet): If the element was removed during load, we still
            don't want to create a style sheet.
    
            * dom/StyleElement.cpp:
            (WebCore::StyleElement::sheet): There is no reason for lazy creation. It was a wrong fix for
            bug 14462, whose regression test still passes.
            (WebCore::StyleElement::removedFromDocument): Clear the relationship between node and style sheet when removed.
            (WebCore::StyleElement::finishParsingChildren): Don't call sheet(), it doens't have side effects any more.
            (WebCore::StyleElement::createSheet): Assert that the element is in document. We never want
            to create a style sheet for an element that isn't.
    
            * dom/StyleElement.h: (WebCore::StyleElement::sheet): Made implementation inline, now that
            it's a simple getter.
    
            * html/HTMLLinkElement.cpp:
            (WebCore::HTMLLinkElement::~HTMLLinkElement): Clear stylesheet's owner node.
            (WebCore::HTMLLinkElement::process): Assert that there is no style sheet lingering for any reason.
            (WebCore::HTMLLinkElement::removedFromDocument): Clear the relationship between node and style sheet when removed.
            (WebCore::HTMLLinkElement::setCSSStyleSheet): If the element was removed during load, we still
            don't want to create a style sheet.
    
            * html/HTMLStyleElement.cpp: (WebCore::HTMLStyleElement::~HTMLStyleElement):
            * html/HTMLStyleElement.h:
            * svg/SVGStyleElement.cpp: (WebCore::SVGStyleElement::~SVGStyleElement):
            * svg/SVGStyleElement.h:
            Clear stylesheet's owner node. As above, this shouldn't have observable effect.
    
            * xml/XSLTProcessor.h:
            * xml/XSLTProcessor.cpp: (WebCore::XSLTProcessor::~XSLTProcessor):
            * dom/Document.cpp: (WebCore::Document::~Document):
            * css/CSSParser.cpp: (WebCore::CSSParser::parseSelector):
            Assert that stylesheet won't outlive its owner node. We don't really use refcounting here.
    
    
    
    git-svn-id: http://svn.webkit.org/repository/webkit/trunk@71767 268f45cc-cd09-0410-ab3c-d52691b4dbfc

diff --git a/LayoutTests/ChangeLog b/LayoutTests/ChangeLog
index 4c3d586..8fdc4e6 100644
--- a/LayoutTests/ChangeLog
+++ b/LayoutTests/ChangeLog
@@ -1,3 +1,26 @@
+2010-11-08  Alexey Proskuryakov  <ap at apple.com>
+
+        Reviewed by Darin Adler.
+
+        https://bugs.webkit.org/show_bug.cgi?id=45205
+        <rdar://problem/8391455> Detached elements shouldn't have style sheets.
+
+        * fast/dom/StyleSheet/ownerNode-lifetime-2-expected.txt: Removed.
+        * fast/dom/StyleSheet/ownerNode-lifetime-2.html: Removed.
+        * fast/dom/StyleSheet/ownerNode-lifetime-expected.txt: Removed.
+        * fast/dom/StyleSheet/ownerNode-lifetime.html: Removed.
+        These tests were wrong, and didn't pass in IE or Firefox. Owner node is undefined or null
+        respectedly in those browsers when detached.
+
+        * fast/dom/StyleSheet/detached-style-2-expected.txt: Added.
+        * fast/dom/StyleSheet/detached-style-2.html: Added.
+        * fast/dom/StyleSheet/detached-style-expected.txt: Added.
+        * fast/dom/StyleSheet/detached-style-pi-2-expected.txt: Added.
+        * fast/dom/StyleSheet/detached-style-pi-2.xhtml: Added.
+        * fast/dom/StyleSheet/detached-style-pi-expected.txt: Added.
+        * fast/dom/StyleSheet/detached-style-pi.xhtml: Added.
+        * fast/dom/StyleSheet/detached-style.html: Added.
+
 2010-11-10  Stephen White  <senorblanco at chromium.org>
 
         Unreviewed; updated test baselines.
diff --git a/LayoutTests/fast/dom/StyleSheet/detached-style-2-expected.txt b/LayoutTests/fast/dom/StyleSheet/detached-style-2-expected.txt
new file mode 100644
index 0000000..fb185d0
--- /dev/null
+++ b/LayoutTests/fast/dom/StyleSheet/detached-style-2-expected.txt
@@ -0,0 +1,5 @@
+Bug 45205: Test that <link> elements only have stylesheets when in document.
+
+Not in document: PASS
+After adding to document: PASS
+DONE
diff --git a/LayoutTests/fast/dom/StyleSheet/detached-style-2.html b/LayoutTests/fast/dom/StyleSheet/detached-style-2.html
new file mode 100644
index 0000000..273f62b
--- /dev/null
+++ b/LayoutTests/fast/dom/StyleSheet/detached-style-2.html
@@ -0,0 +1,31 @@
+<html>
+<head>
+<link rel="stylesheet" href="resources/detached-style.css" type="text/css" media="screen">
+</head>
+<body onload="finishTest()">
+<p><a href="https://bugs.webkit.org/show_bug.cgi?id=45205">Bug 45205</a>:
+Test that &lt;link> elements only have stylesheets when in document.</p>
+<pre id=result></pre>
+<script>
+if (window.layoutTestController)
+    layoutTestController.dumpAsText();
+
+head = document.getElementsByTagName("head")[0];
+link = document.getElementsByTagName("link")[0];
+result = document.getElementById("result");
+
+head.removeChild(link);
+
+function finishTest()
+{
+    result.innerHTML += "Not in document: " + ((link.sheet === null) ? "PASS" : ("FAIL: " + link.sheet)) + "\n";
+
+    head.appendChild(link);
+
+    result.innerHTML += "After adding to document: " + ((link.sheet === null) ? ("FAIL: " + link.sheet) : "PASS") + "\n";
+
+    result.innerHTML += "DONE";
+}
+</script>
+</body>
+</html>
diff --git a/LayoutTests/fast/dom/StyleSheet/detached-style-expected.txt b/LayoutTests/fast/dom/StyleSheet/detached-style-expected.txt
new file mode 100644
index 0000000..028aed1
--- /dev/null
+++ b/LayoutTests/fast/dom/StyleSheet/detached-style-expected.txt
@@ -0,0 +1,28 @@
+Bug 45205: Test that <link> elements only have stylesheets when in document.
+
+Testing <link>...
+PASS sheet.ownerNode is link
+PASS link.sheet === sheet is true
+Removing <link>...
+PASS link.sheet is null
+PASS sheet.ownerNode is null
+PASS sheet.cssRules[0].cssText[0] is "*"
+Re-adding <link>...
+PASS sheet.ownerNode is null
+PASS link.sheet === sheet is false
+PASS link.sheet.ownerNode is link
+Testing <style>...
+PASS sheet.ownerNode is style
+PASS style.sheet is sheet
+Removing <style>...
+PASS style.sheet is null
+PASS sheet.ownerNode is null
+PASS sheet.cssRules[0].cssText[0] is "*"
+Re-adding <style>...
+PASS sheet.ownerNode is null
+PASS style.sheet === sheet is false
+PASS style.sheet.ownerNode is style
+PASS successfullyParsed is true
+
+TEST COMPLETE
+
diff --git a/LayoutTests/fast/dom/StyleSheet/detached-style-pi-2-expected.txt b/LayoutTests/fast/dom/StyleSheet/detached-style-pi-2-expected.txt
new file mode 100644
index 0000000..15f00f1
--- /dev/null
+++ b/LayoutTests/fast/dom/StyleSheet/detached-style-pi-2-expected.txt
@@ -0,0 +1,5 @@
+Bug 45205: Test that <xml-stylesheet> processing instructions only have stylesheets when in document.
+
+Not in document: PASS
+After adding to document: PASS
+DONE
diff --git a/LayoutTests/fast/dom/StyleSheet/detached-style-pi-2.xhtml b/LayoutTests/fast/dom/StyleSheet/detached-style-pi-2.xhtml
new file mode 100644
index 0000000..b286349
--- /dev/null
+++ b/LayoutTests/fast/dom/StyleSheet/detached-style-pi-2.xhtml
@@ -0,0 +1,34 @@
+<?xml-stylesheet href="resources/detached-style.css" media="screen"?>
+<html xmlns="http://www.w3.org/1999/xhtml">
+<head>
+<title/>
+</head>
+<body onload="finishTest()">
+<p><a href="https://bugs.webkit.org/show_bug.cgi?id=45205">Bug 45205</a>:
+Test that &lt;xml-stylesheet> processing instructions only have stylesheets when in document.</p>
+<pre id="result"></pre>
+<script>
+if (window.layoutTestController)
+    layoutTestController.dumpAsText();
+
+sheet = document.styleSheets[0];
+pi = document.firstChild;
+result = document.getElementById("result");
+
+document.removeChild(pi);
+
+function finishTest()
+{
+    result.innerHTML += "Not in document: " + ((pi.sheet === null) ? "PASS" : ("FAIL: " + pi.sheet)) + "\n";
+
+    document.appendChild(pi);
+
+    // This subtest fails in Firefox 4.0b8 - apparently, adding a processing instruction doens't trigger load.
+    result.innerHTML += "After adding to document: " + ((pi.sheet === null) ? ("FAIL: " + pi.sheet) : "PASS") + "\n";
+
+    result.innerHTML += "DONE";
+}
+
+</script>
+</body>
+</html>
diff --git a/LayoutTests/fast/dom/StyleSheet/detached-style-pi-expected.txt b/LayoutTests/fast/dom/StyleSheet/detached-style-pi-expected.txt
new file mode 100644
index 0000000..9f0a46a
--- /dev/null
+++ b/LayoutTests/fast/dom/StyleSheet/detached-style-pi-expected.txt
@@ -0,0 +1,16 @@
+Bug 45205: Test that <xml-stylesheet> processing instructions only have stylesheets when in document.
+
+PASS sheet.ownerNode is pi
+PASS pi.sheet === sheet is true
+Removing <pi>...
+PASS pi.sheet is null
+PASS sheet.ownerNode is null
+PASS sheet.cssRules[0].cssText[0] is "*"
+Re-adding <pi>...
+PASS sheet.ownerNode is null
+PASS pi.sheet === sheet is false
+PASS pi.sheet.ownerNode is pi
+PASS successfullyParsed is true
+
+TEST COMPLETE
+
diff --git a/LayoutTests/fast/dom/StyleSheet/detached-style-pi.xhtml b/LayoutTests/fast/dom/StyleSheet/detached-style-pi.xhtml
new file mode 100644
index 0000000..b6ec096
--- /dev/null
+++ b/LayoutTests/fast/dom/StyleSheet/detached-style-pi.xhtml
@@ -0,0 +1,37 @@
+<?xml-stylesheet href="resources/detached-style.css" media="screen"?>
+<html xmlns="http://www.w3.org/1999/xhtml">
+<head>
+<title/>
+<link rel="stylesheet" href="../../js/resources/js-test-style.css"/>
+<script src="../../js/resources/js-test-pre.js"></script>
+</head>
+<body>
+<p><a href="https://bugs.webkit.org/show_bug.cgi?id=45205">Bug 45205</a>:
+Test that &lt;xml-stylesheet> processing instructions only have stylesheets when in document.</p>
+<div id="console"></div>
+<script>
+    sheet = document.styleSheets[0];
+    pi = document.firstChild;
+
+    shouldBe('sheet.ownerNode', 'pi')
+    shouldBe('pi.sheet === sheet', 'true')
+
+    debug("Removing &amp;lt;pi>...");
+    document.removeChild(pi);
+
+    shouldBe('pi.sheet', 'null')
+    shouldBe('sheet.ownerNode', 'null')
+    shouldBe('sheet.cssRules[0].cssText[0]', '"*"')
+
+    debug("Re-adding &amp;lt;pi>...");
+    document.insertBefore(pi, document.documentElement);
+    shouldBe('sheet.ownerNode', 'null')
+    shouldBe('pi.sheet === sheet', 'false')
+    shouldBe('pi.sheet.ownerNode', 'pi')
+
+    successfullyParsed = true;
+
+</script>
+<script src="../../js/resources/js-test-post.js"></script>
+</body>
+</html>
diff --git a/LayoutTests/fast/dom/StyleSheet/detached-style.html b/LayoutTests/fast/dom/StyleSheet/detached-style.html
new file mode 100644
index 0000000..6d5d7cb
--- /dev/null
+++ b/LayoutTests/fast/dom/StyleSheet/detached-style.html
@@ -0,0 +1,60 @@
+<html>
+<head>
+<link rel="stylesheet" href="resources/detached-style.css" type="text/css" media="screen">
+<link rel="stylesheet" href="../../js/resources/js-test-style.css">
+<style>* { }</style>
+<script src="../../js/resources/js-test-pre.js"></script>
+</head>
+<body>
+<p><a href="https://bugs.webkit.org/show_bug.cgi?id=45205">Bug 45205</a>:
+Test that &lt;link> elements only have stylesheets when in document.</p>
+<div id="console"></div>
+<script>
+    debug("Testing &lt;link>...");
+    sheet = document.styleSheets[0];
+    head = document.getElementsByTagName("head")[0];
+    link = document.getElementsByTagName("link")[0];
+
+    shouldBe('sheet.ownerNode', 'link')
+    shouldBe('link.sheet === sheet', 'true')
+
+    debug("Removing &lt;link>...");
+    head.removeChild(link);
+
+    shouldBe('link.sheet', 'null')
+    shouldBe('sheet.ownerNode', 'null')
+    shouldBe('sheet.cssRules[0].cssText[0]', '"*"')
+
+    debug("Re-adding &lt;link>...");
+    head.appendChild(link);
+    shouldBe('sheet.ownerNode', 'null')
+    shouldBe('link.sheet === sheet', 'false')
+    shouldBe('link.sheet.ownerNode', 'link')
+
+    debug("Testing &lt;style>...");
+    sheet = document.styleSheets[1];
+    head = document.getElementsByTagName("head")[0];
+    style = document.getElementsByTagName("style")[0];
+
+    shouldBe('sheet.ownerNode', 'style')
+    shouldBe('style.sheet', 'sheet')
+
+    debug("Removing &lt;style>...");
+    head.removeChild(style);
+
+    shouldBe('style.sheet', 'null')
+    shouldBe('sheet.ownerNode', 'null')
+    shouldBe('sheet.cssRules[0].cssText[0]', '"*"')
+
+    debug("Re-adding &lt;style>...");
+    head.appendChild(style);
+    shouldBe('sheet.ownerNode', 'null')
+    shouldBe('style.sheet === sheet', 'false')
+    shouldBe('style.sheet.ownerNode', 'style')
+
+    successfullyParsed = true;
+
+</script>
+<script src="../../js/resources/js-test-post.js"></script>
+</body>
+</html>
diff --git a/LayoutTests/fast/dom/StyleSheet/ownerNode-lifetime-2-expected.txt b/LayoutTests/fast/dom/StyleSheet/ownerNode-lifetime-2-expected.txt
deleted file mode 100644
index 5e51726..0000000
--- a/LayoutTests/fast/dom/StyleSheet/ownerNode-lifetime-2-expected.txt
+++ /dev/null
@@ -1,3 +0,0 @@
-This test verifies that style sheet do not outlive their elements. Since you can get back to the element with the ownerNode attribute, it's important to keep the element alive.
-
-Test passed.
diff --git a/LayoutTests/fast/dom/StyleSheet/ownerNode-lifetime-2.html b/LayoutTests/fast/dom/StyleSheet/ownerNode-lifetime-2.html
deleted file mode 100644
index ca6fa16..0000000
--- a/LayoutTests/fast/dom/StyleSheet/ownerNode-lifetime-2.html
+++ /dev/null
@@ -1,37 +0,0 @@
-<html>
-<link rel="stylesheet" type="text/css" href="theme.css"/>
-
-<script>
-function runTest() {
-  if (window.layoutTestController)
-    layoutTestController.dumpAsText();
-
-  var linkElement = document.getElementsByTagName('link')[0];
-  var styleSheet = linkElement.sheet;
-
-  // delete link element
-  linkElement.parentNode.removeChild(linkElement);
-  linkElement = null;
-  
-  if (window.gc) {
-    window.gc();
-  } else if (GCController) {
-      GCController.collect();
-  } else {
-    for (var i = 0; i < 10000; i++)
-      new Object();
-  } 
-  styleSheet.ownerNode.cloneNode();
-
-  document.getElementById("result").innerHTML = "Test passed.";
-}
-</script>
-<body onload="runTest()">
-<p>
-This test verifies that style sheet do not outlive their elements.
-Since you can get back to the element with the ownerNode attribute,
-it's important to keep the element alive.
-</p>
-<p id="result">TEST HAS NOT RUN YET.</p>
-</body>
-</html>
diff --git a/LayoutTests/fast/dom/StyleSheet/ownerNode-lifetime-expected.txt b/LayoutTests/fast/dom/StyleSheet/ownerNode-lifetime-expected.txt
deleted file mode 100644
index d92e2d7..0000000
--- a/LayoutTests/fast/dom/StyleSheet/ownerNode-lifetime-expected.txt
+++ /dev/null
@@ -1,3 +0,0 @@
-This test verifies that style sheets do not outlive their elements. Since you can get back to the element with the ownerNode attribute, it's important to keep the element alive.
-
-Test passed.
diff --git a/LayoutTests/fast/dom/StyleSheet/ownerNode-lifetime.html b/LayoutTests/fast/dom/StyleSheet/ownerNode-lifetime.html
deleted file mode 100644
index 54b1ac4..0000000
--- a/LayoutTests/fast/dom/StyleSheet/ownerNode-lifetime.html
+++ /dev/null
@@ -1,33 +0,0 @@
-<head>
-<script>
-function runTest()
-{
-    if (window.layoutTestController)
-        layoutTestController.dumpAsText();
-
-    var styleElement = document.createElement('style'); 
-    var styleSheet = styleElement.sheet; 
-    styleElement = null;
-
-    // create lots of objects to force a garbage collection
-    var i = 0;
-    var s;
-    while (i < 5000) {
-        i = i+1.11;
-        s = s + " ";
-    }
-
-    styleSheet.ownerNode.cloneNode();
-
-    document.getElementById("result").innerHTML = "Test passed.";
-}
-</script>
-</head>
-<body onload="runTest()">
-<p>
-This test verifies that style sheets do not outlive their elements.
-Since you can get back to the element with the ownerNode attribute,
-it's important to keep the element alive.
-</p>
-<p id="result">TEST HAS NOT RUN YET.</p>
-</body>
diff --git a/WebCore/ChangeLog b/WebCore/ChangeLog
index 2ee6e93..c659904 100644
--- a/WebCore/ChangeLog
+++ b/WebCore/ChangeLog
@@ -1,3 +1,62 @@
+2010-11-08  Alexey Proskuryakov  <ap at apple.com>
+
+        Reviewed by Darin Adler.
+
+        https://bugs.webkit.org/show_bug.cgi?id=45205
+        <rdar://problem/8391455> Detached elements shouldn't have style sheets.
+
+        Tests: fast/dom/StyleSheet/detached-style-2.html
+               fast/dom/StyleSheet/detached-style-pi.xhtml
+               fast/dom/StyleSheet/detached-style.html
+               fast/dom/StyleSheet/detached-style-pi-2.xhtml
+
+        * bindings/js/JSStyleSheetCustom.cpp: (WebCore::JSStyleSheet::markChildren):
+        There is no longer a need to mark owner nodes - StyleSheet->ownerNode() is only non-null when
+        the node is in document.
+
+        * css/StyleSheet.cpp: (WebCore::StyleSheet::StyleSheet): Added an assertion checking that
+        all nodes that can be StyleSheet parents have been verified.
+
+        * css/StyleSheet.h: (WebCore::StyleSheet::clearOwnerNode): Added.
+
+        * dom/ProcessingInstruction.cpp:
+        (WebCore::ProcessingInstruction::~ProcessingInstruction): Clear stylesheet's owner node. This
+        shouldn't have observable effect, since a processing instruction that is in document can only
+        be destroyed with document, and a reachable stylsheet keeps document alive.
+        (WebCore::ProcessingInstruction::removedFromDocument): Clear the relationship between node and style sheet when removed.
+        (WebCore::ProcessingInstruction::setCSSStyleSheet): If the element was removed during load, we still
+        don't want to create a style sheet.
+
+        * dom/StyleElement.cpp:
+        (WebCore::StyleElement::sheet): There is no reason for lazy creation. It was a wrong fix for
+        bug 14462, whose regression test still passes.
+        (WebCore::StyleElement::removedFromDocument): Clear the relationship between node and style sheet when removed.
+        (WebCore::StyleElement::finishParsingChildren): Don't call sheet(), it doens't have side effects any more.
+        (WebCore::StyleElement::createSheet): Assert that the element is in document. We never want
+        to create a style sheet for an element that isn't.
+
+        * dom/StyleElement.h: (WebCore::StyleElement::sheet): Made implementation inline, now that
+        it's a simple getter.
+
+        * html/HTMLLinkElement.cpp:
+        (WebCore::HTMLLinkElement::~HTMLLinkElement): Clear stylesheet's owner node.
+        (WebCore::HTMLLinkElement::process): Assert that there is no style sheet lingering for any reason.
+        (WebCore::HTMLLinkElement::removedFromDocument): Clear the relationship between node and style sheet when removed.
+        (WebCore::HTMLLinkElement::setCSSStyleSheet): If the element was removed during load, we still
+        don't want to create a style sheet.
+
+        * html/HTMLStyleElement.cpp: (WebCore::HTMLStyleElement::~HTMLStyleElement):
+        * html/HTMLStyleElement.h:
+        * svg/SVGStyleElement.cpp: (WebCore::SVGStyleElement::~SVGStyleElement):
+        * svg/SVGStyleElement.h:
+        Clear stylesheet's owner node. As above, this shouldn't have observable effect.
+
+        * xml/XSLTProcessor.h:
+        * xml/XSLTProcessor.cpp: (WebCore::XSLTProcessor::~XSLTProcessor):
+        * dom/Document.cpp: (WebCore::Document::~Document):
+        * css/CSSParser.cpp: (WebCore::CSSParser::parseSelector):
+        Assert that stylesheet won't outlive its owner node. We don't really use refcounting here.
+
 2010-11-10  Dan Bernstein  <mitz at apple.com>
 
         Reviewed by Dave Hyatt.
diff --git a/WebCore/bindings/js/JSStyleSheetCustom.cpp b/WebCore/bindings/js/JSStyleSheetCustom.cpp
index ecfc6a6..04c6561 100644
--- a/WebCore/bindings/js/JSStyleSheetCustom.cpp
+++ b/WebCore/bindings/js/JSStyleSheetCustom.cpp
@@ -62,14 +62,6 @@ void JSStyleSheet::markChildren(MarkStack& markStack)
     unsigned length = sheet->length();
     for (unsigned i = 0; i < length; ++i)
         markDOMObjectWrapper(markStack, globalData, sheet->item(i));
-
-    // This prevents us from having a style sheet with a dangling ownerNode pointer.
-    // A better solution would be to handle this on the DOM side -- if the style sheet
-    // is kept around, then we want the node to stay around too. One possibility would
-    // be to make ref/deref on the style sheet ref/deref the node instead, but there's
-    // a lot of disentangling of the CSS DOM objects that would need to happen first.
-    if (Node* ownerNode = sheet->ownerNode())
-        markDOMNodeWrapper(markStack, ownerNode->document(), ownerNode);
 }
 
 } // namespace WebCore
diff --git a/WebCore/css/CSSParser.cpp b/WebCore/css/CSSParser.cpp
index b1b76cf..8b5b520 100644
--- a/WebCore/css/CSSParser.cpp
+++ b/WebCore/css/CSSParser.cpp
@@ -332,6 +332,9 @@ void CSSParser::parseSelector(const String& string, Document* doc, CSSSelectorLi
     cssyyparse(this);
 
     m_selectorListForParseSelector = 0;
+
+    // The style sheet will be deleted right away, so it won't outlive the document.
+    ASSERT(dummyStyleSheet->hasOneRef());
 }
 
 bool CSSParser::parseDeclaration(CSSMutableStyleDeclaration* declaration, const String& string, RefPtr<CSSStyleSourceData>* styleSourceData)
diff --git a/WebCore/css/StyleSheet.cpp b/WebCore/css/StyleSheet.cpp
index 4f20a20..7cc1f4b 100644
--- a/WebCore/css/StyleSheet.cpp
+++ b/WebCore/css/StyleSheet.cpp
@@ -20,10 +20,27 @@
 #include "config.h"
 #include "StyleSheet.h"
 
+#include "HTMLNames.h"
 #include "MediaList.h"
+#include "Node.h"
+#include "SVGNames.h"
 
 namespace WebCore {
 
+static bool isAcceptableStyleSheetParent(Node* parentNode)
+{
+    // Only these nodes can be parents of StyleSheets, and they need to call clearOwnerNode() when moved out of document.
+    return !parentNode
+        || parentNode->isDocumentNode()
+        || parentNode->hasTagName(HTMLNames::linkTag)
+        || parentNode->hasTagName(HTMLNames::styleTag)
+        || parentNode->nodeType() == Node::PROCESSING_INSTRUCTION_NODE
+#if ENABLE(SVG)
+        || parentNode->hasTagName(SVGNames::styleTag)
+#endif    
+    ;
+}
+
 StyleSheet::StyleSheet(StyleSheet* parentSheet, const String& originalURL, const KURL& finalURL)
     : StyleList(parentSheet)
     , m_parentNode(0)
@@ -40,6 +57,7 @@ StyleSheet::StyleSheet(Node* parentNode, const String& originalURL, const KURL&
     , m_finalURL(finalURL)
     , m_disabled(false)
 {
+    ASSERT(isAcceptableStyleSheetParent(parentNode));
 }
 
 StyleSheet::StyleSheet(StyleBase* owner, const String& originalURL, const KURL& finalURL)
diff --git a/WebCore/css/StyleSheet.h b/WebCore/css/StyleSheet.h
index 621733d..2ff9a01 100644
--- a/WebCore/css/StyleSheet.h
+++ b/WebCore/css/StyleSheet.h
@@ -40,6 +40,7 @@ public:
     void setDisabled(bool disabled) { m_disabled = disabled; styleSheetChanged(); }
 
     Node* ownerNode() const { return m_parentNode; }
+    void clearOwnerNode() { m_parentNode = 0; }
     StyleSheet *parentStyleSheet() const;
 
     // Note that href is the URL that started the redirect chain that led to
diff --git a/WebCore/dom/Document.cpp b/WebCore/dom/Document.cpp
index 9263525..7f77b3e 100644
--- a/WebCore/dom/Document.cpp
+++ b/WebCore/dom/Document.cpp
@@ -575,6 +575,17 @@ Document::~Document()
     if (m_styleSheets)
         m_styleSheets->documentDestroyed();
 
+    if (m_elemSheet)
+        m_elemSheet->clearOwnerNode();
+    if (m_mappedElementSheet)
+        m_mappedElementSheet->clearOwnerNode();
+    if (m_pageUserSheet)
+        m_pageUserSheet->clearOwnerNode();
+    if (m_pageGroupUserSheets) {
+        for (size_t i = 0; i < m_pageGroupUserSheets->size(); ++i)
+            (*m_pageGroupUserSheets)[i]->clearOwnerNode();
+    }
+
     m_weakReference->clear();
 }
 
diff --git a/WebCore/dom/ProcessingInstruction.cpp b/WebCore/dom/ProcessingInstruction.cpp
index 0b4410d..4939c8d 100644
--- a/WebCore/dom/ProcessingInstruction.cpp
+++ b/WebCore/dom/ProcessingInstruction.cpp
@@ -56,6 +56,9 @@ PassRefPtr<ProcessingInstruction> ProcessingInstruction::create(Document* docume
 
 ProcessingInstruction::~ProcessingInstruction()
 {
+    if (m_sheet)
+        m_sheet->clearOwnerNode();
+
     if (m_cachedSheet)
         m_cachedSheet->removeClient(this);
 }
@@ -200,6 +203,11 @@ bool ProcessingInstruction::sheetLoaded()
 
 void ProcessingInstruction::setCSSStyleSheet(const String& href, const KURL& baseURL, const String& charset, const CachedCSSStyleSheet* sheet)
 {
+    if (!inDocument()) {
+        ASSERT(!m_sheet);
+        return;
+    }
+
 #if ENABLE(XSLT)
     ASSERT(!m_isXSL);
 #endif
@@ -274,6 +282,12 @@ void ProcessingInstruction::removedFromDocument()
 
     document()->removeStyleSheetCandidateNode(this);
 
+    if (m_sheet) {
+        ASSERT(m_sheet->ownerNode() == this);
+        m_sheet->clearOwnerNode();
+        m_sheet = 0;
+    }
+
     if (m_cachedSheet)
         document()->styleSelectorChanged(DeferRecalcStyle);
 }
diff --git a/WebCore/dom/StyleElement.cpp b/WebCore/dom/StyleElement.cpp
index f318326..157e8f9 100644
--- a/WebCore/dom/StyleElement.cpp
+++ b/WebCore/dom/StyleElement.cpp
@@ -43,13 +43,6 @@ StyleElement::~StyleElement()
 {
 }
 
-StyleSheet* StyleElement::sheet(Element* e)
-{
-    if (!m_sheet)
-        createSheet(e, 0);
-    return m_sheet.get();
-}
-
 void StyleElement::insertedIntoDocument(Document* document, Element* element)
 {
     ASSERT(document);
@@ -67,11 +60,14 @@ void StyleElement::removedFromDocument(Document* document, Element* element)
     ASSERT(element);
     document->removeStyleSheetCandidateNode(element);
 
-    // If we're in document teardown, then we don't need to do any notification of our sheet's removal.
-    if (!document->renderer())
-        return;
+    if (m_sheet) {
+        ASSERT(m_sheet->ownerNode() == element);
+        m_sheet->clearOwnerNode();
+        m_sheet = 0;
+    }
 
-    if (m_sheet)
+    // If we're in document teardown, then we don't need to do any notification of our sheet's removal.
+    if (document->renderer())
         document->styleSelectorChanged(DeferRecalcStyle);
 }
 
@@ -88,7 +84,6 @@ void StyleElement::finishParsingChildren(Element* element)
 {
     ASSERT(element);
     process(element);
-    sheet(element);
     m_createdByParser = false;
 }
 
@@ -124,6 +119,7 @@ void StyleElement::process(Element* e)
 void StyleElement::createSheet(Element* e, int startLineNumber, const String& text)
 {
     ASSERT(e);
+    ASSERT(e->inDocument());
     Document* document = e->document();
     if (m_sheet) {
         if (m_sheet->isLoading())
diff --git a/WebCore/dom/StyleElement.h b/WebCore/dom/StyleElement.h
index 65f6310..05c07c5 100644
--- a/WebCore/dom/StyleElement.h
+++ b/WebCore/dom/StyleElement.h
@@ -37,7 +37,7 @@ protected:
     virtual const AtomicString& type() const = 0;
     virtual const AtomicString& media() const = 0;
 
-    StyleSheet* sheet(Element*);
+    StyleSheet* sheet() { return m_sheet.get(); }
 
     bool isLoading() const;
     bool sheetLoaded(Document*);
diff --git a/WebCore/html/HTMLLinkElement.cpp b/WebCore/html/HTMLLinkElement.cpp
index 033206d..8dd055c 100644
--- a/WebCore/html/HTMLLinkElement.cpp
+++ b/WebCore/html/HTMLLinkElement.cpp
@@ -62,6 +62,9 @@ PassRefPtr<HTMLLinkElement> HTMLLinkElement::create(const QualifiedName& tagName
 
 HTMLLinkElement::~HTMLLinkElement()
 {
+    if (m_sheet)
+        m_sheet->clearOwnerNode();
+
     if (m_cachedSheet) {
         m_cachedSheet->removeClient(this);
         if (m_loading && !isDisabled() && !isAlternate())
@@ -179,8 +182,10 @@ void HTMLLinkElement::tokenizeRelAttribute(const AtomicString& rel, RelAttribute
 
 void HTMLLinkElement::process()
 {
-    if (!inDocument())
+    if (!inDocument()) {
+        ASSERT(!m_sheet);
         return;
+    }
 
     String type = m_type.lower();
 
@@ -261,6 +266,12 @@ void HTMLLinkElement::removedFromDocument()
 
     document()->removeStyleSheetCandidateNode(this);
 
+    if (m_sheet) {
+        ASSERT(m_sheet->ownerNode() == this);
+        m_sheet->clearOwnerNode();
+        m_sheet = 0;
+    }
+
     if (document()->renderer())
         document()->styleSelectorChanged(DeferRecalcStyle);
 }
@@ -273,6 +284,11 @@ void HTMLLinkElement::finishParsingChildren()
 
 void HTMLLinkElement::setCSSStyleSheet(const String& href, const KURL& baseURL, const String& charset, const CachedCSSStyleSheet* sheet)
 {
+    if (!inDocument()) {
+        ASSERT(!m_sheet);
+        return;
+    }
+
     m_sheet = CSSStyleSheet::create(this, href, baseURL, charset);
 
     bool strictParsing = !document()->inQuirksMode();
diff --git a/WebCore/html/HTMLStyleElement.cpp b/WebCore/html/HTMLStyleElement.cpp
index 1066c75..7c2512b 100644
--- a/WebCore/html/HTMLStyleElement.cpp
+++ b/WebCore/html/HTMLStyleElement.cpp
@@ -41,6 +41,12 @@ inline HTMLStyleElement::HTMLStyleElement(const QualifiedName& tagName, Document
     ASSERT(hasTagName(styleTag));
 }
 
+HTMLStyleElement::~HTMLStyleElement()
+{
+    if (m_sheet)
+        m_sheet->clearOwnerNode();
+}
+
 PassRefPtr<HTMLStyleElement> HTMLStyleElement::create(const QualifiedName& tagName, Document* document, bool createdByParser)
 {
     return adoptRef(new HTMLStyleElement(tagName, document, createdByParser));
@@ -80,11 +86,6 @@ void HTMLStyleElement::childrenChanged(bool changedByParser, Node* beforeChange,
     HTMLElement::childrenChanged(changedByParser, beforeChange, afterChange, childCountDelta);
 }
 
-StyleSheet* HTMLStyleElement::sheet()
-{
-    return StyleElement::sheet(this);
-}
-
 const AtomicString& HTMLStyleElement::media() const
 {
     return getAttribute(mediaAttr);
diff --git a/WebCore/html/HTMLStyleElement.h b/WebCore/html/HTMLStyleElement.h
index b4013b8..3d6958f 100644
--- a/WebCore/html/HTMLStyleElement.h
+++ b/WebCore/html/HTMLStyleElement.h
@@ -33,10 +33,11 @@ class StyleSheet;
 class HTMLStyleElement : public HTMLElement, private StyleElement {
 public:
     static PassRefPtr<HTMLStyleElement> create(const QualifiedName&, Document*, bool createdByParser);
+    virtual ~HTMLStyleElement();
 
     void setType(const AtomicString&);
 
-    StyleSheet* sheet();
+    using StyleElement::sheet;
 
 private:
     HTMLStyleElement(const QualifiedName&, Document*, bool createdByParser);
diff --git a/WebCore/svg/SVGStyleElement.cpp b/WebCore/svg/SVGStyleElement.cpp
index 4a80319..042af1c 100644
--- a/WebCore/svg/SVGStyleElement.cpp
+++ b/WebCore/svg/SVGStyleElement.cpp
@@ -40,6 +40,12 @@ inline SVGStyleElement::SVGStyleElement(const QualifiedName& tagName, Document*
 {
 }
 
+SVGStyleElement::~SVGStyleElement()
+{
+    if (m_sheet)
+        m_sheet->clearOwnerNode();
+}
+
 PassRefPtr<SVGStyleElement> SVGStyleElement::create(const QualifiedName& tagName, Document* document, bool createdByParser)
 {
     return adoptRef(new SVGStyleElement(tagName, document, createdByParser));
@@ -114,11 +120,6 @@ void SVGStyleElement::childrenChanged(bool changedByParser, Node* beforeChange,
     SVGElement::childrenChanged(changedByParser, beforeChange, afterChange, childCountDelta);
 }
 
-StyleSheet* SVGStyleElement::sheet()
-{
-    return StyleElement::sheet(this);
-}
-
 }
 
 #endif // ENABLE(SVG)
diff --git a/WebCore/svg/SVGStyleElement.h b/WebCore/svg/SVGStyleElement.h
index bb46549..acf358e 100644
--- a/WebCore/svg/SVGStyleElement.h
+++ b/WebCore/svg/SVGStyleElement.h
@@ -33,8 +33,9 @@ class SVGStyleElement : public SVGElement
                       , public StyleElement {
 public:
     static PassRefPtr<SVGStyleElement> create(const QualifiedName&, Document*, bool createdByParser);
+    virtual ~SVGStyleElement();
 
-    StyleSheet* sheet();
+    using StyleElement::sheet;
 
     virtual const AtomicString& type() const;
     void setType(const AtomicString&, ExceptionCode&);
diff --git a/WebCore/xml/XSLTProcessor.cpp b/WebCore/xml/XSLTProcessor.cpp
index 5fd009c..59afd73 100644
--- a/WebCore/xml/XSLTProcessor.cpp
+++ b/WebCore/xml/XSLTProcessor.cpp
@@ -60,6 +60,12 @@ static inline void transformTextStringToXHTMLDocumentString(String& text)
         "</html>\n";
 }
 
+XSLTProcessor::~XSLTProcessor()
+{
+    // Stylesheet shouldn't outlive its root node.
+    ASSERT(!m_stylesheetRootNode || !m_stylesheet || m_stylesheet->hasOneRef());
+}
+
 PassRefPtr<Document> XSLTProcessor::createDocumentFromSource(const String& sourceString,
     const String& sourceEncoding, const String& sourceMIMEType, Node* sourceNode, Frame* frame)
 {
diff --git a/WebCore/xml/XSLTProcessor.h b/WebCore/xml/XSLTProcessor.h
index 5be6b17..451e12c 100644
--- a/WebCore/xml/XSLTProcessor.h
+++ b/WebCore/xml/XSLTProcessor.h
@@ -44,6 +44,7 @@ class DocumentFragment;
 class XSLTProcessor : public RefCounted<XSLTProcessor> {
 public:
     static PassRefPtr<XSLTProcessor> create() { return adoptRef(new XSLTProcessor); }
+    ~XSLTProcessor();
 
     void setXSLStyleSheet(PassRefPtr<XSLStyleSheet> styleSheet) { m_stylesheet = styleSheet; }
     bool transformToString(Node* source, String& resultMIMEType, String& resultString, String& resultEncoding);

-- 
WebKit Debian packaging



More information about the Pkg-webkit-commits mailing list