Title: [104259] trunk/Source/WebCore
Revision
104259
Author
[email protected]
Date
2012-01-05 17:58:34 -0800 (Thu, 05 Jan 2012)

Log Message

[Refactoring] Moving between TreeScopes should be done by its own class.
https://bugs.webkit.org/show_bug.cgi?id=75290

Reviewed by Ryosuke Niwa.

This change extracted Node::setTreeScopeRecursively(),
setDocumentRecursively() and a part of setDocument() into a new
class called TreeScopeAdopter. By doing this, the idea of
moving a node from scope to scope, that was originally hidden
behind the forest of Node APIs, has become clearer.

Note that this change is a preparation for Bug 59816.

No new tests. No behavioral change.

* CMakeLists.txt:
* GNUmakefile.list.am:
* Target.pri:
* WebCore.gypi:
* WebCore.vcproj/WebCore.vcproj:
* WebCore.xcodeproj/project.pbxproj:
* dom/ContainerNode.cpp: Followed the renaming.
(WebCore::ContainerNode::takeAllChildrenFrom):
(WebCore::ContainerNode::insertBefore):
(WebCore::ContainerNode::replaceChild):
(WebCore::ContainerNode::removeBetween):
(WebCore::ContainerNode::removeChildren):
(WebCore::ContainerNode::appendChild):
(WebCore::ContainerNode::parserAddChild):
* dom/DOMAllInOne.cpp:
* dom/Document.cpp: Followed te renaming.
(WebCore::Document::setDocType):
(WebCore::Document::adoptNode):
* dom/Element.cpp: Followed te renaming.
(WebCore::Element::removeShadowRoot):
* dom/Node.cpp:
(WebCore::Node::setDocument):
(WebCore::Node::setTreeScope):
(WebCore::Node::didMoveToNewDocument):
* dom/Node.h:
* dom/TreeScope.h:
* dom/TreeScope.cpp:
(WebCore::TreeScope::adoptIfNeeded): moved from setTreeScopeRecursively()
* dom/TreeScopeAdopter.cpp: Added.
(WebCore::TreeScopeAdopter::TreeScopeAdopter):
(WebCore::TreeScopeAdopter::moveTreeToNewScope):
(WebCore::TreeScopeAdopter::moveTreeToNewDocument):
(WebCore::TreeScopeAdopter::ensureDidMoveToNewDocumentWasCalled):
(WebCore::TreeScopeAdopter::moveNodeToNewDocument):
* dom/TreeScopeAdopter.h: Added.
(WebCore::TreeScopeAdopter::ensureDidMoveToNewDocumentWasCalled):
(WebCore::TreeScopeAdopter::execute):
(WebCore::TreeScopeAdopter::needsScopeChange()):
(WebCore::TreeScopeAdopter::shadowRootFor):

Modified Paths

Added Paths

Property Changed

Diff

Modified: trunk/Source/WebCore/CMakeLists.txt (104258 => 104259)


--- trunk/Source/WebCore/CMakeLists.txt	2012-01-06 01:37:39 UTC (rev 104258)
+++ trunk/Source/WebCore/CMakeLists.txt	2012-01-06 01:58:34 UTC (rev 104259)
@@ -610,6 +610,7 @@
     dom/TransformSourceLibxslt.cpp
     dom/Traversal.cpp
     dom/TreeScope.cpp
+    dom/TreeScopeAdopter.cpp
     dom/TreeWalker.cpp
     dom/UIEvent.cpp
     dom/UIEventWithKeyState.cpp

Modified: trunk/Source/WebCore/ChangeLog (104258 => 104259)


