2011-03-02 Sheriff Bot <webkit.review.bot@gmail.com>
authorrniwa@webkit.org <rniwa@webkit.org@268f45cc-cd09-0410-ab3c-d52691b4dbfc>
Thu, 3 Mar 2011 06:18:55 +0000 (06:18 +0000)
committerrniwa@webkit.org <rniwa@webkit.org@268f45cc-cd09-0410-ab3c-d52691b4dbfc>
Thu, 3 Mar 2011 06:18:55 +0000 (06:18 +0000)
        Unreviewed, rolling out r80201.
        http://trac.webkit.org/changeset/80201
        https://bugs.webkit.org/show_bug.cgi?id=55648

        "caused tests to crash on several bots" (Requested by rniwa on
        #webkit).

        * dom/Element.h:
        (WebCore::Node::hasTagName):
        * dom/Node.h:
        * html/parser/HTMLConstructionSite.cpp:
        (WebCore::HTMLNames::hasImpliedEndTag):
        (WebCore::HTMLConstructionSite::insertHTMLHtmlStartTagInBody):
        (WebCore::HTMLConstructionSite::insertComment):
        (WebCore::HTMLConstructionSite::insertCommentOnHTMLHtmlElement):
        (WebCore::HTMLConstructionSite::attachToCurrent):
        (WebCore::HTMLConstructionSite::insertScriptElement):
        (WebCore::HTMLConstructionSite::insertTextNode):
        (WebCore::HTMLConstructionSite::createElement):
        (WebCore::HTMLConstructionSite::createHTMLElement):
        (WebCore::HTMLConstructionSite::generateImpliedEndTagsWithExclusion):
        (WebCore::HTMLConstructionSite::generateImpliedEndTags):
        (WebCore::HTMLConstructionSite::findFosterSite):
        (WebCore::HTMLConstructionSite::shouldFosterParent):
        * html/parser/HTMLConstructionSite.h:
        * html/parser/HTMLElementStack.cpp:
        (WebCore::HTMLNames::isNumberedHeaderElement):
        (WebCore::HTMLNames::isScopeMarker):
        (WebCore::HTMLNames::isListItemScopeMarker):
        (WebCore::HTMLNames::isTableScopeMarker):
        (WebCore::HTMLNames::isTableBodyScopeMarker):
        (WebCore::HTMLNames::isTableRowScopeMarker):
        (WebCore::HTMLNames::isButtonScopeMarker):
        (WebCore::HTMLNames::isSelectScopeMarker):
        (WebCore::HTMLElementStack::ElementRecord::ElementRecord):
        (WebCore::HTMLElementStack::ElementRecord::replaceElement):
        (WebCore::HTMLElementStack::HTMLElementStack):
        (WebCore::HTMLElementStack::secondElementIsHTMLBodyElement):
        (WebCore::HTMLElementStack::popAll):
        (WebCore::HTMLElementStack::popUntilTableScopeMarker):
        (WebCore::HTMLElementStack::popUntilTableBodyScopeMarker):
        (WebCore::HTMLElementStack::popUntilTableRowScopeMarker):
        (WebCore::HTMLElementStack::popUntilForeignContentScopeMarker):
        (WebCore::HTMLElementStack::pushHTMLHtmlElement):
        (WebCore::HTMLElementStack::push):
        (WebCore::HTMLElementStack::insertAbove):
        (WebCore::HTMLElementStack::find):
        (WebCore::HTMLElementStack::topmost):
        (WebCore::inScopeCommon):
        (WebCore::HTMLElementStack::hasNumberedHeaderElementInScope):
        (WebCore::HTMLElementStack::htmlElement):
        (WebCore::HTMLElementStack::bodyElement):
        (WebCore::HTMLElementStack::pushCommon):
        * html/parser/HTMLElementStack.h:
        (WebCore::HTMLElementStack::ElementRecord::element):
        (WebCore::HTMLElementStack::top):
        * html/parser/HTMLTreeBuilder.cpp:
        (WebCore::HTMLTreeBuilder::HTMLTreeBuilder):
        (WebCore::HTMLTreeBuilder::FragmentParsingContext::finished):
        (WebCore::HTMLTreeBuilder::processCloseWhenNestedTag):
        (WebCore::HTMLTreeBuilder::processStartTagForInBody):
        (WebCore::HTMLTreeBuilder::processColgroupEndTagForInColumnGroup):
        (WebCore::HTMLTreeBuilder::processStartTag):
        (WebCore::HTMLTreeBuilder::processAnyOtherEndTagForInBody):
        (WebCore::HTMLTreeBuilder::callTheAdoptionAgency):
        (WebCore::HTMLTreeBuilder::resetInsertionModeAppropriately):
        (WebCore::HTMLTreeBuilder::processEndTagForInCell):
        (WebCore::HTMLTreeBuilder::processEndTagForInBody):
        (WebCore::HTMLTreeBuilder::processEndTag):
        (WebCore::HTMLTreeBuilder::processEndOfFile):
        (WebCore::HTMLTreeBuilder::finished):
        * html/parser/HTMLTreeBuilder.h:

git-svn-id: https://svn.webkit.org/repository/webkit/trunk@80209 268f45cc-cd09-0410-ab3c-d52691b4dbfc

Source/WebCore/ChangeLog
Source/WebCore/dom/Element.h
Source/WebCore/dom/Node.h
Source/WebCore/html/parser/HTMLConstructionSite.cpp
Source/WebCore/html/parser/HTMLConstructionSite.h
Source/WebCore/html/parser/HTMLElementStack.cpp
Source/WebCore/html/parser/HTMLElementStack.h
Source/WebCore/html/parser/HTMLTreeBuilder.cpp
Source/WebCore/html/parser/HTMLTreeBuilder.h

index 9414fda..7d04ab0 100644 (file)
@@ -1,3 +1,78 @@
+2011-03-02  Sheriff Bot  <webkit.review.bot@gmail.com>
+
+        Unreviewed, rolling out r80201.
+        http://trac.webkit.org/changeset/80201
+        https://bugs.webkit.org/show_bug.cgi?id=55648
+
+        "caused tests to crash on several bots" (Requested by rniwa on
+        #webkit).
+
+        * dom/Element.h:
+        (WebCore::Node::hasTagName):
+        * dom/Node.h:
+        * html/parser/HTMLConstructionSite.cpp:
+        (WebCore::HTMLNames::hasImpliedEndTag):
+        (WebCore::HTMLConstructionSite::insertHTMLHtmlStartTagInBody):
+        (WebCore::HTMLConstructionSite::insertComment):
+        (WebCore::HTMLConstructionSite::insertCommentOnHTMLHtmlElement):
+        (WebCore::HTMLConstructionSite::attachToCurrent):
+        (WebCore::HTMLConstructionSite::insertScriptElement):
+        (WebCore::HTMLConstructionSite::insertTextNode):
+        (WebCore::HTMLConstructionSite::createElement):
+        (WebCore::HTMLConstructionSite::createHTMLElement):
+        (WebCore::HTMLConstructionSite::generateImpliedEndTagsWithExclusion):
+        (WebCore::HTMLConstructionSite::generateImpliedEndTags):
+        (WebCore::HTMLConstructionSite::findFosterSite):
+        (WebCore::HTMLConstructionSite::shouldFosterParent):
+        * html/parser/HTMLConstructionSite.h:
+        * html/parser/HTMLElementStack.cpp:
+        (WebCore::HTMLNames::isNumberedHeaderElement):
+        (WebCore::HTMLNames::isScopeMarker):
+        (WebCore::HTMLNames::isListItemScopeMarker):
+        (WebCore::HTMLNames::isTableScopeMarker):
+        (WebCore::HTMLNames::isTableBodyScopeMarker):
+        (WebCore::HTMLNames::isTableRowScopeMarker):
+        (WebCore::HTMLNames::isButtonScopeMarker):
+        (WebCore::HTMLNames::isSelectScopeMarker):
+        (WebCore::HTMLElementStack::ElementRecord::ElementRecord):
+        (WebCore::HTMLElementStack::ElementRecord::replaceElement):
+        (WebCore::HTMLElementStack::HTMLElementStack):
+        (WebCore::HTMLElementStack::secondElementIsHTMLBodyElement):
+        (WebCore::HTMLElementStack::popAll):
+        (WebCore::HTMLElementStack::popUntilTableScopeMarker):
+        (WebCore::HTMLElementStack::popUntilTableBodyScopeMarker):
+        (WebCore::HTMLElementStack::popUntilTableRowScopeMarker):
+        (WebCore::HTMLElementStack::popUntilForeignContentScopeMarker):
+        (WebCore::HTMLElementStack::pushHTMLHtmlElement):
+        (WebCore::HTMLElementStack::push):
+        (WebCore::HTMLElementStack::insertAbove):
+        (WebCore::HTMLElementStack::find):
+        (WebCore::HTMLElementStack::topmost):
+        (WebCore::inScopeCommon):
+        (WebCore::HTMLElementStack::hasNumberedHeaderElementInScope):
+        (WebCore::HTMLElementStack::htmlElement):
+        (WebCore::HTMLElementStack::bodyElement):
+        (WebCore::HTMLElementStack::pushCommon):
+        * html/parser/HTMLElementStack.h:
+        (WebCore::HTMLElementStack::ElementRecord::element):
+        (WebCore::HTMLElementStack::top):
+        * html/parser/HTMLTreeBuilder.cpp:
+        (WebCore::HTMLTreeBuilder::HTMLTreeBuilder):
+        (WebCore::HTMLTreeBuilder::FragmentParsingContext::finished):
+        (WebCore::HTMLTreeBuilder::processCloseWhenNestedTag):
+        (WebCore::HTMLTreeBuilder::processStartTagForInBody):
+        (WebCore::HTMLTreeBuilder::processColgroupEndTagForInColumnGroup):
+        (WebCore::HTMLTreeBuilder::processStartTag):
+        (WebCore::HTMLTreeBuilder::processAnyOtherEndTagForInBody):
+        (WebCore::HTMLTreeBuilder::callTheAdoptionAgency):
+        (WebCore::HTMLTreeBuilder::resetInsertionModeAppropriately):
+        (WebCore::HTMLTreeBuilder::processEndTagForInCell):
+        (WebCore::HTMLTreeBuilder::processEndTagForInBody):
+        (WebCore::HTMLTreeBuilder::processEndTag):
+        (WebCore::HTMLTreeBuilder::processEndOfFile):
+        (WebCore::HTMLTreeBuilder::finished):
+        * html/parser/HTMLTreeBuilder.h:
+
 2011-03-02  Yury Semikhatsky  <yurys@chromium.org>
 
         Reviewed by Pavel Feldman.
index 81828ea..751e7e9 100644 (file)
@@ -427,11 +427,6 @@ inline bool Node::hasTagName(const QualifiedName& name) const
 {
     return isElementNode() && toElement(this)->hasTagName(name);
 }
-    
-inline bool Node::hasLocalName(const AtomicString& name) const
-{
-    return isElementNode() && toElement(this)->hasLocalName(name);
-}
 
 inline bool Node::hasAttributes() const
 {
index 01cab7a..35ce718 100644 (file)
@@ -2,7 +2,7 @@
  * Copyright (C) 1999 Lars Knoll (knoll@kde.org)
  *           (C) 1999 Antti Koivisto (koivisto@kde.org)
  *           (C) 2001 Dirk Mueller (mueller@kde.org)
- * Copyright (C) 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011 Apple Inc. All rights reserved.
+ * Copyright (C) 2004, 2005, 2006, 2007, 2008, 2009, 2010 Apple Inc. All rights reserved.
  * Copyright (C) 2008, 2009 Torch Mobile Inc. All rights reserved. (http://www.torchmobile.com/)
  *
  * This library is free software; you can redistribute it and/or
@@ -134,7 +134,6 @@ public:
     // DOM methods & attributes for Node
 
     bool hasTagName(const QualifiedName&) const;
-    bool hasLocalName(const AtomicString&) const;
     virtual String nodeName() const = 0;
     virtual String nodeValue() const;
     virtual void setNodeValue(const String&, ExceptionCode&);
index 64d319e..a026ef9 100644 (file)
@@ -1,6 +1,5 @@
 /*
  * Copyright (C) 2010 Google, Inc. All Rights Reserved.
- * Copyright (C) 2011 Apple Inc. All rights reserved.
  *
  * Redistribution and use in source and binary forms, with or without
  * modification, are permitted provided that the following conditions
@@ -59,16 +58,16 @@ using namespace HTMLNames;
 
 namespace {
 
-bool hasImpliedEndTag(ContainerNode* node)
+bool hasImpliedEndTag(Element* element)
 {
-    return node->hasTagName(ddTag)
-        || node->hasTagName(dtTag)
-        || node->hasTagName(liTag)
-        || node->hasTagName(optionTag)
-        || node->hasTagName(optgroupTag)
-        || node->hasTagName(pTag)
-        || node->hasTagName(rpTag)
-        || node->hasTagName(rtTag);
+    return element->hasTagName(ddTag)
+        || element->hasTagName(dtTag)
+        || element->hasTagName(liTag)
+        || element->hasTagName(optionTag)
+        || element->hasTagName(optgroupTag)
+        || element->hasTagName(pTag)
+        || element->hasTagName(rpTag)
+        || element->hasTagName(rtTag);
 }
 
 bool causesFosterParenting(const QualifiedName& tagName)
@@ -205,12 +204,6 @@ void HTMLConstructionSite::mergeAttributesFromTokenIntoElement(AtomicHTMLToken&
 void HTMLConstructionSite::insertHTMLHtmlStartTagInBody(AtomicHTMLToken& token)
 {
     // FIXME: parse error
-    
-    // Fragments do not have a root HTML element, so any additional HTML elements
-    // encountered during fragment parsing should be ignored.
-    if (m_isParsingFragment)
-        return;
-
     mergeAttributesFromTokenIntoElement(token, m_openElements.htmlElement());
 }
 
@@ -243,7 +236,7 @@ void HTMLConstructionSite::insertDoctype(AtomicHTMLToken& token)
 void HTMLConstructionSite::insertComment(AtomicHTMLToken& token)
 {
     ASSERT(token.type() == HTMLToken::Comment);
-    attach(currentNode(), Comment::create(currentNode()->document(), token.comment()));
+    attach(currentElement(), Comment::create(currentElement()->document(), token.comment()));
 }
 
 void HTMLConstructionSite::insertCommentOnDocument(AtomicHTMLToken& token)
@@ -255,13 +248,13 @@ void HTMLConstructionSite::insertCommentOnDocument(AtomicHTMLToken& token)
 void HTMLConstructionSite::insertCommentOnHTMLHtmlElement(AtomicHTMLToken& token)
 {
     ASSERT(token.type() == HTMLToken::Comment);
-    ContainerNode* parent = m_openElements.rootNode();
+    Element* parent = m_openElements.htmlElement();
     attach(parent, Comment::create(parent->document(), token.comment()));
 }
 
 PassRefPtr<Element> HTMLConstructionSite::attachToCurrent(PassRefPtr<Element> child)
 {
-    return attach(currentNode(), child);
+    return attach(currentElement(), child);
 }
 
 void HTMLConstructionSite::insertHTMLHeadElement(AtomicHTMLToken& token)
@@ -317,7 +310,7 @@ void HTMLConstructionSite::insertFormattingElement(AtomicHTMLToken& token)
 
 void HTMLConstructionSite::insertScriptElement(AtomicHTMLToken& token)
 {
-    RefPtr<HTMLScriptElement> element = HTMLScriptElement::create(scriptTag, currentNode()->document(), true);
+    RefPtr<HTMLScriptElement> element = HTMLScriptElement::create(scriptTag, currentElement()->document(), true);
     if (m_fragmentScriptingPermission == FragmentScriptingAllowed)
         element->setAttributeMap(token.takeAtributes(), m_fragmentScriptingPermission);
     m_openElements.push(attachToCurrent(element.release()));
@@ -336,7 +329,7 @@ void HTMLConstructionSite::insertForeignElement(AtomicHTMLToken& token, const At
 void HTMLConstructionSite::insertTextNode(const String& characters)
 {
     AttachmentSite site;
-    site.parent = currentNode();
+    site.parent = currentElement();
     site.nextChild = 0;
     if (shouldFosterParent())
         findFosterSite(site);
@@ -356,7 +349,7 @@ void HTMLConstructionSite::insertTextNode(const String& characters)
 PassRefPtr<Element> HTMLConstructionSite::createElement(AtomicHTMLToken& token, const AtomicString& namespaceURI)
 {
     QualifiedName tagName(nullAtom, token.name(), namespaceURI);
-    RefPtr<Element> element = currentNode()->document()->createElement(tagName, true);
+    RefPtr<Element> element = currentElement()->document()->createElement(tagName, true);
     element->setAttributeMap(token.takeAtributes(), m_fragmentScriptingPermission);
     return element.release();
 }
@@ -367,7 +360,7 @@ PassRefPtr<Element> HTMLConstructionSite::createHTMLElement(AtomicHTMLToken& tok
     // FIXME: This can't use HTMLConstructionSite::createElement because we
     // have to pass the current form element.  We should rework form association
     // to occur after construction to allow better code sharing here.
-    RefPtr<Element> element = HTMLElementFactory::createHTMLElement(tagName, currentNode()->document(), form(), true);
+    RefPtr<Element> element = HTMLElementFactory::createHTMLElement(tagName, currentElement()->document(), form(), true);
     element->setAttributeMap(token.takeAtributes(), m_fragmentScriptingPermission);
     ASSERT(element->isHTMLElement());
     return element.release();
@@ -446,13 +439,13 @@ void HTMLConstructionSite::reconstructTheActiveFormattingElements()
 
 void HTMLConstructionSite::generateImpliedEndTagsWithExclusion(const AtomicString& tagName)
 {
-    while (hasImpliedEndTag(currentNode()) && !currentNode()->hasLocalName(tagName))
+    while (hasImpliedEndTag(currentElement()) && !currentElement()->hasLocalName(tagName))
         m_openElements.pop();
 }
 
 void HTMLConstructionSite::generateImpliedEndTags()
 {
-    while (hasImpliedEndTag(currentNode()))
+    while (hasImpliedEndTag(currentElement()))
         m_openElements.pop();
 }
 
@@ -471,14 +464,13 @@ void HTMLConstructionSite::findFosterSite(AttachmentSite& site)
         return;
     }
     // Fragment case
-    site.parent = m_openElements.rootNode(); // DocumentFragment
+    site.parent = m_openElements.bottom(); // <html> element
     site.nextChild = 0;
 }
 
 bool HTMLConstructionSite::shouldFosterParent() const
 {
     return m_redirectAttachToFosterParent
-        && currentNode()->isElementNode()
         && causesFosterParenting(currentElement()->tagQName());
 }
 
index 380e487..0298503 100644 (file)
@@ -1,6 +1,5 @@
 /*
  * Copyright (C) 2010 Google, Inc. All Rights Reserved.
- * Copyright (C) 2011 Apple Inc. All rights reserved.
  *
  * Redistribution and use in source and binary forms, with or without
  * modification, are permitted provided that the following conditions
@@ -81,7 +80,6 @@ public:
     void generateImpliedEndTagsWithExclusion(const AtomicString& tagName);
 
     Element* currentElement() const { return m_openElements.top(); }
-    ContainerNode* currentNode() const { return m_openElements.topNode(); }
     Element* oneBelowTop() const { return m_openElements.oneBelowTop(); }
 
     HTMLElementStack* openElements() const { return &m_openElements; }
index 0820125..6aab0f7 100644 (file)
@@ -1,6 +1,5 @@
 /*
  * Copyright (C) 2010 Google, Inc. All Rights Reserved.
- * Copyright (C) 2011 Apple Inc. All rights reserved.
  *
  * Redistribution and use in source and binary forms, with or without
  * modification, are permitted provided that the following conditions
@@ -27,7 +26,6 @@
 #include "config.h"
 #include "HTMLElementStack.h"
 
-#include "DocumentFragment.h"
 #include "Element.h"
 #include "HTMLNames.h"
 #include "MathMLNames.h"
@@ -49,59 +47,53 @@ inline bool isNumberedHeaderElement(Element* element)
         || element->hasTagName(h5Tag)
         || element->hasTagName(h6Tag);
 }
-    
-inline bool isRootNode(ContainerNode* node)
-{
-    return node->nodeType() == Node::DOCUMENT_FRAGMENT_NODE
-        || node->hasTagName(htmlTag);
-}
 
-inline bool isScopeMarker(ContainerNode* node)
+inline bool isScopeMarker(Element* element)
 {
-    return node->hasTagName(appletTag)
-        || node->hasTagName(captionTag)
-        || node->hasTagName(marqueeTag)
-        || node->hasTagName(objectTag)
-        || node->hasTagName(tableTag)
-        || node->hasTagName(tdTag)
-        || node->hasTagName(thTag)
-        || node->hasTagName(MathMLNames::miTag)
-        || node->hasTagName(MathMLNames::moTag)
-        || node->hasTagName(MathMLNames::mnTag)
-        || node->hasTagName(MathMLNames::msTag)
-        || node->hasTagName(MathMLNames::mtextTag)
-        || node->hasTagName(MathMLNames::annotation_xmlTag)
-        || node->hasTagName(SVGNames::foreignObjectTag)
-        || node->hasTagName(SVGNames::descTag)
-        || node->hasTagName(SVGNames::titleTag)
-        || isRootNode(node);
+    return element->hasTagName(appletTag)
+        || element->hasTagName(captionTag)
+        || element->hasTagName(htmlTag)
+        || element->hasTagName(marqueeTag)
+        || element->hasTagName(objectTag)
+        || element->hasTagName(tableTag)
+        || element->hasTagName(tdTag)
+        || element->hasTagName(thTag)
+        || element->hasTagName(MathMLNames::miTag)
+        || element->hasTagName(MathMLNames::moTag)
+        || element->hasTagName(MathMLNames::mnTag)
+        || element->hasTagName(MathMLNames::msTag)
+        || element->hasTagName(MathMLNames::mtextTag)
+        || element->hasTagName(MathMLNames::annotation_xmlTag)
+        || element->hasTagName(SVGNames::foreignObjectTag)
+        || element->hasTagName(SVGNames::descTag)
+        || element->hasTagName(SVGNames::titleTag);
 }
 
-inline bool isListItemScopeMarker(ContainerNode* node)
+inline bool isListItemScopeMarker(Element* element)
 {
-    return isScopeMarker(node)
-        || node->hasTagName(olTag)
-        || node->hasTagName(ulTag);
+    return isScopeMarker(element)
+        || element->hasTagName(olTag)
+        || element->hasTagName(ulTag);
 }
 
-inline bool isTableScopeMarker(ContainerNode* node)
+inline bool isTableScopeMarker(Element* element)
 {
-    return node->hasTagName(tableTag)
-        || isRootNode(node);
+    return element->hasTagName(tableTag)
+        || element->hasTagName(htmlTag);
 }
 
-inline bool isTableBodyScopeMarker(ContainerNode* node)
+inline bool isTableBodyScopeMarker(Element* element)
 {
-    return node->hasTagName(tbodyTag)
-        || node->hasTagName(tfootTag)
-        || node->hasTagName(theadTag)
-        || isRootNode(node);
+    return element->hasTagName(tbodyTag)
+        || element->hasTagName(tfootTag)
+        || element->hasTagName(theadTag)
+        || element->hasTagName(htmlTag);
 }
 
-inline bool isTableRowScopeMarker(ContainerNode* node)
+inline bool isTableRowScopeMarker(Element* element)
 {
-    return node->hasTagName(trTag)
-        || isRootNode(node);
+    return element->hasTagName(trTag)
+        || element->hasTagName(htmlTag);
 }
 
 inline bool isForeignContentScopeMarker(Element* element)
@@ -117,25 +109,25 @@ inline bool isForeignContentScopeMarker(Element* element)
         || element->namespaceURI() == HTMLNames::xhtmlNamespaceURI;
 }
 
-inline bool isButtonScopeMarker(ContainerNode* node)
+inline bool isButtonScopeMarker(Element* element)
 {
-    return isScopeMarker(node)
-        || node->hasTagName(buttonTag);
+    return isScopeMarker(element)
+        || element->hasTagName(buttonTag);
 }
 
-inline bool isSelectScopeMarker(ContainerNode* node)
+inline bool isSelectScopeMarker(Element* element)
 {
-    return !node->hasTagName(optgroupTag)
-        && !node->hasTagName(optionTag);
+    return !element->hasTagName(optgroupTag)
+        && !element->hasTagName(optionTag);
 }
 
 }
 
-HTMLElementStack::ElementRecord::ElementRecord(PassRefPtr<ContainerNode> node, PassOwnPtr<ElementRecord> next)
-    : m_node(node)
+HTMLElementStack::ElementRecord::ElementRecord(PassRefPtr<Element> element, PassOwnPtr<ElementRecord> next)
+    : m_element(element)
     , m_next(next)
 {
-    ASSERT(m_node);
+    ASSERT(m_element);
 }
 
 HTMLElementStack::ElementRecord::~ElementRecord()
@@ -145,9 +137,8 @@ HTMLElementStack::ElementRecord::~ElementRecord()
 void HTMLElementStack::ElementRecord::replaceElement(PassRefPtr<Element> element)
 {
     ASSERT(element);
-    ASSERT(!m_node || m_node->isElementNode());
     // FIXME: Should this call finishParsingChildren?
-    m_node = element;
+    m_element = element;
 }
 
 bool HTMLElementStack::ElementRecord::isAbove(ElementRecord* other) const
@@ -160,7 +151,7 @@ bool HTMLElementStack::ElementRecord::isAbove(ElementRecord* other) const
 }
 
 HTMLElementStack::HTMLElementStack()
-    : m_rootNode(0)
+    : m_htmlElement(0)
     , m_headElement(0)
     , m_bodyElement(0)
 {
@@ -180,7 +171,7 @@ bool HTMLElementStack::secondElementIsHTMLBodyElement() const
     // This is used the fragment case of <body> and <frameset> in the "in body"
     // insertion mode.
     // http://www.whatwg.org/specs/web-apps/current-work/multipage/tokenization.html#parsing-main-inbody
-    ASSERT(m_rootNode);
+    ASSERT(m_htmlElement);
     // If we have a body element, it must always be the second element on the
     // stack, as we always start with an html element, and any other element
     // would cause the implicit creation of a body element.
@@ -203,11 +194,11 @@ void HTMLElementStack::popHTMLBodyElement()
 
 void HTMLElementStack::popAll()
 {
-    m_rootNode = 0;
+    m_htmlElement = 0;
     m_headElement = 0;
     m_bodyElement = 0;
     while (m_top) {
-        topNode()->finishParsingChildren();
+        top()->finishParsingChildren();
         m_top = m_top->releaseNext();
     }
 }
@@ -255,21 +246,21 @@ void HTMLElementStack::popUntilPopped(Element* element)
 void HTMLElementStack::popUntilTableScopeMarker()
 {
     // http://www.whatwg.org/specs/web-apps/current-work/multipage/tokenization.html#clear-the-stack-back-to-a-table-context
-    while (!isTableScopeMarker(topNode()))
+    while (!isTableScopeMarker(top()))
         pop();
 }
 
 void HTMLElementStack::popUntilTableBodyScopeMarker()
 {
     // http://www.whatwg.org/specs/web-apps/current-work/multipage/tokenization.html#clear-the-stack-back-to-a-table-body-context
-    while (!isTableBodyScopeMarker(topNode()))
+    while (!isTableBodyScopeMarker(top()))
         pop();
 }
 
 void HTMLElementStack::popUntilTableRowScopeMarker()
 {
     // http://www.whatwg.org/specs/web-apps/current-work/multipage/tokenization.html#clear-the-stack-back-to-a-table-row-context
-    while (!isTableRowScopeMarker(topNode()))
+    while (!isTableRowScopeMarker(top()))
         pop();
 }
 
@@ -278,25 +269,14 @@ void HTMLElementStack::popUntilForeignContentScopeMarker()
     while (!isForeignContentScopeMarker(top()))
         pop();
 }
-    
-void HTMLElementStack::pushRootNode(PassRefPtr<ContainerNode> rootNode)
-{
-    ASSERT(rootNode->nodeType() == Node::DOCUMENT_FRAGMENT_NODE);
-    pushRootNodeCommon(rootNode);
-}
 
 void HTMLElementStack::pushHTMLHtmlElement(PassRefPtr<Element> element)
 {
+    ASSERT(!m_top); // <html> should always be the bottom of the stack.
     ASSERT(element->hasTagName(HTMLNames::htmlTag));
-    pushRootNodeCommon(element);
-}
-    
-void HTMLElementStack::pushRootNodeCommon(PassRefPtr<ContainerNode> rootNode)
-{
-    ASSERT(!m_top);
-    ASSERT(!m_rootNode);
-    m_rootNode = rootNode.get();
-    pushCommon(rootNode);
+    ASSERT(!m_htmlElement);
+    m_htmlElement = element.get();
+    pushCommon(element);
 }
 
 void HTMLElementStack::pushHTMLHeadElement(PassRefPtr<Element> element)
@@ -320,7 +300,7 @@ void HTMLElementStack::push(PassRefPtr<Element> element)
     ASSERT(!element->hasTagName(HTMLNames::htmlTag));
     ASSERT(!element->hasTagName(HTMLNames::headTag));
     ASSERT(!element->hasTagName(HTMLNames::bodyTag));
-    ASSERT(m_rootNode);
+    ASSERT(m_htmlElement);
     pushCommon(element);
 }
 
@@ -332,7 +312,7 @@ void HTMLElementStack::insertAbove(PassRefPtr<Element> element, ElementRecord* r
     ASSERT(!element->hasTagName(HTMLNames::htmlTag));
     ASSERT(!element->hasTagName(HTMLNames::headTag));
     ASSERT(!element->hasTagName(HTMLNames::bodyTag));
-    ASSERT(m_rootNode);
+    ASSERT(m_htmlElement);
     if (recordBelow == m_top) {
         push(element);
         return;
@@ -392,7 +372,7 @@ void HTMLElementStack::remove(Element* element)
 HTMLElementStack::ElementRecord* HTMLElementStack::find(Element* element) const
 {
     for (ElementRecord* pos = m_top.get(); pos; pos = pos->next()) {
-        if (pos->node() == element)
+        if (pos->element() == element)
             return pos;
     }
     return 0;
@@ -401,7 +381,7 @@ HTMLElementStack::ElementRecord* HTMLElementStack::find(Element* element) const
 HTMLElementStack::ElementRecord* HTMLElementStack::topmost(const AtomicString& tagName) const
 {
     for (ElementRecord* pos = m_top.get(); pos; pos = pos->next()) {
-        if (pos->node()->hasLocalName(tagName))
+        if (pos->element()->hasLocalName(tagName))
             return pos;
     }
     return 0;
@@ -417,14 +397,14 @@ bool HTMLElementStack::contains(const AtomicString& tagName) const
     return !!topmost(tagName);
 }
 
-template <bool isMarker(ContainerNode*)>
+template <bool isMarker(Element*)>
 bool inScopeCommon(HTMLElementStack::ElementRecord* top, const AtomicString& targetTag)
 {
     for (HTMLElementStack::ElementRecord* pos = top; pos; pos = pos->next()) {
-        ContainerNode* node = pos->node();
-        if (node->hasLocalName(targetTag))
+        Element* element = pos->element();
+        if (element->hasLocalName(targetTag))
             return true;
-        if (isMarker(node))
+        if (isMarker(element))
             return false;
     }
     ASSERT_NOT_REACHED(); // <html> is always on the stack and is a scope marker.
@@ -447,10 +427,11 @@ bool HTMLElementStack::hasOnlyHTMLElementsInScope() const
 bool HTMLElementStack::hasNumberedHeaderElementInScope() const
 {
     for (ElementRecord* record = m_top.get(); record; record = record->next()) {
-        if (isScopeMarker(record->node()))
-            return false;
-        if (isNumberedHeaderElement(record->element()))
+        Element* element = record->element();
+        if (isNumberedHeaderElement(element))
             return true;
+        if (isScopeMarker(element))
+            return false;
     }
     ASSERT_NOT_REACHED(); // <html> is always on the stack and is a scope marker.
     return false;
@@ -526,8 +507,8 @@ bool HTMLElementStack::inSelectScope(const QualifiedName& tagName) const
 
 Element* HTMLElementStack::htmlElement() const
 {
-    ASSERT(m_rootNode);
-    return toElement(m_rootNode);
+    ASSERT(m_htmlElement);
+    return m_htmlElement;
 }
 
 Element* HTMLElementStack::headElement() const
@@ -541,18 +522,12 @@ Element* HTMLElementStack::bodyElement() const
     ASSERT(m_bodyElement);
     return m_bodyElement;
 }
-    
-ContainerNode* HTMLElementStack::rootNode() const
-{
-    ASSERT(m_rootNode);
-    return m_rootNode;
-}
 
-void HTMLElementStack::pushCommon(PassRefPtr<ContainerNode> node)
+void HTMLElementStack::pushCommon(PassRefPtr<Element> element)
 {
-    ASSERT(m_rootNode);
-    m_top = adoptPtr(new ElementRecord(node, m_top.release()));
-    topNode()->beginParsingChildren();
+    ASSERT(m_htmlElement);
+    m_top = adoptPtr(new ElementRecord(element, m_top.release()));
+    top()->beginParsingChildren();
 }
 
 void HTMLElementStack::popCommon()
index a710932..ad8b941 100644 (file)
@@ -1,6 +1,5 @@
 /*
  * Copyright (C) 2010 Google, Inc. All Rights Reserved.
- * Copyright (C) 2011 Apple Inc. All rights reserved.
  *
  * Redistribution and use in source and binary forms, with or without
  * modification, are permitted provided that the following conditions
@@ -27,7 +26,6 @@
 #ifndef HTMLElementStack_h
 #define HTMLElementStack_h
 
-#include "Element.h"
 #include <wtf/Forward.h>
 #include <wtf/Noncopyable.h>
 #include <wtf/OwnPtr.h>
@@ -36,8 +34,6 @@
 
 namespace WebCore {
 
-class ContainerNode;
-class DocumentFragment;
 class Element;
 class QualifiedName;
 
@@ -54,8 +50,7 @@ public:
     public:
         ~ElementRecord(); // Public for ~PassOwnPtr()
     
-        Element* element() const { return toElement(m_node.get()); }
-        ContainerNode* node() const { return m_node.get(); }
+        Element* element() const { return m_element.get(); }
         void replaceElement(PassRefPtr<Element>);
 
         bool isAbove(ElementRecord*) const;
@@ -65,12 +60,12 @@ public:
     private:
         friend class HTMLElementStack;
 
-        ElementRecord(PassRefPtr<ContainerNode>, PassOwnPtr<ElementRecord>);
+        ElementRecord(PassRefPtr<Element>, PassOwnPtr<ElementRecord>);
 
         PassOwnPtr<ElementRecord> releaseNext() { return m_next.release(); }
         void setNext(PassOwnPtr<ElementRecord> next) { m_next = next; }
 
-        RefPtr<ContainerNode> m_node;
+        RefPtr<Element> m_element;
         OwnPtr<ElementRecord> m_next;
     };
 
@@ -81,12 +76,6 @@ public:
         ASSERT(m_top->element());
         return m_top->element();
     }
-    
-    ContainerNode* topNode() const
-    {
-        ASSERT(m_top->node());
-        return m_top->node();
-    }
 
     Element* oneBelowTop() const;
     ElementRecord* topRecord() const;
@@ -97,7 +86,6 @@ public:
     void insertAbove(PassRefPtr<Element>, ElementRecord*);
 
     void push(PassRefPtr<Element>);
-    void pushRootNode(PassRefPtr<ContainerNode>);
     void pushHTMLHtmlElement(PassRefPtr<Element>);
     void pushHTMLHeadElement(PassRefPtr<Element>);
     void pushHTMLBodyElement(PassRefPtr<Element>);
@@ -143,27 +131,24 @@ public:
     Element* htmlElement() const;
     Element* headElement() const;
     Element* bodyElement() const;
-    
-    ContainerNode* rootNode() const;
 
 #ifndef NDEBUG
     void show();
 #endif
 
 private:
-    void pushCommon(PassRefPtr<ContainerNode>);
-    void pushRootNodeCommon(PassRefPtr<ContainerNode>);
+    void pushCommon(PassRefPtr<Element>);
     void popCommon();
     void removeNonTopCommon(Element*);
 
     OwnPtr<ElementRecord> m_top;
 
-    // We remember the root node, <head> and <body> as they are pushed. Their
-    // ElementRecords keep them alive. The root node is never popped.
+    // We remember <html>, <head> and <body> as they are pushed.  Their
+    // ElementRecords keep them alive.  <html> is never popped.
     // FIXME: We don't currently require type-specific information about
     // these elements so we haven't yet bothered to plumb the types all the
     // way down through createElement, etc.
-    ContainerNode* m_rootNode;
+    Element* m_htmlElement;
     Element* m_headElement;
     Element* m_bodyElement;
 };
index 672979d..f0b196a 100644 (file)
@@ -1,6 +1,5 @@
 /*
  * Copyright (C) 2010 Google, Inc. All Rights Reserved.
- * Copyright (C) 2011 Apple Inc. All rights reserved.
  *
  * Redistribution and use in source and binary forms, with or without
  * modification, are permitted provided that the following conditions
@@ -123,8 +122,6 @@ bool isSpecialNode(Node* node)
         || node->hasTagName(SVGNames::descTag)
         || node->hasTagName(SVGNames::titleTag))
         return true;
-    if (node->nodeType() == Node::DOCUMENT_FRAGMENT_NODE)
-        return true;
     if (node->namespaceURI() != xhtmlNamespaceURI)
         return false;
     const AtomicString& tagName = node->localName();
@@ -378,9 +375,7 @@ HTMLTreeBuilder::HTMLTreeBuilder(HTMLDocumentParser* parser, DocumentFragment* f
     if (contextElement) {
         // Steps 4.2-4.6 of the HTML5 Fragment Case parsing algorithm:
         // http://www.whatwg.org/specs/web-apps/current-work/multipage/the-end.html#fragment-case
-        // For efficiency, we skip step 4.2 ("Let root be a new html element with no attributes")
-        // and instead use the DocumentFragment as a root node.
-        m_tree.openElements()->pushRootNode(fragment);
+        processFakeStartTag(htmlTag);
         resetInsertionModeAppropriately();
         m_tree.setForm(closestFormAncestor(contextElement));
     }
@@ -415,6 +410,19 @@ HTMLTreeBuilder::FragmentParsingContext::FragmentParsingContext(DocumentFragment
     ASSERT(!fragment->hasChildNodes());
 }
 
+void HTMLTreeBuilder::FragmentParsingContext::finished()
+{
+    if (!m_contextElement)
+        return;
+    
+    // The HTML5 spec says to return the children of the fragment's document
+    // element when there is a context element (10.4.7).
+    RefPtr<ContainerNode> documentElement = firstElementChild(m_fragment);
+    m_fragment->removeChildren();
+    ASSERT(documentElement);
+    m_fragment->takeAllChildrenFrom(documentElement.get());
+}
+
 HTMLTreeBuilder::FragmentParsingContext::~FragmentParsingContext()
 {
 }
@@ -566,12 +574,12 @@ void HTMLTreeBuilder::processIsindexStartTagForInBody(AtomicHTMLToken& token)
 
 namespace {
 
-bool isLi(const ContainerNode* element)
+bool isLi(const Element* element)
 {
     return element->hasTagName(liTag);
 }
 
-bool isDdOrDt(const ContainerNode* element)
+bool isDdOrDt(const Element* element)
 {
     return element->hasTagName(ddTag)
         || element->hasTagName(dtTag);
@@ -579,16 +587,15 @@ bool isDdOrDt(const ContainerNode* element)
 
 }
 
-template <bool shouldClose(const ContainerNode*)>
+template <bool shouldClose(const Element*)>
 void HTMLTreeBuilder::processCloseWhenNestedTag(AtomicHTMLToken& token)
 {
     m_framesetOk = false;
     HTMLElementStack::ElementRecord* nodeRecord = m_tree.openElements()->topRecord();
     while (1) {
-        ContainerNode* node = nodeRecord->node();
+        Element* node = nodeRecord->element();
         if (shouldClose(node)) {
-            ASSERT(node->isElementNode());
-            processFakeEndTag(toElement(node)->tagQName());
+            processFakeEndTag(node->tagQName());
             break;
         }
         if (isSpecialNode(node) && !node->hasTagName(addressTag) && !node->hasTagName(divTag) && !node->hasTagName(pTag))
@@ -779,7 +786,7 @@ void HTMLTreeBuilder::processStartTagForInBody(AtomicHTMLToken& token)
     }
     if (isNumberedHeaderTag(token.name())) {
         processFakePEndTagIfPInButtonScope();
-        if (isNumberedHeaderTag(m_tree.currentNode()->localName())) {
+        if (isNumberedHeaderTag(m_tree.currentElement()->localName())) {
             parseError(token);
             m_tree.openElements()->pop();
         }
@@ -971,7 +978,7 @@ void HTMLTreeBuilder::processStartTagForInBody(AtomicHTMLToken& token)
     if (token.name() == rpTag || token.name() == rtTag) {
         if (m_tree.openElements()->inScope(rubyTag.localName())) {
             m_tree.generateImpliedEndTags();
-            if (!m_tree.currentNode()->hasTagName(rubyTag)) {
+            if (!m_tree.currentElement()->hasTagName(rubyTag)) {
                 parseError(token);
                 m_tree.openElements()->popUntil(rubyTag.localName());
             }
@@ -1012,7 +1019,7 @@ void HTMLTreeBuilder::processStartTagForInBody(AtomicHTMLToken& token)
 
 bool HTMLTreeBuilder::processColgroupEndTagForInColumnGroup()
 {
-    if (m_tree.currentNode() == m_tree.openElements()->rootNode()) {
+    if (m_tree.currentElement() == m_tree.openElements()->htmlElement()) {
         ASSERT(isParsingFragment());
         // FIXME: parse error
         return false;
@@ -1108,7 +1115,7 @@ void HTMLTreeBuilder::processStartTagForInTable(AtomicHTMLToken& token)
 
 namespace {
 
-bool shouldProcessForeignContentUsingInBodyInsertionMode(AtomicHTMLToken& token, ContainerNode* currentElement)
+bool shouldProcessForeignContentUsingInBodyInsertionMode(AtomicHTMLToken& token, Element* currentElement)
 {
     ASSERT(token.type() == HTMLToken::StartTag);
     if (currentElement->hasTagName(MathMLNames::miTag)
@@ -1402,7 +1409,7 @@ void HTMLTreeBuilder::processStartTag(AtomicHTMLToken& token)
             return;
         }
         if (token.name() == optionTag) {
-            if (m_tree.currentNode()->hasTagName(optionTag)) {
+            if (m_tree.currentElement()->hasTagName(optionTag)) {
                 AtomicHTMLToken endOption(HTMLToken::EndTag, optionTag.localName());
                 processEndTag(endOption);
             }
@@ -1410,11 +1417,11 @@ void HTMLTreeBuilder::processStartTag(AtomicHTMLToken& token)
             return;
         }
         if (token.name() == optgroupTag) {
-            if (m_tree.currentNode()->hasTagName(optionTag)) {
+            if (m_tree.currentElement()->hasTagName(optionTag)) {
                 AtomicHTMLToken endOption(HTMLToken::EndTag, optionTag.localName());
                 processEndTag(endOption);
             }
-            if (m_tree.currentNode()->hasTagName(optgroupTag)) {
+            if (m_tree.currentElement()->hasTagName(optgroupTag)) {
                 AtomicHTMLToken endOptgroup(HTMLToken::EndTag, optgroupTag.localName());
                 processEndTag(endOptgroup);
             }
@@ -1536,20 +1543,20 @@ void HTMLTreeBuilder::processAnyOtherEndTagForInBody(AtomicHTMLToken& token)
     ASSERT(token.type() == HTMLToken::EndTag);
     HTMLElementStack::ElementRecord* record = m_tree.openElements()->topRecord();
     while (1) {
-        ContainerNode* node = record->node();
+        Element* node = record->element();
         if (node->hasLocalName(token.name())) {
             m_tree.generateImpliedEndTags();
-            if (!m_tree.currentNode()->hasLocalName(token.name())) {
+            if (!m_tree.currentElement()->hasLocalName(token.name())) {
                 parseError(token);
                 // FIXME: This is either a bug in the spec, or a bug in our
                 // implementation.  Filed a bug with HTML5:
                 // http://www.w3.org/Bugs/Public/show_bug.cgi?id=10080
                 // We might have already popped the node for the token in
                 // generateImpliedEndTags, just abort.
-                if (!m_tree.openElements()->contains(record->element()))
+                if (!m_tree.openElements()->contains(node))
                     return;
             }
-            m_tree.openElements()->popUntilPopped(record->element());
+            m_tree.openElements()->popUntilPopped(node);
             return;
         }
         if (isSpecialNode(node)) {
@@ -1609,7 +1616,7 @@ void HTMLTreeBuilder::callTheAdoptionAgency(AtomicHTMLToken& token)
         }
         // 4.
         ASSERT(furthestBlock->isAbove(formattingElementRecord));
-        ContainerNode* commonAncestor = formattingElementRecord->next()->node();
+        Element* commonAncestor = formattingElementRecord->next()->element();
         // 5.
         HTMLFormattingElementList::Bookmark bookmark = m_tree.activeFormattingElements()->bookmarkFor(formattingElement);
         // 6.
@@ -1661,9 +1668,7 @@ void HTMLTreeBuilder::callTheAdoptionAgency(AtomicHTMLToken& token)
             m_tree.fosterParent(lastNode->element());
         else {
             commonAncestor->parserAddChild(lastNode->element());
-            ASSERT(lastNode->node()->isElementNode());
-            ASSERT(lastNode->element()->parentNode());
-            if (lastNode->element()->parentNode()->attached() && !lastNode->element()->attached())
+            if (lastNode->element()->parentElement()->attached() && !lastNode->element()->attached())
                 lastNode->element()->lazyAttach();
         }
         // 8
@@ -1695,8 +1700,8 @@ void HTMLTreeBuilder::resetInsertionModeAppropriately()
     bool last = false;
     HTMLElementStack::ElementRecord* nodeRecord = m_tree.openElements()->topRecord();
     while (1) {
-        ContainerNode* node = nodeRecord->node();
-        if (node == m_tree.openElements()->rootNode()) {
+        Element* node = nodeRecord->element();
+        if (node == m_tree.openElements()->bottom()) {
             ASSERT(isParsingFragment());
             last = true;
             node = m_fragmentContext.contextElement();
@@ -1826,7 +1831,7 @@ void HTMLTreeBuilder::processEndTagForInCell(AtomicHTMLToken& token)
             return;
         }
         m_tree.generateImpliedEndTags();
-        if (!m_tree.currentNode()->hasLocalName(token.name()))
+        if (!m_tree.currentElement()->hasLocalName(token.name()))
             parseError(token);
         m_tree.openElements()->popUntilPopped(token.name());
         m_tree.activeFormattingElements()->clearToLastMarker();
@@ -1896,7 +1901,7 @@ void HTMLTreeBuilder::processEndTagForInBody(AtomicHTMLToken& token)
             return;
         }
         m_tree.generateImpliedEndTags();
-        if (!m_tree.currentNode()->hasLocalName(token.name()))
+        if (!m_tree.currentElement()->hasLocalName(token.name()))
             parseError(token);
         m_tree.openElements()->popUntilPopped(token.name());
         return;
@@ -1921,7 +1926,7 @@ void HTMLTreeBuilder::processEndTagForInBody(AtomicHTMLToken& token)
             return;
         }
         m_tree.generateImpliedEndTagsWithExclusion(token.name());
-        if (!m_tree.currentNode()->hasLocalName(token.name()))
+        if (!m_tree.currentElement()->hasLocalName(token.name()))
             parseError(token);
         m_tree.openElements()->popUntilPopped(token.name());
         return;
@@ -1932,7 +1937,7 @@ void HTMLTreeBuilder::processEndTagForInBody(AtomicHTMLToken& token)
             return;
         }
         m_tree.generateImpliedEndTagsWithExclusion(token.name());
-        if (!m_tree.currentNode()->hasLocalName(token.name()))
+        if (!m_tree.currentElement()->hasLocalName(token.name()))
             parseError(token);
         m_tree.openElements()->popUntilPopped(token.name());
         return;
@@ -1944,7 +1949,7 @@ void HTMLTreeBuilder::processEndTagForInBody(AtomicHTMLToken& token)
             return;
         }
         m_tree.generateImpliedEndTagsWithExclusion(token.name());
-        if (!m_tree.currentNode()->hasLocalName(token.name()))
+        if (!m_tree.currentElement()->hasLocalName(token.name()))
             parseError(token);
         m_tree.openElements()->popUntilPopped(token.name());
         return;
@@ -1955,7 +1960,7 @@ void HTMLTreeBuilder::processEndTagForInBody(AtomicHTMLToken& token)
             return;
         }
         m_tree.generateImpliedEndTags();
-        if (!m_tree.currentNode()->hasLocalName(token.name()))
+        if (!m_tree.currentElement()->hasLocalName(token.name()))
             parseError(token);
         m_tree.openElements()->popUntilNumberedHeaderElementPopped();
         return;
@@ -1972,7 +1977,7 @@ void HTMLTreeBuilder::processEndTagForInBody(AtomicHTMLToken& token)
             return;
         }
         m_tree.generateImpliedEndTags();
-        if (!m_tree.currentNode()->hasLocalName(token.name()))
+        if (!m_tree.currentElement()->hasLocalName(token.name()))
             parseError(token);
         m_tree.openElements()->popUntilPopped(token.name());
         m_tree.activeFormattingElements()->clearToLastMarker();
@@ -2216,7 +2221,7 @@ void HTMLTreeBuilder::processEndTag(AtomicHTMLToken& token)
     case InFramesetMode:
         ASSERT(insertionMode() == InFramesetMode);
         if (token.name() == framesetTag) {
-            if (m_tree.currentNode() == m_tree.openElements()->rootNode()) {
+            if (m_tree.currentElement() == m_tree.openElements()->htmlElement()) {
                 parseError(token);
                 return;
             }
@@ -2256,9 +2261,9 @@ void HTMLTreeBuilder::processEndTag(AtomicHTMLToken& token)
     case InSelectMode:
         ASSERT(insertionMode() == InSelectMode || insertionMode() == InSelectInTableMode);
         if (token.name() == optgroupTag) {
-            if (m_tree.currentNode()->hasTagName(optionTag) && m_tree.oneBelowTop()->hasTagName(optgroupTag))
+            if (m_tree.currentElement()->hasTagName(optionTag) && m_tree.oneBelowTop()->hasTagName(optgroupTag))
                 processFakeEndTag(optionTag);
-            if (m_tree.currentNode()->hasTagName(optgroupTag)) {
+            if (m_tree.currentElement()->hasTagName(optgroupTag)) {
                 m_tree.openElements()->pop();
                 return;
             }
@@ -2289,32 +2294,23 @@ void HTMLTreeBuilder::processEndTag(AtomicHTMLToken& token)
         processEndTag(token);
         break;
     case InForeignContentMode:
-        if (token.name() == SVGNames::scriptTag && m_tree.currentNode()->hasTagName(SVGNames::scriptTag)) {
+        if (token.name() == SVGNames::scriptTag && m_tree.currentElement()->hasTagName(SVGNames::scriptTag)) {
             notImplemented();
             return;
         }
-        if (m_tree.currentNode()->namespaceURI() != xhtmlNamespaceURI) {
+        if (m_tree.currentElement()->namespaceURI() != xhtmlNamespaceURI) {
             // FIXME: This code just wants an Element* iterator, instead of an ElementRecord*
             HTMLElementStack::ElementRecord* nodeRecord = m_tree.openElements()->topRecord();
-            if (!nodeRecord->node()->hasLocalName(token.name()))
+            if (!nodeRecord->element()->hasLocalName(token.name()))
                 parseError(token);
             while (1) {
-                if (nodeRecord->node()->hasLocalName(token.name())) {
+                if (nodeRecord->element()->hasLocalName(token.name())) {
                     m_tree.openElements()->popUntilPopped(nodeRecord->element());
                     resetForeignInsertionMode();
                     return;
                 }
                 nodeRecord = nodeRecord->next();
-                
-                // Fragments containing only foreign content will not have a
-                // node with the XHTML namespace URI, so we should stop walking
-                // the element stack when we encounter the DocumentFragment itself.
-                if (nodeRecord->node()->nodeType() == Node::DOCUMENT_FRAGMENT_NODE) {
-                    ASSERT(isParsingFragment());
-                    break;
-                }
-                
-                if (nodeRecord->node()->namespaceURI() == xhtmlNamespaceURI)
+                if (nodeRecord->element()->namespaceURI() == xhtmlNamespaceURI)
                     break;
             }
         }
@@ -2613,11 +2609,11 @@ void HTMLTreeBuilder::processEndOfFile(AtomicHTMLToken& token)
     case InSelectInTableMode:
     case InSelectMode:
         ASSERT(insertionMode() == InSelectMode || insertionMode() == InSelectInTableMode || insertionMode() == InTableMode || insertionMode() == InFramesetMode || insertionMode() == InTableBodyMode);
-        if (m_tree.currentNode() != m_tree.openElements()->rootNode())
+        if (m_tree.currentElement() != m_tree.openElements()->htmlElement())
             parseError(token);
         break;
     case InColumnGroupMode:
-        if (m_tree.currentNode() == m_tree.openElements()->rootNode()) {
+        if (m_tree.currentElement() == m_tree.openElements()->htmlElement()) {
             ASSERT(isParsingFragment());
             return; // FIXME: Should we break here instead of returning?
         }
@@ -2646,7 +2642,7 @@ void HTMLTreeBuilder::processEndOfFile(AtomicHTMLToken& token)
         processEndOfFile(token);
         return;
     }
-    ASSERT(m_tree.currentNode());
+    ASSERT(m_tree.openElements()->top());
     m_tree.openElements()->popAll();
 }
 
@@ -2798,10 +2794,12 @@ void HTMLTreeBuilder::processScriptStartTag(AtomicHTMLToken& token)
 
 void HTMLTreeBuilder::finished()
 {
-    if (isParsingFragment())
-        return;
-    
     ASSERT(m_document);
+    if (isParsingFragment()) {
+        m_fragmentContext.finished();
+        return;
+    }
+
     // Warning, this may detach the parser. Do not do anything else after this.
     m_document->finishedParsing();
 }
index 5bdc44b..0cec667 100644 (file)
@@ -1,6 +1,5 @@
 /*
  * Copyright (C) 2010 Google, Inc. All Rights Reserved.
- * Copyright (C) 2011 Apple Inc. All rights reserved.
  *
  * Redistribution and use in source and binary forms, with or without
  * modification, are permitted provided that the following conditions
@@ -179,7 +178,7 @@ private:
 
     void closeTheCell();
 
-    template <bool shouldClose(const ContainerNode*)>
+    template <bool shouldClose(const Element*)>
     void processCloseWhenNestedTag(AtomicHTMLToken&);
 
     bool m_framesetOk;
@@ -216,6 +215,8 @@ private:
         Element* contextElement() const { ASSERT(m_fragment); return m_contextElement; }
         FragmentScriptingPermission scriptingPermission() const { ASSERT(m_fragment); return m_scriptingPermission; }
 
+        void finished();
+
     private:
         DocumentFragment* m_fragment;
         Element* m_contextElement;