--- trunk/Source/WebCore/ChangeLog	2012-01-06 01:37:39 UTC (rev 104258)
+++ trunk/Source/WebCore/ChangeLog	2012-01-06 01:58:34 UTC (rev 104259)
@@ -1,3 +1,60 @@
+2012-01-04  Hajime Morrita  <[email protected]>
+
+        [Refactoring] Moving between TreeScopes should be done by its own class.
+        https://bugs.webkit.org/show_bug.cgi?id=75290
+
+        Reviewed by Ryosuke Niwa.
+
+        This change extracted Node::setTreeScopeRecursively(),
+        setDocumentRecursively() and a part of setDocument() into a new
+        class called TreeScopeAdopter. By doing this, the idea of
+        moving a node from scope to scope, that was originally hidden
+        behind the forest of Node APIs, has become clearer.
+
+        Note that this change is a preparation for Bug 59816.
+
+        No new tests. No behavioral change.
+
+        * CMakeLists.txt:
+        * GNUmakefile.list.am:
+        * Target.pri:
+        * WebCore.gypi:
+        * WebCore.vcproj/WebCore.vcproj:
+        * WebCore.xcodeproj/project.pbxproj:
+        * dom/ContainerNode.cpp: Followed the renaming.
+        (WebCore::ContainerNode::takeAllChildrenFrom):
+        (WebCore::ContainerNode::insertBefore):
+        (WebCore::ContainerNode::replaceChild):
+        (WebCore::ContainerNode::removeBetween):
+        (WebCore::ContainerNode::removeChildren):
+        (WebCore::ContainerNode::appendChild):
+        (WebCore::ContainerNode::parserAddChild):
+        * dom/DOMAllInOne.cpp:
+        * dom/Document.cpp: Followed te renaming.
+        (WebCore::Document::setDocType):
+        (WebCore::Document::adoptNode):
+        * dom/Element.cpp: Followed te renaming.
+        (WebCore::Element::removeShadowRoot):
+        * dom/Node.cpp:
+        (WebCore::Node::setDocument):
+        (WebCore::Node::setTreeScope):
+        (WebCore::Node::didMoveToNewDocument):
+        * dom/Node.h:
+        * dom/TreeScope.h:
+        * dom/TreeScope.cpp:
+        (WebCore::TreeScope::adoptIfNeeded): moved from setTreeScopeRecursively()
+        * dom/TreeScopeAdopter.cpp: Added.
+        (WebCore::TreeScopeAdopter::TreeScopeAdopter):
+        (WebCore::TreeScopeAdopter::moveTreeToNewScope):
+        (WebCore::TreeScopeAdopter::moveTreeToNewDocument):
+        (WebCore::TreeScopeAdopter::ensureDidMoveToNewDocumentWasCalled):
+        (WebCore::TreeScopeAdopter::moveNodeToNewDocument):
+        * dom/TreeScopeAdopter.h: Added.
+        (WebCore::TreeScopeAdopter::ensureDidMoveToNewDocumentWasCalled):
+        (WebCore::TreeScopeAdopter::execute):
+        (WebCore::TreeScopeAdopter::needsScopeChange()):
+        (WebCore::TreeScopeAdopter::shadowRootFor):
+
 2012-01-05  Jochen Eisinger  <[email protected]>
 
         Disallow access to DOM storage from detached frames.
Property changes on: trunk/Source/WebCore/ChangeLog
___________________________________________________________________

Deleted: svn:executable

Modified: trunk/Source/WebCore/GNUmakefile.list.am (104258 => 104259)


--- trunk/Source/WebCore/GNUmakefile.list.am	2012-01-06 01:37:39 UTC (rev 104258)
+++ trunk/Source/WebCore/GNUmakefile.list.am	2012-01-06 01:58:34 UTC (rev 104259)
@@ -1674,6 +1674,8 @@
 	Source/WebCore/dom/TreeDepthLimit.h \
 	Source/WebCore/dom/TreeScope.cpp \
 	Source/WebCore/dom/TreeScope.h \
+	Source/WebCore/dom/TreeScopeAdopter.cpp \
+	Source/WebCore/dom/TreeScopeAdopter.h \
 	Source/WebCore/dom/TreeWalker.cpp \
 	Source/WebCore/dom/TreeWalker.h \
 	Source/WebCore/dom/UIEvent.cpp \

Modified: trunk/Source/WebCore/Target.pri (104258 => 104259)


--- trunk/Source/WebCore/Target.pri	2012-01-06 01:37:39 UTC (rev 104258)
+++ trunk/Source/WebCore/Target.pri	2012-01-06 01:58:34 UTC (rev 104259)
@@ -574,6 +574,7 @@
     dom/TouchList.cpp \
     dom/Traversal.cpp \
     dom/TreeScope.cpp \
+    dom/TreeScopeAdopter.cpp \
     dom/TreeWalker.cpp \
     dom/UIEvent.cpp \
     dom/UIEventWithKeyState.cpp \
@@ -1670,6 +1671,7 @@
     dom/Traversal.h \
     dom/TreeDepthLimit.h \
     dom/TreeScope.h \
+    dom/TreeScopeAdopter.h \
     dom/TreeWalker.h \
     dom/UIEvent.h \
     dom/UIEventWithKeyState.h \

Modified: trunk/Source/WebCore/WebCore.gypi (104258 => 104259)


--- trunk/Source/WebCore/WebCore.gypi	2012-01-06 01:37:39 UTC (rev 104258)
+++ trunk/Source/WebCore/WebCore.gypi	2012-01-06 01:58:34 UTC (rev 104259)
@@ -5465,6 +5465,8 @@
             'dom/TreeDepthLimit.h',
             'dom/TreeScope.cpp',
             'dom/TreeScope.h',
+            'dom/TreeScopeAdopter.cpp',
+            'dom/TreeScopeAdopter.h',
             'dom/TreeWalker.cpp',
             'dom/TreeWalker.h',
             'dom/UIEvent.cpp',

Modified: trunk/Source/WebCore/WebCore.vcproj/WebCore.vcproj (104258 => 104259)


--- trunk/Source/WebCore/WebCore.vcproj/WebCore.vcproj	2012-01-06 01:37:39 UTC (rev 104258)
+++ trunk/Source/WebCore/WebCore.vcproj/WebCore.vcproj	2012-01-06 01:58:34 UTC (rev 104259)
@@ -51774,6 +51774,62 @@
 				>
 			</File>
 			<File
+				RelativePath="..\dom\TreeScopeAdopter.cpp"
+				>
+				<FileConfiguration
+					Name="Debug|Win32"
+					ExcludedFromBuild="true"
+					>
+					<Tool
+						Name="VCCLCompilerTool"
+					/>
+				</FileConfiguration>
+				<FileConfiguration
+					Name="Release|Win32"
+					ExcludedFromBuild="true"
+					>
+					<Tool
+						Name="VCCLCompilerTool"
+					/>
+				</FileConfiguration>
+				<FileConfiguration
+					Name="Debug_Cairo_CFLite|Win32"
+					ExcludedFromBuild="true"
+					>
+					<Tool
+						Name="VCCLCompilerTool"
+					/>
+				</FileConfiguration>
+				<FileConfiguration
+					Name="Release_Cairo_CFLite|Win32"
+					ExcludedFromBuild="true"
+					>
+					<Tool
+						Name="VCCLCompilerTool"
+					/>
+				</FileConfiguration>
+				<FileConfiguration
+					Name="Debug_All|Win32"
+					ExcludedFromBuild="true"
+					>
+					<Tool
+						Name="VCCLCompilerTool"
+					/>
+				</FileConfiguration>
+				<FileConfiguration
+					Name="Production|Win32"
+					ExcludedFromBuild="true"
+					>
+					<Tool
+						Name="VCCLCompilerTool"
+					/>
+				</FileConfiguration>
+			</File>
+			<File
+				RelativePath="..\dom\TreeScopeAdopter.h"
+				>
+			</File>
+			<File
 				RelativePath="..\dom\TreeWalker.cpp"
 				>
 				<FileConfiguration

Modified: trunk/Source/WebCore/WebCore.xcodeproj/project.pbxproj (104258 => 104259)


--- trunk/Source/WebCore/WebCore.xcodeproj/project.pbxproj	2012-01-06 01:37:39 UTC (rev 104258)
+++ trunk/Source/WebCore/WebCore.xcodeproj/project.pbxproj	2012-01-06 01:58:34 UTC (rev 104259)
@@ -3507,6 +3507,8 @@
 		A77979290D6B9E64003851B9 /* JSImageData.h in Headers */ = {isa = PBXBuildFile; fileRef = A77979250D6B9E64003851B9 /* JSImageData.h */; };
 		A77B41A012E675A90054343D /* TextEventInputType.h in Headers */ = {isa = PBXBuildFile; fileRef = A77B419F12E675A90054343D /* TextEventInputType.h */; settings = {ATTRIBUTES = (Private, ); }; };
 		A77D0012133B0AEB00D6658C /* TextChecking.h in Headers */ = {isa = PBXBuildFile; fileRef = A77D0011133B0AEB00D6658C /* TextChecking.h */; settings = {ATTRIBUTES = (Private, ); }; };
+		A77E1FEF14AACB6E005B7CB6 /* TreeScopeAdopter.cpp in Sources */ = {isa = PBXBuildFile; fileRef = A77E1FED14AACB6E005B7CB6 /* TreeScopeAdopter.cpp */; };
+		A77E1FF014AACB6E005B7CB6 /* TreeScopeAdopter.h in Headers */ = {isa = PBXBuildFile; fileRef = A77E1FEE14AACB6E005B7CB6 /* TreeScopeAdopter.h */; };
 		A781C6A713828B5D0012A62A /* DocumentMarker.cpp in Sources */ = {isa = PBXBuildFile; fileRef = A781C6A613828B5D0012A62A /* DocumentMarker.cpp */; };
 		A784941B0B5FE507001E237A /* Clipboard.cpp in Sources */ = {isa = PBXBuildFile; fileRef = A784941A0B5FE507001E237A /* Clipboard.cpp */; };
 		A78E526F1346BD1700AD9C31 /* MeterShadowElement.cpp in Sources */ = {isa = PBXBuildFile; fileRef = A78E526D1346BD1700AD9C31 /* MeterShadowElement.cpp */; };
@@ -10776,6 +10778,8 @@
 		A77979250D6B9E64003851B9 /* JSImageData.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = JSImageData.h; sourceTree = "<group>"; };
 		A77B419F12E675A90054343D /* TextEventInputType.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = TextEventInputType.h; sourceTree = "<group>"; };
 		A77D0011133B0AEB00D6658C /* TextChecking.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = TextChecking.h; sourceTree = "<group>"; };
+		A77E1FED14AACB6E005B7CB6 /* TreeScopeAdopter.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = TreeScopeAdopter.cpp; sourceTree = "<group>"; };
+		A77E1FEE14AACB6E005B7CB6 /* TreeScopeAdopter.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = TreeScopeAdopter.h; sourceTree = "<group>"; };
 		A781C6A613828B5D0012A62A /* DocumentMarker.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = DocumentMarker.cpp; sourceTree = "<group>"; };
 		A784941A0B5FE507001E237A /* Clipboard.cpp */ = {isa = PBXFileReference; fileEncoding = 30; lastKnownFileType = sourcecode.cpp.cpp; path = Clipboard.cpp; sourceTree = "<group>"; };
 		A78E526D1346BD1700AD9C31 /* MeterShadowElement.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = MeterShadowElement.cpp; sourceTree = "<group>"; };
@@ -21444,6 +21448,8 @@
 				37FD4297118368460093C029 /* TreeDepthLimit.h */,
 				14D64B5A134A5B6B00E58FDA /* TreeScope.cpp */,
 				14D64B5B134A5B6B00E58FDA /* TreeScope.h */,
+				A77E1FED14AACB6E005B7CB6 /* TreeScopeAdopter.cpp */,
+				A77E1FEE14AACB6E005B7CB6 /* TreeScopeAdopter.h */,
 				854FE72E0A2297BE0058D7AD /* TreeWalker.cpp */,
 				854FE72F0A2297BE0058D7AD /* TreeWalker.h */,
 				1A750D3C0A90DE35000FF215 /* TreeWalker.idl */,
@@ -24695,6 +24701,7 @@
 				854FE7370A2297BE0058D7AD /* Traversal.h in Headers */,
 				37FD4298118368460093C029 /* TreeDepthLimit.h in Headers */,
 				14D64B5D134A5B6B00E58FDA /* TreeScope.h in Headers */,
+				A77E1FF014AACB6E005B7CB6 /* TreeScopeAdopter.h in Headers */,
 				1419D2C50CEA6F6100FF507A /* TreeShared.h in Headers */,
 				854FE7390A2297BE0058D7AD /* TreeWalker.h in Headers */,
 				37C28A6810F659CC008C7813 /* TypesettingFeatures.h in Headers */,
@@ -27626,6 +27633,7 @@
 				49E911D10EF86D47009D0CAF /* TranslateTransformOperation.cpp in Sources */,
 				854FE7360A2297BE0058D7AD /* Traversal.cpp in Sources */,
 				14D64B5C134A5B6B00E58FDA /* TreeScope.cpp in Sources */,
+				A77E1FEF14AACB6E005B7CB6 /* TreeScopeAdopter.cpp in Sources */,
 				854FE7380A2297BE0058D7AD /* TreeWalker.cpp in Sources */,
 				93309E19099E64920056E581 /* TypingCommand.cpp in Sources */,
 				85031B4D0A44EFC700F992E0 /* UIEvent.cpp in Sources */,

Modified: trunk/Source/WebCore/dom/ContainerNode.cpp (104258 => 104259)


--- trunk/Source/WebCore/dom/ContainerNode.cpp	2012-01-06 01:37:39 UTC (rev 104258)
+++ trunk/Source/WebCore/dom/ContainerNode.cpp	2012-01-06 01:58:34 UTC (rev 104259)
@@ -99,7 +99,7 @@
         // FIXME: Together with adoptNode above, the tree scope might get updated recursively twice
         // (if the document changed or oldParent was in a shadow tree, AND *this is in a shadow tree).
         // Can we do better?
-        child->setTreeScopeRecursively(treeScope());
+        treeScope()->adoptIfNeeded(child.get());
         if (attached() && !child->attached())
             child->attach();
     }
@@ -175,7 +175,7 @@
         InspectorInstrumentation::willInsertDOMNode(document(), child, this);
 #endif
 
-        child->setTreeScopeRecursively(treeScope());
+        treeScope()->adoptIfNeeded(child);
 
         insertBeforeCommon(next.get(), child);
 
@@ -329,7 +329,7 @@
         InspectorInstrumentation::willInsertDOMNode(document(), child.get(), this);
 #endif
 
-        child->setTreeScopeRecursively(treeScope());
+        treeScope()->adoptIfNeeded(child.get());
 
         // Add child after "prev".
         forbidEventDispatch();
@@ -509,7 +509,7 @@
     oldChild->setNextSibling(0);
     oldChild->setParent(0);
 
-    oldChild->setTreeScopeRecursively(document());
+    document()->adoptIfNeeded(oldChild);
 
     allowEventDispatch();
 }
@@ -564,7 +564,7 @@
         n->setPreviousSibling(0);
         n->setNextSibling(0);
         n->setParent(0);
-        n->setTreeScopeRecursively(document());
+        document()->adoptIfNeeded(n.get());
 
         m_firstChild = next;
         if (n == m_lastChild)
@@ -649,7 +649,7 @@
         InspectorInstrumentation::willInsertDOMNode(document(), child, this);
 #endif
 
-        child->setTreeScopeRecursively(treeScope());
+        treeScope()->adoptIfNeeded(child);
 
         // Append child to the end of the list
         forbidEventDispatch();
@@ -697,7 +697,7 @@
     Node* last = m_lastChild;
     // FIXME: This method should take a PassRefPtr.
     appendChildToContainer<Node, ContainerNode>(newChild.get(), this);
-    newChild->setTreeScopeRecursively(treeScope());
+    treeScope()->adoptIfNeeded(newChild.get());
     
     allowEventDispatch();
 

Modified: trunk/Source/WebCore/dom/DOMAllInOne.cpp (104258 => 104259)


--- trunk/Source/WebCore/dom/DOMAllInOne.cpp	2012-01-06 01:37:39 UTC (rev 104258)
+++ trunk/Source/WebCore/dom/DOMAllInOne.cpp	2012-01-06 01:58:34 UTC (rev 104259)
@@ -129,6 +129,7 @@
 #include "TransformSourceLibxslt.cpp"
 #include "Traversal.cpp"
 #include "TreeScope.cpp"
+#include "TreeScopeAdopter.cpp"
 #include "TreeWalker.cpp"
 #include "UIEvent.cpp"
 #include "UIEventWithKeyState.cpp"

Modified: trunk/Source/WebCore/dom/Document.cpp (104258 => 104259)


--- trunk/Source/WebCore/dom/Document.cpp	2012-01-06 01:37:39 UTC (rev 104258)
+++ trunk/Source/WebCore/dom/Document.cpp	2012-01-06 01:58:34 UTC (rev 104259)
@@ -712,7 +712,7 @@
     ASSERT(!m_docType || !docType);
     m_docType = docType;
     if (m_docType)
-        m_docType->setTreeScopeRecursively(this);
+        this->adoptIfNeeded(m_docType.get());
 }
 
 DOMImplementation* Document::implementation()
@@ -942,7 +942,7 @@
             source->parentNode()->removeChild(source.get(), ec);
     }
 
-    source->setTreeScopeRecursively(this);
+    this->adoptIfNeeded(source.get());
 
     return source;
 }

Modified: trunk/Source/WebCore/dom/Element.cpp (104258 => 104259)


--- trunk/Source/WebCore/dom/Element.cpp	2012-01-06 01:37:39 UTC (rev 104258)
+++ trunk/Source/WebCore/dom/Element.cpp	2012-01-06 01:58:34 UTC (rev 104259)
@@ -1221,7 +1221,7 @@
             oldRoot->detach();
 
         oldRoot->setShadowHost(0);
-        oldRoot->setTreeScopeRecursively(document());
+        document()->adoptIfNeeded(oldRoot.get());
         if (oldRoot->inDocument())
             oldRoot->removedFromDocument();
         else

Modified: trunk/Source/WebCore/dom/Node.cpp (104258 => 104259)


--- trunk/Source/WebCore/dom/Node.cpp	2012-01-06 01:37:39 UTC (rev 104258)
+++ trunk/Source/WebCore/dom/Node.cpp	2012-01-06 01:58:34 UTC (rev 104259)
@@ -90,6 +90,7 @@
 #include "TagNodeList.h"
 #include "Text.h"
 #include "TextEvent.h"
+#include "TreeScopeAdopter.h"
 #include "UIEvent.h"
 #include "UIEventWithKeyState.h"
 #include "WebKitAnimationEvent.h"
@@ -417,37 +418,30 @@
         doc->guardDeref();
 }
 
-#ifndef NDEBUG
-
-static bool didMoveToNewDocumentWasCalled;
-static Document* oldDocumentDidMoveToNewDocumentWasCalledWith;
-
-#endif
-    
 void Node::setDocument(Document* document)
 {
     ASSERT(!inDocument() || m_document == document);
     if (inDocument() || m_document == document)
         return;
 
-    document->guardRef();
-
-    if (m_document) {
-        m_document->moveNodeIteratorsToNewDocument(this, document);
-        m_document->guardDeref();
-    }
-
-    Document* oldDocument = m_document;
     m_document = document;
+}
 
-#ifndef NDEBUG
-    didMoveToNewDocumentWasCalled = false;
-    oldDocumentDidMoveToNewDocumentWasCalledWith = oldDocument;
-#endif
+NodeRareData* Node::setTreeScope(TreeScope* scope)
+{
+    if (!scope) {
+        if (hasRareData()) {
+            NodeRareData* data = ""
+            data->setTreeScope(0);
+            return data;
+        }
 
-    didMoveToNewDocument(oldDocument);
+        return 0;
+    }
 
-    ASSERT(didMoveToNewDocumentWasCalled);
+    NodeRareData* data = ""
+    data->setTreeScope(scope);
+    return data;
 }
 
 TreeScope* Node::treeScope() const
@@ -459,54 +453,6 @@
     return scope ? scope : m_document;
 }
 
-void Node::setTreeScopeRecursively(TreeScope* newTreeScope)
-{
-    ASSERT(this);
-    ASSERT(!isDocumentNode());
-    ASSERT(newTreeScope);
-    ASSERT(!m_deletionHasBegun);
-
-    TreeScope* currentTreeScope = treeScope();
-    if (currentTreeScope == newTreeScope)
-        return;
-
-    Document* currentDocument = document();
-    Document* newDocument = newTreeScope->document();
-    // If an element is moved from a document and then eventually back again the collection cache for
-    // that element may contain stale data as changes made to it will have updated the DOMTreeVersion
-    // of the document it was moved to. By increasing the DOMTreeVersion of the donating document here
-    // we ensure that the collection cache will be invalidated as needed when the element is moved back.
-    if (currentDocument && currentDocument != newDocument)
-        currentDocument->incDOMTreeVersion();
-
-    for (Node* node = this; node; node = node->traverseNextNode(this)) {
-        if (newTreeScope == newDocument) {
-            if (node->hasRareData())
-                node->rareData()->setTreeScope(0);
-            // Setting the new document tree scope will be handled implicitly
-            // by setDocument() below.
-        } else
-            node->ensureRareData()->setTreeScope(newTreeScope);
-
-        if (node->hasRareData() && node->rareData()->nodeLists()) {
-            node->rareData()->nodeLists()->invalidateCaches();
-            if (currentTreeScope)
-                currentTreeScope->removeNodeListCache();
-            newTreeScope->addNodeListCache();
-        }
-
-        node->setDocument(newDocument);
-
-        if (!node->isElementNode())
-            continue;
-        if (ShadowRoot* shadowRoot = toElement(node)->shadowRoot()) {
-            shadowRoot->setParentTreeScope(newTreeScope);
-            if (currentDocument != newDocument)
-                shadowRoot->setDocumentRecursively(newDocument);
-        }
-    }
-}
-
 NodeRareData* Node::rareData() const
 {
     ASSERT(hasRareData());
@@ -852,19 +798,6 @@
     return node->isElementNode() ? toElement(node)->shadowRoot() : 0;
 }
 
-void Node::setDocumentRecursively(Document* newDocument)
-{
-    ASSERT(document() != newDocument);
-
-    for (Node* node = this; node; node = node->traverseNextNode(this)) {
-        node->setDocument(newDocument);
-        if (!node->isElementNode())
-            continue;
-        if (ShadowRoot* shadow = shadowRoot(node))
-            shadow->setDocumentRecursively(newDocument);
-    }
-}
-
 inline void Node::setStyleChange(StyleChangeType changeType)
 {
     m_nodeFlags = (m_nodeFlags & ~StyleChangeMask) | changeType;
@@ -2408,13 +2341,8 @@
 
 void Node::didMoveToNewDocument(Document* oldDocument)
 {
-    ASSERT(!didMoveToNewDocumentWasCalled);
-    ASSERT_UNUSED(oldDocument, oldDocument == oldDocumentDidMoveToNewDocumentWasCalledWith);
+    TreeScopeAdopter::ensureDidMoveToNewDocumentWasCalled(oldDocument);
 
-#ifndef NDEBUG
-    didMoveToNewDocumentWasCalled = true;
-#endif
-
     // FIXME: Event listener types for this node should be set on the new owner document here.
 
 #if ENABLE(MUTATION_OBSERVERS)

Modified: trunk/Source/WebCore/dom/Node.h (104258 => 104259)


--- trunk/Source/WebCore/dom/Node.h	2012-01-06 01:37:39 UTC (rev 104258)
+++ trunk/Source/WebCore/dom/Node.h	2012-01-06 01:58:34 UTC (rev 104259)
@@ -104,6 +104,7 @@
 class Node : public EventTarget, public ScriptWrappable, public TreeShared<ContainerNode> {
     friend class Document;
     friend class TreeScope;
+    friend class TreeScopeAdopter;
 
 public:
     enum NodeType {
@@ -383,9 +384,6 @@
 
     TreeScope* treeScope() const;
 
-    // Used by the basic DOM methods (e.g., appendChild()).
-    void setTreeScopeRecursively(TreeScope*);
-
     // Returns true if this node is associated with a document and is in its associated document's
     // node tree, false otherwise.
     bool inDocument() const 
@@ -695,9 +693,9 @@
     void clearHasCustomStyleForRenderer() { clearFlag(HasCustomStyleForRendererFlag); }
 
 private:
-    // Do not use this method to change the document of a node until after the node has been
-    // removed from its previous document.
-    void setDocumentRecursively(Document*);
+    // These API should be only used for a tree scope migration.
+    // setTreeScope() returns NodeRareData to save extra nodeRareData() invocations on the caller site.
+    NodeRareData* setTreeScope(TreeScope*);
     void setDocument(Document*);
 
     enum EditableLevel { Editable, RichlyEditable };

Modified: trunk/Source/WebCore/dom/TreeScope.cpp (104258 => 104259)


--- trunk/Source/WebCore/dom/TreeScope.cpp	2012-01-06 01:37:39 UTC (rev 104258)
+++ trunk/Source/WebCore/dom/TreeScope.cpp	2012-01-06 01:58:34 UTC (rev 104259)
@@ -31,6 +31,7 @@
 #include "HTMLMapElement.h"
 #include "HTMLNames.h"
 #include "NodeRareData.h"
+#include "TreeScopeAdopter.h"
 
 namespace WebCore {
 
@@ -137,5 +138,16 @@
     return true;
 }
 
+void TreeScope::adoptIfNeeded(Node* node)
+{
+    ASSERT(this);
+    ASSERT(node);
+    ASSERT(!node->isDocumentNode());
+    ASSERT(!node->m_deletionHasBegun);
+    TreeScopeAdopter adopter(node, this);
+    if (adopter.needsScopeChange())
+        adopter.execute();
+}
+
 } // namespace WebCore
 

Modified: trunk/Source/WebCore/dom/TreeScope.h (104258 => 104259)


--- trunk/Source/WebCore/dom/TreeScope.h	2012-01-06 01:37:39 UTC (rev 104258)
+++ trunk/Source/WebCore/dom/TreeScope.h	2012-01-06 01:58:34 UTC (rev 104259)
@@ -64,6 +64,9 @@
 
     virtual bool applyAuthorSheets() const;
 
+    // Used by the basic DOM mutation methods (e.g., appendChild()).
+    void adoptIfNeeded(Node*);
+
 protected:
     TreeScope(Document*, ConstructionType = CreateContainer);
     virtual ~TreeScope();

Added: trunk/Source/WebCore/dom/TreeScopeAdopter.cpp (0 => 104259)


--- trunk/Source/WebCore/dom/TreeScopeAdopter.cpp	                        (rev 0)
+++ trunk/Source/WebCore/dom/TreeScopeAdopter.cpp	2012-01-06 01:58:34 UTC (rev 104259)
@@ -0,0 +1,114 @@
+/*
+ * Copyright (C) 1999 Lars Knoll ([email protected])
+ *           (C) 1999 Antti Koivisto ([email protected])
+ *           (C) 2001 Dirk Mueller ([email protected])
+ * Copyright (C) 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011 Apple Inc. All rights reserved.
+ * Copyright (C) 2008 Nokia Corporation and/or its subsidiary(-ies)
+ * Copyright (C) 2009 Torch Mobile Inc. All rights reserved. (http://www.torchmobile.com/)
+ * Copyright (C) 2011 Google Inc. All rights reserved.
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Library General Public
+ * License as published by the Free Software Foundation; either
+ * version 2 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Library General Public License for more details.
+ *
+ * You should have received a copy of the GNU Library General Public License
+ * along with this library; see the file COPYING.LIB.  If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
+ * Boston, MA 02110-1301, USA.
+ */
+#include "config.h"
+#include "TreeScopeAdopter.h"
+
+#include "Document.h"
+#include "NodeRareData.h"
+#include "ShadowRoot.h"
+
+namespace WebCore {
+
+static inline ShadowRoot* shadowRootFor(Node* node)
+{
+    return node->isElementNode() ? toElement(node)->shadowRoot() : 0;
+}
+
+void TreeScopeAdopter::moveTreeToNewScope(Node* root) const
+{
+    ASSERT(needsScopeChange());
+
+    // If an element is moved from a document and then eventually back again the collection cache for
+    // that element may contain stale data as changes made to it will have updated the DOMTreeVersion
+    // of the document it was moved to. By increasing the DOMTreeVersion of the donating document here
+    // we ensure that the collection cache will be invalidated as needed when the element is moved back.
+    Document* oldDocument = m_oldScope->document();
+    Document* newDocument = m_newScope->document();
+    bool willMoveToNewDocument = oldDocument != newDocument;
+    if (oldDocument && willMoveToNewDocument)
+        oldDocument->incDOMTreeVersion();
+
+    for (Node* node = root; node; node = node->traverseNextNode(root)) {
+        NodeRareData* rareData = node->setTreeScope(newDocument == m_newScope ? 0 : m_newScope);
+        if (rareData && rareData->nodeLists()) {
+            if (m_oldScope)
+                m_oldScope->removeNodeListCache();
+            m_newScope->addNodeListCache();
+        }
+
+        if (willMoveToNewDocument)
+            moveNodeToNewDocument(node, oldDocument, newDocument);
+
+        if (ShadowRoot* shadow = shadowRootFor(node)) {
+            shadow->setParentTreeScope(m_newScope);
+            if (willMoveToNewDocument)
+                moveTreeToNewDocument(shadow, oldDocument, newDocument);
+        }
+    }
+}
+
+void TreeScopeAdopter::moveTreeToNewDocument(Node* root, Document* oldDocument, Document* newDocument) const
+{
+    for (Node* node = root; node; node = node->traverseNextNode(root)) {
+        moveNodeToNewDocument(node, oldDocument, newDocument);
+        if (ShadowRoot* shadow = shadowRootFor(node))
+            moveTreeToNewDocument(shadow, oldDocument, newDocument);
+    }
+}
+
+#ifndef NDEBUG
+static bool didMoveToNewDocumentWasCalled = false;
+static Document* oldDocumentDidMoveToNewDocumentWasCalledWith = NULL;
+
+void TreeScopeAdopter::ensureDidMoveToNewDocumentWasCalled(Document* oldDocument)
+{
+    ASSERT(!didMoveToNewDocumentWasCalled);
+    ASSERT_UNUSED(oldDocument, oldDocument == oldDocumentDidMoveToNewDocumentWasCalledWith);
+    didMoveToNewDocumentWasCalled = true;
+}
+#endif
+
+void TreeScopeAdopter::moveNodeToNewDocument(Node* node, Document* oldDocument, Document* newDocument) const
+{
+    ASSERT(!node->inDocument() || oldDocument != newDocument);
+
+    newDocument->guardRef();
+    if (oldDocument) {
+        oldDocument->moveNodeIteratorsToNewDocument(node, newDocument);
+        oldDocument->guardDeref();
+    }
+
+    node->setDocument(newDocument);
+
+#ifndef NDEBUG
+    didMoveToNewDocumentWasCalled = false;
+    oldDocumentDidMoveToNewDocumentWasCalledWith = oldDocument;
+#endif
+
+    node->didMoveToNewDocument(oldDocument);
+    ASSERT(didMoveToNewDocumentWasCalled);
+}
+
+}

Added: trunk/Source/WebCore/dom/TreeScopeAdopter.h (0 => 104259)


--- trunk/Source/WebCore/dom/TreeScopeAdopter.h	                        (rev 0)
+++ trunk/Source/WebCore/dom/TreeScopeAdopter.h	2012-01-06 01:58:34 UTC (rev 104259)
@@ -0,0 +1,65 @@
+/*
+ * Copyright (C) 1999 Lars Knoll ([email protected])
+ *           (C) 1999 Antti Koivisto ([email protected])
+ *           (C) 2001 Dirk Mueller ([email protected])
+ * Copyright (C) 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011 Apple Inc. All rights reserved.
+ * Copyright (C) 2008 Nokia Corporation and/or its subsidiary(-ies)
+ * Copyright (C) 2009 Torch Mobile Inc. All rights reserved. (http://www.torchmobile.com/)
+ * Copyright (C) 2011 Google Inc. All rights reserved.
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Library General Public
+ * License as published by the Free Software Foundation; either
+ * version 2 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Library General Public License for more details.
+ *
+ * You should have received a copy of the GNU Library General Public License
+ * along with this library; see the file COPYING.LIB.  If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
+ * Boston, MA 02110-1301, USA.
+ */
+#ifndef TreeScopeAdopter_h
+#define TreeScopeAdopter_h
+
+#include "Element.h"
+
+namespace WebCore {
+
+class TreeScopeAdopter {
+public:
+    explicit TreeScopeAdopter(Node* toAdopt, TreeScope* newScope);
+
+    void execute() const { moveTreeToNewScope(m_toAdopt); }
+    bool needsScopeChange() const { return m_oldScope != m_newScope; }
+
+#ifdef NDEBUG
+    static void ensureDidMoveToNewDocumentWasCalled(Document*) { }
+#else
+    static void ensureDidMoveToNewDocumentWasCalled(Document*);
+#endif
+
+private:
+    void moveTreeToNewScope(Node*) const;
+    void moveTreeToNewDocument(Node*, Document* oldDocument, Document* newDocument) const;
+    void moveNodeToNewDocument(Node*, Document* oldDocument, Document* newDocument) const;
+
+    Node* m_toAdopt;
+    TreeScope* m_newScope;
+    TreeScope* m_oldScope;
+};
+
+inline TreeScopeAdopter::TreeScopeAdopter(Node* toAdopt, TreeScope* newScope)
+    : m_toAdopt(toAdopt)
+    , m_newScope(newScope)
+    , m_oldScope(toAdopt->treeScope())
+{
+    ASSERT(newScope);
+}
+
+}
+
+#endif
_______________________________________________
webkit-changes mailing list
[email protected]
http://lists.webkit.org/mailman/listinfo.cgi/webkit-changes

Reply via email to