Changeset 62599 in webkit


Ignore:
Timestamp:
Jul 6, 2010 3:51:18 PM (14 years ago)
Author:
abarth@webkit.org
Message:

2010-07-06 Adam Barth <abarth@webkit.org>

Reviewed by Eric Seidel.

Factor HTMLConstructionSite out of HTMLTreeBuilder
https://bugs.webkit.org/show_bug.cgi?id=41716

The HTMLContructionSite is the model object on which the
HTMLTreeBuilder (a controller) acts.

No behavior change. I'll move this class into its own file in a
followup patch.

  • html/HTMLFormattingElementList.h: (WebCore::HTMLFormattingElementList::at):
  • html/HTMLTreeBuilder.cpp: (WebCore::HTMLTreeBuilder::HTMLTreeBuilder): (WebCore::HTMLConstructionSite::HTMLConstructionSite): (WebCore::HTMLTreeBuilder::passTokenToLegacyParser): (WebCore::HTMLTreeBuilder::processDoctypeToken): (WebCore::HTMLConstructionSite::insertHTMLHtmlStartTagBeforeHTML): (WebCore::HTMLConstructionSite::mergeAttributesFromTokenIntoElement): (WebCore::HTMLConstructionSite::insertHTMLHtmlStartTagInBody): (WebCore::HTMLConstructionSite::insertHTMLBodyStartTagInBody): (WebCore::HTMLTreeBuilder::processFakePEndTagIfPInScope): (WebCore::HTMLTreeBuilder::processIsindexStartTagForInBody): (WebCore::HTMLTreeBuilder::processStartTagForInBody): (WebCore::HTMLTreeBuilder::processColgroupEndTagForInColumnGroup): (WebCore::HTMLTreeBuilder::closeTheCell): (WebCore::HTMLTreeBuilder::processStartTagForInTable): (WebCore::HTMLTreeBuilder::processStartTag): (WebCore::HTMLTreeBuilder::processBodyEndTagForInBody): (WebCore::HTMLTreeBuilder::processAnyOtherEndTagForInBody): (WebCore::HTMLTreeBuilder::furthestBlockForFormattingElement): (WebCore::HTMLTreeBuilder::findFosterParentFor): (WebCore::HTMLTreeBuilder::callTheAdoptionAgency): (WebCore::HTMLTreeBuilder::resetInsertionModeAppropriately): (WebCore::HTMLTreeBuilder::processEndTagForInBody): (WebCore::HTMLTreeBuilder::processCaptionEndTagForInCaption): (WebCore::HTMLTreeBuilder::processTrEndTagForInRow): (WebCore::HTMLTreeBuilder::processEndTagForInTable): (WebCore::HTMLTreeBuilder::processEndTag): (WebCore::HTMLTreeBuilder::processComment): (WebCore::HTMLTreeBuilder::processCharacter): (WebCore::HTMLTreeBuilder::processEndOfFile): (WebCore::HTMLTreeBuilder::processDefaultForBeforeHTMLMode): (WebCore::HTMLTreeBuilder::processStartTagForInHead): (WebCore::HTMLConstructionSite::insertDoctype): (WebCore::HTMLConstructionSite::insertComment): (WebCore::HTMLConstructionSite::insertCommentOnDocument): (WebCore::HTMLConstructionSite::insertCommentOnHTMLHtmlElement): (WebCore::HTMLConstructionSite::createElementAndAttachToCurrent): (WebCore::HTMLConstructionSite::insertHTMLHtmlElement): (WebCore::HTMLConstructionSite::insertHTMLHeadElement): (WebCore::HTMLConstructionSite::insertHTMLBodyElement): (WebCore::HTMLConstructionSite::insertElement): (WebCore::HTMLConstructionSite::insertSelfClosingElement): (WebCore::HTMLConstructionSite::insertFormattingElement): (WebCore::HTMLTreeBuilder::processGenericRCDATAStartTag): (WebCore::HTMLTreeBuilder::processGenericRawTextStartTag): (WebCore::HTMLConstructionSite::insertScriptElement): (WebCore::HTMLTreeBuilder::processScriptStartTag): (WebCore::HTMLConstructionSite::insertTextNode): (WebCore::HTMLConstructionSite::createElement): (WebCore::HTMLTreeBuilder::indexOfFirstUnopenFormattingElement): (WebCore::HTMLTreeBuilder::reconstructTheActiveFormattingElements): (WebCore::HTMLTreeBuilder::generateImpliedEndTagsWithExclusion): (WebCore::HTMLTreeBuilder::generateImpliedEndTags):
  • html/HTMLTreeBuilder.h: (WebCore::HTMLConstructionSite::currentElement): (WebCore::HTMLConstructionSite::openElements): (WebCore::HTMLConstructionSite::activeFormattingElements): (WebCore::HTMLConstructionSite::head): (WebCore::HTMLConstructionSite::form): (WebCore::HTMLConstructionSite::releaseForm): (WebCore::HTMLConstructionSite::setForm): (WebCore::HTMLConstructionSite::fragmentScriptingPermission): (WebCore::HTMLConstructionSite::attach):
Location:
trunk/WebCore
Files:
4 edited

Legend:

Unmodified
Added
Removed
  • trunk/WebCore/ChangeLog

    r62598 r62599  
     12010-07-06  Adam Barth  <abarth@webkit.org>
     2
     3        Reviewed by Eric Seidel.
     4
     5        Factor HTMLConstructionSite out of HTMLTreeBuilder
     6        https://bugs.webkit.org/show_bug.cgi?id=41716
     7
     8        The HTMLContructionSite is the model object on which the
     9        HTMLTreeBuilder (a controller) acts.
     10
     11        No behavior change.  I'll move this class into its own file in a
     12        followup patch.
     13
     14        * html/HTMLFormattingElementList.h:
     15        (WebCore::HTMLFormattingElementList::at):
     16        * html/HTMLTreeBuilder.cpp:
     17        (WebCore::HTMLTreeBuilder::HTMLTreeBuilder):
     18        (WebCore::HTMLConstructionSite::HTMLConstructionSite):
     19        (WebCore::HTMLTreeBuilder::passTokenToLegacyParser):
     20        (WebCore::HTMLTreeBuilder::processDoctypeToken):
     21        (WebCore::HTMLConstructionSite::insertHTMLHtmlStartTagBeforeHTML):
     22        (WebCore::HTMLConstructionSite::mergeAttributesFromTokenIntoElement):
     23        (WebCore::HTMLConstructionSite::insertHTMLHtmlStartTagInBody):
     24        (WebCore::HTMLConstructionSite::insertHTMLBodyStartTagInBody):
     25        (WebCore::HTMLTreeBuilder::processFakePEndTagIfPInScope):
     26        (WebCore::HTMLTreeBuilder::processIsindexStartTagForInBody):
     27        (WebCore::HTMLTreeBuilder::processStartTagForInBody):
     28        (WebCore::HTMLTreeBuilder::processColgroupEndTagForInColumnGroup):
     29        (WebCore::HTMLTreeBuilder::closeTheCell):
     30        (WebCore::HTMLTreeBuilder::processStartTagForInTable):
     31        (WebCore::HTMLTreeBuilder::processStartTag):
     32        (WebCore::HTMLTreeBuilder::processBodyEndTagForInBody):
     33        (WebCore::HTMLTreeBuilder::processAnyOtherEndTagForInBody):
     34        (WebCore::HTMLTreeBuilder::furthestBlockForFormattingElement):
     35        (WebCore::HTMLTreeBuilder::findFosterParentFor):
     36        (WebCore::HTMLTreeBuilder::callTheAdoptionAgency):
     37        (WebCore::HTMLTreeBuilder::resetInsertionModeAppropriately):
     38        (WebCore::HTMLTreeBuilder::processEndTagForInBody):
     39        (WebCore::HTMLTreeBuilder::processCaptionEndTagForInCaption):
     40        (WebCore::HTMLTreeBuilder::processTrEndTagForInRow):
     41        (WebCore::HTMLTreeBuilder::processEndTagForInTable):
     42        (WebCore::HTMLTreeBuilder::processEndTag):
     43        (WebCore::HTMLTreeBuilder::processComment):
     44        (WebCore::HTMLTreeBuilder::processCharacter):
     45        (WebCore::HTMLTreeBuilder::processEndOfFile):
     46        (WebCore::HTMLTreeBuilder::processDefaultForBeforeHTMLMode):
     47        (WebCore::HTMLTreeBuilder::processStartTagForInHead):
     48        (WebCore::HTMLConstructionSite::insertDoctype):
     49        (WebCore::HTMLConstructionSite::insertComment):
     50        (WebCore::HTMLConstructionSite::insertCommentOnDocument):
     51        (WebCore::HTMLConstructionSite::insertCommentOnHTMLHtmlElement):
     52        (WebCore::HTMLConstructionSite::createElementAndAttachToCurrent):
     53        (WebCore::HTMLConstructionSite::insertHTMLHtmlElement):
     54        (WebCore::HTMLConstructionSite::insertHTMLHeadElement):
     55        (WebCore::HTMLConstructionSite::insertHTMLBodyElement):
     56        (WebCore::HTMLConstructionSite::insertElement):
     57        (WebCore::HTMLConstructionSite::insertSelfClosingElement):
     58        (WebCore::HTMLConstructionSite::insertFormattingElement):
     59        (WebCore::HTMLTreeBuilder::processGenericRCDATAStartTag):
     60        (WebCore::HTMLTreeBuilder::processGenericRawTextStartTag):
     61        (WebCore::HTMLConstructionSite::insertScriptElement):
     62        (WebCore::HTMLTreeBuilder::processScriptStartTag):
     63        (WebCore::HTMLConstructionSite::insertTextNode):
     64        (WebCore::HTMLConstructionSite::createElement):
     65        (WebCore::HTMLTreeBuilder::indexOfFirstUnopenFormattingElement):
     66        (WebCore::HTMLTreeBuilder::reconstructTheActiveFormattingElements):
     67        (WebCore::HTMLTreeBuilder::generateImpliedEndTagsWithExclusion):
     68        (WebCore::HTMLTreeBuilder::generateImpliedEndTags):
     69        * html/HTMLTreeBuilder.h:
     70        (WebCore::HTMLConstructionSite::currentElement):
     71        (WebCore::HTMLConstructionSite::openElements):
     72        (WebCore::HTMLConstructionSite::activeFormattingElements):
     73        (WebCore::HTMLConstructionSite::head):
     74        (WebCore::HTMLConstructionSite::form):
     75        (WebCore::HTMLConstructionSite::releaseForm):
     76        (WebCore::HTMLConstructionSite::setForm):
     77        (WebCore::HTMLConstructionSite::fragmentScriptingPermission):
     78        (WebCore::HTMLConstructionSite::attach):
     79
    1802010-07-06  Gustavo Noronha Silva  <gustavo.noronha@collabora.co.uk>
    281
  • trunk/WebCore/html/HTMLFormattingElementList.h

    r62537 r62599  
    103103    void clearToLastMarker();
    104104
    105     const Entry& operator[](size_t i) const { return m_entries[i]; }
    106     Entry& operator[](size_t i) { return m_entries[i]; }
     105    const Entry& at(size_t i) const { return m_entries[i]; }
     106    Entry& at(size_t i) { return m_entries[i]; }
    107107
    108108private:
  • trunk/WebCore/html/HTMLTreeBuilder.cpp

    r62593 r62599  
    2121 * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
    2222 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
    23  * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 
     23 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
    2424 */
    2525
     
    208208    : m_framesetOk(true)
    209209    , m_document(document)
     210    , m_tree(document, FragmentScriptingAllowed)
    210211    , m_reportErrors(reportErrors)
    211212    , m_isPaused(false)
     
    227228    : m_framesetOk(true)
    228229    , m_document(fragment->document())
     230    , m_tree(fragment->document(), scriptingPermission)
    229231    , m_reportErrors(false) // FIXME: Why not report errors in fragments?
    230232    , m_isPaused(false)
     
    238240    , m_fragmentScriptingPermission(scriptingPermission)
    239241    , m_isParsingFragment(true)
     242{
     243}
     244
     245template<typename ChildType>
     246PassRefPtr<ChildType> HTMLConstructionSite::attach(Node* parent, PassRefPtr<ChildType> prpChild)
     247{
     248    RefPtr<ChildType> child = prpChild;
     249    parent->parserAddChild(child);
     250    // It's slightly unfortunate that we need to hold a reference to child
     251    // here to call attach().  We should investigate whether we can rely on
     252    // |parent| to hold a ref at this point.  In the common case (at least
     253    // for elements), however, we'll get to use this ref in the stack of
     254    // open elements.
     255    child->attach();
     256    return child.release();
     257}
     258
     259HTMLConstructionSite::HTMLConstructionSite(Document* document, FragmentScriptingPermission scriptingPermission)
     260    : m_document(document)
     261    , m_fragmentScriptingPermission(scriptingPermission)
    240262{
    241263}
     
    418440    ASSERT(token.type() == HTMLToken::DOCTYPE);
    419441    if (insertionMode() == InitialMode) {
    420         insertDoctype(token);
     442        m_tree.insertDoctype(token);
    421443        return;
    422444    }
     
    424446}
    425447
    426 void HTMLTreeBuilder::insertHTMLStartTagBeforeHTML(AtomicHTMLToken& token)
     448void HTMLConstructionSite::insertHTMLHtmlStartTagBeforeHTML(AtomicHTMLToken& token)
    427449{
    428450    RefPtr<Element> element = HTMLHtmlElement::create(m_document);
     
    431453}
    432454
    433 void HTMLTreeBuilder::mergeAttributesFromTokenIntoElement(AtomicHTMLToken& token, Element* element)
     455void HTMLConstructionSite::mergeAttributesFromTokenIntoElement(AtomicHTMLToken& token, Element* element)
    434456{
    435457    if (!token.attributes())
     
    444466}
    445467
    446 void HTMLTreeBuilder::insertHTMLStartTagInBody(AtomicHTMLToken& token)
    447 {
    448     parseError(token);
     468void HTMLConstructionSite::insertHTMLHtmlStartTagInBody(AtomicHTMLToken& token)
     469{
     470    // FIXME: parse error
    449471    mergeAttributesFromTokenIntoElement(token, m_openElements.htmlElement());
     472}
     473
     474void HTMLConstructionSite::insertHTMLBodyStartTagInBody(AtomicHTMLToken& token)
     475{
     476    // FIXME: parse error
     477    notImplemented(); // fragment case
     478    mergeAttributesFromTokenIntoElement(token, m_openElements.bodyElement());
    450479}
    451480
     
    472501void HTMLTreeBuilder::processFakePEndTagIfPInScope()
    473502{
    474     if (!m_openElements.inScope(pTag.localName()))
     503    if (!m_tree.openElements()->inScope(pTag.localName()))
    475504        return;
    476505    AtomicHTMLToken endP(HTMLToken::EndTag, pTag.localName());
     
    499528    ASSERT(token.name() == isindexTag);
    500529    parseError(token);
    501     if (m_formElement)
     530    if (m_tree.form())
    502531        return;
    503532    notImplemented(); // Acknowledge self-closing flag
     
    505534    Attribute* actionAttribute = token.getAttributeItem(actionAttr);
    506535    if (actionAttribute) {
    507         ASSERT(currentElement()->hasTagName(formTag));
    508         currentElement()->setAttribute(actionAttr, actionAttribute->value());
     536        ASSERT(m_tree.currentElement()->hasTagName(formTag));
     537        m_tree.currentElement()->setAttribute(actionAttr, actionAttribute->value());
    509538    }
    510539    processFakeStartTag(hrTag);
     
    526555    ASSERT(token.type() == HTMLToken::StartTag);
    527556    if (token.name() == htmlTag) {
    528         insertHTMLStartTagInBody(token);
     557        m_tree.insertHTMLHtmlStartTagInBody(token);
    529558        return;
    530559    }
     
    535564    }
    536565    if (token.name() == bodyTag) {
    537         parseError(token);
    538         notImplemented(); // fragment case
    539         mergeAttributesFromTokenIntoElement(token, m_openElements.bodyElement());
     566        m_tree.insertHTMLBodyStartTagInBody(token);
    540567        return;
    541568    }
     
    546573            return;
    547574        ExceptionCode ec = 0;
    548         m_openElements.bodyElement()->remove(ec);
     575        m_tree.openElements()->bodyElement()->remove(ec);
    549576        ASSERT(!ec);
    550         m_openElements.popUntil(m_openElements.bodyElement());
    551         m_openElements.popHTMLBodyElement();
    552         ASSERT(m_openElements.top() == m_openElements.htmlElement());
    553         insertElement(token);
     577        m_tree.openElements()->popUntil(m_tree.openElements()->bodyElement());
     578        m_tree.openElements()->popHTMLBodyElement();
     579        ASSERT(m_tree.openElements()->top() == m_tree.openElements()->htmlElement());
     580        m_tree.insertElement(token);
    554581        m_insertionMode = InFramesetMode;
    555582        return;
     
    557584    if (token.name() == addressTag || token.name() == articleTag || token.name() == asideTag || token.name() == blockquoteTag || token.name() == centerTag || token.name() == "details" || token.name() == dirTag || token.name() == divTag || token.name() == dlTag || token.name() == fieldsetTag || token.name() == "figure" || token.name() == footerTag || token.name() == headerTag || token.name() == hgroupTag || token.name() == menuTag || token.name() == navTag || token.name() == olTag || token.name() == pTag || token.name() == sectionTag || token.name() == ulTag) {
    558585        processFakePEndTagIfPInScope();
    559         insertElement(token);
     586        m_tree.insertElement(token);
    560587        return;
    561588    }
    562589    if (isNumberedHeaderTag(token.name())) {
    563590        processFakePEndTagIfPInScope();
    564         if (isNumberedHeaderTag(currentElement()->localName())) {
    565             parseError(token); 
    566             m_openElements.pop();
    567         } 
    568         insertElement(token);
     591        if (isNumberedHeaderTag(m_tree.currentElement()->localName())) {
     592            parseError(token);
     593            m_tree.openElements()->pop();
     594        }
     595        m_tree.insertElement(token);
    569596        return;
    570597    }
    571598    if (token.name() == preTag || token.name() == listingTag) {
    572599        processFakePEndTagIfPInScope();
    573         insertElement(token);
     600        m_tree.insertElement(token);
    574601        m_tokenizer->skipLeadingNewLineForListing();
    575602        m_framesetOk = false;
     
    579606        notImplemented();
    580607        processFakePEndTagIfPInScope();
    581         insertElement(token);
    582         m_formElement = currentElement();
     608        m_tree.insertElement(token);
     609        m_tree.setForm(m_tree.currentElement());
    583610        return;
    584611    }
     
    586613        notImplemented();
    587614        processFakePEndTagIfPInScope();
    588         insertElement(token);
     615        m_tree.insertElement(token);
    589616        return;
    590617    }
     
    592619        notImplemented();
    593620        processFakePEndTagIfPInScope();
    594         insertElement(token);
     621        m_tree.insertElement(token);
    595622        return;
    596623    }
    597624    if (token.name() == plaintextTag) {
    598625        processFakePEndTagIfPInScope();
    599         insertElement(token);
     626        m_tree.insertElement(token);
    600627        m_tokenizer->setState(HTMLTokenizer::PLAINTEXTState);
    601628        return;
     
    603630    if (token.name() == buttonTag) {
    604631        notImplemented();
    605         reconstructTheActiveFormattingElements();
    606         insertElement(token);
     632        m_tree.reconstructTheActiveFormattingElements();
     633        m_tree.insertElement(token);
    607634        m_framesetOk = false;
    608635        return;
    609636    }
    610637    if (token.name() == aTag) {
    611         Element* activeATag = m_activeFormattingElements.closestElementInScopeWithName(aTag.localName());
     638        Element* activeATag = m_tree.activeFormattingElements()->closestElementInScopeWithName(aTag.localName());
    612639        if (activeATag) {
    613640            parseError(token);
    614641            processFakeEndTag(aTag);
    615             m_activeFormattingElements.remove(activeATag);
    616             if (m_openElements.contains(activeATag))
    617                 m_openElements.remove(activeATag);
    618         }
    619         reconstructTheActiveFormattingElements();
    620         insertFormattingElement(token);
     642            m_tree.activeFormattingElements()->remove(activeATag);
     643            if (m_tree.openElements()->contains(activeATag))
     644                m_tree.openElements()->remove(activeATag);
     645        }
     646        m_tree.reconstructTheActiveFormattingElements();
     647        m_tree.insertFormattingElement(token);
    621648        return;
    622649    }
    623650    if (isNonAnchorFormattingTag(token.name())) {
    624         reconstructTheActiveFormattingElements();
    625         insertFormattingElement(token);
     651        m_tree.reconstructTheActiveFormattingElements();
     652        m_tree.insertFormattingElement(token);
    626653        return;
    627654    }
    628655    if (token.name() == nobrTag) {
    629         reconstructTheActiveFormattingElements();
    630         notImplemented();
    631         insertFormattingElement(token);
     656        m_tree.reconstructTheActiveFormattingElements();
     657        notImplemented();
     658        m_tree.insertFormattingElement(token);
    632659        return;
    633660    }
    634661    if (token.name() == appletTag || token.name() == marqueeTag || token.name() == objectTag) {
    635         reconstructTheActiveFormattingElements();
    636         insertElement(token);
    637         m_activeFormattingElements.appendMarker();
     662        m_tree.reconstructTheActiveFormattingElements();
     663        m_tree.insertElement(token);
     664        m_tree.activeFormattingElements()->appendMarker();
    638665        m_framesetOk = false;
    639666        return;
     
    641668    if (token.name() == tableTag) {
    642669        notImplemented();
    643         insertElement(token);
     670        m_tree.insertElement(token);
    644671        m_framesetOk = false;
    645672        m_insertionMode = InTableMode;
     
    653680    }
    654681    if (token.name() == areaTag || token.name() == basefontTag || token.name() == "bgsound" || token.name() == brTag || token.name() == embedTag || token.name() == imgTag || token.name() == inputTag || token.name() == keygenTag || token.name() == wbrTag) {
    655         reconstructTheActiveFormattingElements();
    656         insertSelfClosingElement(token);
     682        m_tree.reconstructTheActiveFormattingElements();
     683        m_tree.insertSelfClosingElement(token);
    657684        m_framesetOk = false;
    658685        return;
    659686    }
    660687    if (token.name() == paramTag || token.name() == sourceTag || token.name() == "track") {
    661         insertSelfClosingElement(token);
     688        m_tree.insertSelfClosingElement(token);
    662689        return;
    663690    }
    664691    if (token.name() == hrTag) {
    665692        processFakePEndTagIfPInScope();
    666         insertSelfClosingElement(token);
     693        m_tree.insertSelfClosingElement(token);
    667694        m_framesetOk = false;
    668695        return;
     
    673700    }
    674701    if (token.name() == textareaTag) {
    675         insertElement(token);
     702        m_tree.insertElement(token);
    676703        m_tokenizer->skipLeadingNewLineForListing();
    677704        m_tokenizer->setState(HTMLTokenizer::RCDATAState);
     
    683710    if (token.name() == xmpTag) {
    684711        processFakePEndTagIfPInScope();
    685         reconstructTheActiveFormattingElements();
     712        m_tree.reconstructTheActiveFormattingElements();
    686713        m_framesetOk = false;
    687         insertGenericRawTextElement(token);
     714        processGenericRawTextStartTag(token);
    688715        return;
    689716    }
    690717    if (token.name() == iframeTag) {
    691718        m_framesetOk = false;
    692         insertGenericRawTextElement(token);
     719        processGenericRawTextStartTag(token);
    693720        return;
    694721    }
    695722    if (token.name() == noembedTag) {
    696         insertGenericRawTextElement(token);
     723        processGenericRawTextStartTag(token);
    697724        return;
    698725    }
    699726    if (token.name() == noscriptTag && isScriptingFlagEnabled(m_document->frame())) {
    700         insertGenericRawTextElement(token);
     727        processGenericRawTextStartTag(token);
    701728        return;
    702729    }
    703730    if (token.name() == selectTag) {
    704         reconstructTheActiveFormattingElements();
    705         insertElement(token);
     731        m_tree.reconstructTheActiveFormattingElements();
     732        m_tree.insertElement(token);
    706733        m_framesetOk = false;
    707734        if (m_insertionMode == InTableMode || m_insertionMode == InCaptionMode || m_insertionMode == InColumnGroupMode || m_insertionMode == InTableBodyMode || m_insertionMode == InRowMode || m_insertionMode == InCellMode)
     
    712739    }
    713740    if (token.name() == optgroupTag || token.name() == optionTag) {
    714         if (m_openElements.inScope(optionTag.localName())) {
     741        if (m_tree.openElements()->inScope(optionTag.localName())) {
    715742            AtomicHTMLToken endOption(HTMLToken::EndTag, optionTag.localName());
    716743            processEndTag(endOption);
    717744        }
    718         reconstructTheActiveFormattingElements();
    719         insertElement(token);
     745        m_tree.reconstructTheActiveFormattingElements();
     746        m_tree.insertElement(token);
    720747        return;
    721748    }
    722749    if (token.name() == rpTag || token.name() == rtTag) {
    723         if (m_openElements.inScope(rubyTag.localName())) {
    724             generateImpliedEndTags();
    725             if (!currentElement()->hasTagName(rubyTag)) {
     750        if (m_tree.openElements()->inScope(rubyTag.localName())) {
     751            m_tree.generateImpliedEndTags();
     752            if (!m_tree.currentElement()->hasTagName(rubyTag)) {
    726753                parseError(token);
    727                 m_openElements.popUntil(rubyTag.localName());
     754                m_tree.openElements()->popUntil(rubyTag.localName());
    728755            }
    729756        }
    730         insertElement(token);
     757        m_tree.insertElement(token);
    731758        return;
    732759    }
     
    743770        return;
    744771    }
    745     reconstructTheActiveFormattingElements();
    746     insertElement(token);
     772    m_tree.reconstructTheActiveFormattingElements();
     773    m_tree.insertElement(token);
    747774}
    748775
    749776bool HTMLTreeBuilder::processColgroupEndTagForInColumnGroup()
    750777{
    751     if (currentElement() == m_openElements.htmlElement()) {
     778    if (m_tree.currentElement() == m_tree.openElements()->htmlElement()) {
    752779        ASSERT(m_isParsingFragment);
    753780        // FIXME: parse error
    754781        return false;
    755782    }
    756     m_openElements.pop();
     783    m_tree.openElements()->pop();
    757784    m_insertionMode = InTableMode;
    758785    return true;
     
    763790{
    764791    ASSERT(insertionMode() == InCellMode);
    765     if (m_openElements.inScope(tdTag)) {
    766         ASSERT(!m_openElements.inScope(thTag));
     792    if (m_tree.openElements()->inScope(tdTag)) {
     793        ASSERT(!m_tree.openElements()->inScope(thTag));
    767794        processFakeEndTag(tdTag);
    768795        return;
    769796    }
    770     ASSERT(m_openElements.inScope(thTag));
     797    ASSERT(m_tree.openElements()->inScope(thTag));
    771798    processFakeEndTag(thTag);
    772799    ASSERT(insertionMode() == InRowMode);
     
    777804    ASSERT(token.type() == HTMLToken::StartTag);
    778805    if (token.name() == captionTag) {
    779         m_openElements.popUntilTableScopeMarker();
    780         m_activeFormattingElements.appendMarker();
    781         insertElement(token);
     806        m_tree.openElements()->popUntilTableScopeMarker();
     807        m_tree.activeFormattingElements()->appendMarker();
     808        m_tree.insertElement(token);
    782809        m_insertionMode = InCaptionMode;
    783810        return;
    784811    }
    785812    if (token.name() == colgroupTag) {
    786         m_openElements.popUntilTableScopeMarker();
    787         insertElement(token);
     813        m_tree.openElements()->popUntilTableScopeMarker();
     814        m_tree.insertElement(token);
    788815        m_insertionMode = InColumnGroupMode;
    789816        return;
     
    796823    }
    797824    if (isTableBodyContextTag(token.name())) {
    798         m_openElements.popUntilTableScopeMarker();
    799         insertElement(token);
     825        m_tree.openElements()->popUntilTableScopeMarker();
     826        m_tree.insertElement(token);
    800827        m_insertionMode = InTableBodyMode;
    801828        return;
     
    821848    if (token.name() == formTag) {
    822849        parseError(token);
    823         if (m_formElement)
    824             return;
    825         insertSelfClosingElement(token);
     850        if (m_tree.form())
     851            return;
     852        m_tree.insertSelfClosingElement(token);
    826853        return;
    827854    }
    828855    parseError(token);
    829     if (currentElement()->hasTagName(tableTag) || isTableBodyContextTag(currentElement()->localName()) || currentElement()->hasTagName(trTag))
     856    if (m_tree.currentElement()->hasTagName(tableTag) || isTableBodyContextTag(m_tree.currentElement()->localName()) || m_tree.currentElement()->hasTagName(trTag))
    830857        notImplemented(); // "whenever a node would be inserted into the current node, it must instead be foster parented."
    831858    processStartTagForInBody(token);
     
    843870        ASSERT(insertionMode() == BeforeHTMLMode);
    844871        if (token.name() == htmlTag) {
    845             insertHTMLStartTagBeforeHTML(token);
     872            m_tree.insertHTMLHtmlStartTagBeforeHTML(token);
    846873            setInsertionMode(BeforeHeadMode);
    847874            return;
     
    852879        ASSERT(insertionMode() == BeforeHeadMode);
    853880        if (token.name() == htmlTag) {
    854             insertHTMLStartTagInBody(token);
     881            m_tree.insertHTMLHtmlStartTagInBody(token);
    855882            return;
    856883        }
    857884        if (token.name() == headTag) {
    858             insertHTMLHeadElement(token);
     885            m_tree.insertHTMLHeadElement(token);
    859886            setInsertionMode(InHeadMode);
    860887            return;
     
    871898        ASSERT(insertionMode() == AfterHeadMode);
    872899        if (token.name() == htmlTag) {
    873             insertHTMLStartTagInBody(token);
     900            m_tree.insertHTMLHtmlStartTagInBody(token);
    874901            return;
    875902        }
    876903        if (token.name() == bodyTag) {
    877904            m_framesetOk = false;
    878             insertHTMLBodyElement(token);
     905            m_tree.insertHTMLBodyElement(token);
    879906            m_insertionMode = InBodyMode;
    880907            return;
    881908        }
    882909        if (token.name() == framesetTag) {
    883             insertElement(token);
     910            m_tree.insertElement(token);
    884911            setInsertionMode(InFramesetMode);
    885912            return;
     
    887914        if (token.name() == baseTag || token.name() == linkTag || token.name() == metaTag || token.name() == noframesTag || token.name() == scriptTag || token.name() == styleTag || token.name() == titleTag) {
    888915            parseError(token);
    889             ASSERT(m_headElement);
    890             m_openElements.pushHTMLHeadElement(m_headElement);
     916            ASSERT(m_tree.head());
     917            m_tree.openElements()->pushHTMLHeadElement(m_tree.head());
    891918            processStartTagForInHead(token);
    892             m_openElements.removeHTMLHeadElement(m_headElement.get());
     919            m_tree.openElements()->removeHTMLHeadElement(m_tree.head());
    893920            return;
    894921        }
     
    923950        ASSERT(insertionMode() == InColumnGroupMode);
    924951        if (token.name() == htmlTag) {
    925             insertHTMLStartTagInBody(token);
     952            m_tree.insertHTMLHtmlStartTagInBody(token);
    926953            return;
    927954        }
    928955        if (token.name() == colTag) {
    929             insertSelfClosingElement(token);
     956            m_tree.insertSelfClosingElement(token);
    930957            return;
    931958        }
     
    939966        ASSERT(insertionMode() == InTableBodyMode);
    940967        if (token.name() == trTag) {
    941             m_openElements.popUntilTableBodyScopeMarker(); // How is there ever anything to pop?
    942             insertElement(token);
     968            m_tree.openElements()->popUntilTableBodyScopeMarker(); // How is there ever anything to pop?
     969            m_tree.insertElement(token);
    943970            m_insertionMode = InRowMode;
    944971            return;
     
    953980        if (token.name() == captionTag || token.name() == colTag || token.name() == colgroupTag || isTableBodyContextTag(token.name())) {
    954981            // FIXME: This is slow.
    955             if (!m_openElements.inTableScope(tbodyTag.localName()) && !m_openElements.inTableScope(theadTag.localName()) && !m_openElements.inTableScope(tfootTag.localName())) {
     982            if (!m_tree.openElements()->inTableScope(tbodyTag.localName()) && !m_tree.openElements()->inTableScope(theadTag.localName()) && !m_tree.openElements()->inTableScope(tfootTag.localName())) {
    956983                ASSERT(m_isParsingFragment);
    957984                parseError(token);
    958985                return;
    959986            }
    960             m_openElements.popUntilTableBodyScopeMarker();
    961             ASSERT(isTableBodyContextTag(currentElement()->localName()));
    962             processFakeEndTag(currentElement()->tagQName());
     987            m_tree.openElements()->popUntilTableBodyScopeMarker();
     988            ASSERT(isTableBodyContextTag(m_tree.currentElement()->localName()));
     989            processFakeEndTag(m_tree.currentElement()->tagQName());
    963990            processStartTag(token);
    964991            return;
     
    969996        ASSERT(insertionMode() == InRowMode);
    970997        if (token.name() == thTag || token.name() == tdTag) {
    971             m_openElements.popUntilTableRowScopeMarker();
    972             insertElement(token);
     998            m_tree.openElements()->popUntilTableRowScopeMarker();
     999            m_tree.insertElement(token);
    9731000            m_insertionMode = InCellMode;
    974             m_activeFormattingElements.appendMarker();
     1001            m_tree.activeFormattingElements()->appendMarker();
    9751002        }
    9761003        if (token.name() == captionTag || token.name() == colTag || token.name() == colgroupTag || isTableBodyContextTag(token.name())) {
     
    9891016        if (token.name() == captionTag || token.name() == colTag || token.name() == colgroupTag || token.name() == thTag || token.name() == tdTag || isTableBodyContextTag(token.name())) {
    9901017            // FIXME: This could be more efficient.
    991             if (!m_openElements.inTableScope(tdTag) || !m_openElements.inTableScope(thTag)) {
     1018            if (!m_tree.openElements()->inTableScope(tdTag) || !m_tree.openElements()->inTableScope(thTag)) {
    9921019                parseError(token);
    9931020                return;
     
    10021029        ASSERT(insertionMode() == AfterBodyMode || insertionMode() == AfterAfterBodyMode);
    10031030        if (token.name() == htmlTag) {
    1004             insertHTMLStartTagInBody(token);
     1031            m_tree.insertHTMLHtmlStartTagInBody(token);
    10051032            return;
    10061033        }
     
    10111038        ASSERT(insertionMode() == InHeadNoscriptMode);
    10121039        if (token.name() == htmlTag) {
    1013             insertHTMLStartTagInBody(token);
     1040            m_tree.insertHTMLHtmlStartTagInBody(token);
    10141041            return;
    10151042        }
     
    10291056        ASSERT(insertionMode() == InFramesetMode);
    10301057        if (token.name() == htmlTag) {
    1031             insertHTMLStartTagInBody(token);
     1058            m_tree.insertHTMLHtmlStartTagInBody(token);
    10321059            return;
    10331060        }
    10341061        if (token.name() == framesetTag) {
    1035             insertElement(token);
     1062            m_tree.insertElement(token);
    10361063            return;
    10371064        }
    10381065        if (token.name() == frameTag) {
    1039             insertSelfClosingElement(token);
     1066            m_tree.insertSelfClosingElement(token);
    10401067            return;
    10411068        }
     
    10501077        ASSERT(insertionMode() == AfterFramesetMode || insertionMode() == AfterAfterFramesetMode);
    10511078        if (token.name() == htmlTag) {
    1052             insertHTMLStartTagInBody(token);
     1079            m_tree.insertHTMLHtmlStartTagInBody(token);
    10531080            return;
    10541081        }
     
    10721099        ASSERT(insertionMode() == InSelectMode || insertionMode() == InSelectInTableMode);
    10731100        if (token.name() == htmlTag) {
    1074             insertHTMLStartTagInBody(token);
     1101            m_tree.insertHTMLHtmlStartTagInBody(token);
    10751102            return;
    10761103        }
    10771104        if (token.name() == optionTag) {
    1078             if (currentElement()->hasTagName(optionTag)) {
     1105            if (m_tree.currentElement()->hasTagName(optionTag)) {
    10791106                AtomicHTMLToken endOption(HTMLToken::EndTag, optionTag.localName());
    10801107                processEndTag(endOption);
    10811108            }
    1082             insertElement(token);
     1109            m_tree.insertElement(token);
    10831110            return;
    10841111        }
    10851112        if (token.name() == optgroupTag) {
    1086             if (currentElement()->hasTagName(optionTag)) {
     1113            if (m_tree.currentElement()->hasTagName(optionTag)) {
    10871114                AtomicHTMLToken endOption(HTMLToken::EndTag, optionTag.localName());
    10881115                processEndTag(endOption);
    10891116            }
    1090             if (currentElement()->hasTagName(optgroupTag)) {
     1117            if (m_tree.currentElement()->hasTagName(optgroupTag)) {
    10911118                AtomicHTMLToken endOptgroup(HTMLToken::EndTag, optgroupTag.localName());
    10921119                processEndTag(endOptgroup);
    10931120            }
    1094             insertElement(token);
     1121            m_tree.insertElement(token);
    10951122            return;
    10961123        }
     
    11271154    ASSERT(token.type() == HTMLToken::EndTag);
    11281155    ASSERT(token.name() == bodyTag);
    1129     if (!m_openElements.inScope(bodyTag.localName())) {
     1156    if (!m_tree.openElements()->inScope(bodyTag.localName())) {
    11301157        parseError(token);
    11311158        return false;
     
    11391166{
    11401167    ASSERT(token.type() == HTMLToken::EndTag);
    1141     HTMLElementStack::ElementRecord* record = m_openElements.topRecord();
     1168    HTMLElementStack::ElementRecord* record = m_tree.openElements()->topRecord();
    11421169    while (1) {
    11431170        Element* node = record->element();
    11441171        if (node->hasLocalName(token.name())) {
    1145             generateImpliedEndTags();
    1146             if (!currentElement()->hasLocalName(token.name())) {
     1172            m_tree.generateImpliedEndTags();
     1173            if (!m_tree.currentElement()->hasLocalName(token.name())) {
    11471174                parseError(token);
    11481175                // FIXME: This is either a bug in the spec, or a bug in our
     
    11511178                // We might have already popped the node for the token in
    11521179                // generateImpliedEndTags, just abort.
    1153                 if (!m_openElements.contains(node))
     1180                if (!m_tree.openElements()->contains(node))
    11541181                    return;
    11551182            }
    1156             m_openElements.popUntil(node);
    1157             m_openElements.pop();
     1183            m_tree.openElements()->popUntil(node);
     1184            m_tree.openElements()->pop();
    11581185            return;
    11591186        }
     
    11721199{
    11731200    HTMLElementStack::ElementRecord* furthestBlock = 0;
    1174     HTMLElementStack::ElementRecord* record = m_openElements.topRecord();
     1201    HTMLElementStack::ElementRecord* record = m_tree.openElements()->topRecord();
    11751202    for (; record; record = record->next()) {
    11761203        if (record->element() == formattingElement)
     
    11881215{
    11891216    Element* fosterParentElement = 0;
    1190     HTMLElementStack::ElementRecord* lastTableElementRecord = m_openElements.topmost(tableTag.localName());
     1217    HTMLElementStack::ElementRecord* lastTableElementRecord = m_tree.openElements()->topmost(tableTag.localName());
    11911218    if (lastTableElementRecord) {
    11921219        Element* lastTableElement = lastTableElementRecord->element();
     
    12011228    } else {
    12021229        ASSERT(m_isParsingFragment);
    1203         fosterParentElement = m_openElements.bottom(); // <html> element
     1230        fosterParentElement = m_tree.openElements()->bottom(); // <html> element
    12041231    }
    12051232
     
    12261253    while (1) {
    12271254        // 1.
    1228         Element* formattingElement = m_activeFormattingElements.closestElementInScopeWithName(token.name());
    1229         if (!formattingElement || !m_openElements.inScope(formattingElement)) {
     1255        Element* formattingElement = m_tree.activeFormattingElements()->closestElementInScopeWithName(token.name());
     1256        if (!formattingElement || !m_tree.openElements()->inScope(formattingElement)) {
    12301257            parseError(token);
    12311258            notImplemented(); // Check the stack of open elements for a more specific parse error.
    12321259            return;
    12331260        }
    1234         HTMLElementStack::ElementRecord* formattingElementRecord = m_openElements.find(formattingElement);
     1261        HTMLElementStack::ElementRecord* formattingElementRecord = m_tree.openElements()->find(formattingElement);
    12351262        if (!formattingElementRecord) {
    12361263            parseError(token);
    1237             m_activeFormattingElements.remove(formattingElement);
    1238             return;
    1239         }
    1240         if (formattingElement != currentElement())
     1264            m_tree.activeFormattingElements()->remove(formattingElement);
     1265            return;
     1266        }
     1267        if (formattingElement != m_tree.currentElement())
    12411268            parseError(token);
    12421269        // 2.
     
    12441271        // 3.
    12451272        if (!furthestBlock) {
    1246             m_openElements.popUntil(formattingElement);
    1247             m_openElements.pop();
    1248             m_activeFormattingElements.remove(formattingElement);
     1273            m_tree.openElements()->popUntil(formattingElement);
     1274            m_tree.openElements()->pop();
     1275            m_tree.activeFormattingElements()->remove(formattingElement);
    12491276            return;
    12501277        }
     
    12531280        Element* commonAncestor = formattingElementRecord->next()->element();
    12541281        // 5.
    1255         HTMLFormattingElementList::Bookmark bookmark = m_activeFormattingElements.bookmarkFor(formattingElement);
     1282        HTMLFormattingElementList::Bookmark bookmark = m_tree.activeFormattingElements()->bookmarkFor(formattingElement);
    12561283        // 6.
    12571284        HTMLElementStack::ElementRecord* node = furthestBlock;
     
    12641291            nextNode = node->next(); // Save node->next() for the next iteration in case node is deleted in 6.2.
    12651292            // 6.2
    1266             if (!m_activeFormattingElements.contains(node->element())) {
    1267                 m_openElements.remove(node->element());
     1293            if (!m_tree.activeFormattingElements()->contains(node->element())) {
     1294                m_tree.openElements()->remove(node->element());
    12681295                node = 0;
    12691296                continue;
     
    12771304            // Is createElement correct? (instead of insertElement)
    12781305            // Does this code ever leave newElement unattached?
    1279             RefPtr<Element> newElement = createElement(fakeToken);
    1280             HTMLFormattingElementList::Entry* nodeEntry = m_activeFormattingElements.find(node->element());
     1306            RefPtr<Element> newElement = m_tree.createElement(fakeToken);
     1307            HTMLFormattingElementList::Entry* nodeEntry = m_tree.activeFormattingElements()->find(node->element());
    12811308            nodeEntry->replaceElement(newElement.get());
    12821309            node->replaceElement(newElement.release());
     
    13081335        // FIXME: We're supposed to save the original token in the entry.
    13091336        AtomicHTMLToken fakeToken(HTMLToken::StartTag, formattingElement->localName());
    1310         RefPtr<Element> newElement = createElement(fakeToken);
     1337        RefPtr<Element> newElement = m_tree.createElement(fakeToken);
    13111338        // 9
    13121339        reparentChildren(furthestBlock->element(), newElement.get());
     
    13141341        furthestBlock->element()->parserAddChild(newElement);
    13151342        // 11
    1316         m_activeFormattingElements.remove(formattingElement);
    1317         m_activeFormattingElements.insertAt(newElement.get(), bookmark);
     1343        m_tree.activeFormattingElements()->remove(formattingElement);
     1344        m_tree.activeFormattingElements()->insertAt(newElement.get(), bookmark);
    13181345        // 12
    1319         m_openElements.remove(formattingElement);
    1320         m_openElements.insertAbove(newElement, furthestBlock);
     1346        m_tree.openElements()->remove(formattingElement);
     1347        m_tree.openElements()->insertAbove(newElement, furthestBlock);
    13211348    }
    13221349}
     
    13361363    bool last = false;
    13371364    bool foreign = false;
    1338     HTMLElementStack::ElementRecord* nodeRecord = m_openElements.topRecord();
     1365    HTMLElementStack::ElementRecord* nodeRecord = m_tree.openElements()->topRecord();
    13391366    while (1) {
    13401367        Element* node = nodeRecord->element();
    1341         if (node == m_openElements.bottom()) {
     1368        if (node == m_tree.openElements()->bottom()) {
    13421369            ASSERT(m_isParsingFragment);
    13431370            last = true;
     
    14071434    }
    14081435    if (token.name() == addressTag || token.name() == articleTag || token.name() == asideTag || token.name() == blockquoteTag || token.name() == buttonTag || token.name() == centerTag || token.name() == "details" || token.name() == dirTag || token.name() == divTag || token.name() == dlTag || token.name() == fieldsetTag || token.name() == "figure" || token.name() == footerTag || token.name() == headerTag || token.name() == hgroupTag || token.name() == listingTag || token.name() == menuTag || token.name() == navTag || token.name() == olTag || token.name() == preTag || token.name() == sectionTag || token.name() == ulTag) {
    1409         if (!m_openElements.inScope(token.name())) {
    1410             parseError(token);
    1411             return;
    1412         }
    1413         generateImpliedEndTags();
    1414         if (currentElement()->tagQName() != token.name())
    1415             parseError(token);
    1416         m_openElements.popUntil(token.name());
    1417         m_openElements.pop();
     1436        if (!m_tree.openElements()->inScope(token.name())) {
     1437            parseError(token);
     1438            return;
     1439        }
     1440        m_tree.generateImpliedEndTags();
     1441        if (!m_tree.currentElement()->hasLocalName(token.name()))
     1442            parseError(token);
     1443        m_tree.openElements()->popUntil(token.name());
     1444        m_tree.openElements()->pop();
    14181445    }
    14191446    if (token.name() == formTag) {
    1420         RefPtr<Element> node = m_formElement.release();
    1421         if (!node || !m_openElements.inScope(node.get())) {
    1422             parseError(token);
    1423             return;
    1424         }
    1425         generateImpliedEndTags();
    1426         if (currentElement() != node.get())
    1427             parseError(token);
    1428         m_openElements.remove(node.get());
     1447        RefPtr<Element> node = m_tree.takeForm();
     1448        if (!node || !m_tree.openElements()->inScope(node.get())) {
     1449            parseError(token);
     1450            return;
     1451        }
     1452        m_tree.generateImpliedEndTags();
     1453        if (m_tree.currentElement() != node.get())
     1454            parseError(token);
     1455        m_tree.openElements()->remove(node.get());
    14291456    }
    14301457    if (token.name() == pTag) {
    1431         if (!m_openElements.inScope(token.name())) {
     1458        if (!m_tree.openElements()->inScope(token.name())) {
    14321459            parseError(token);
    14331460            processFakeStartTag(pTag);
    1434             ASSERT(m_openElements.inScope(token.name()));
     1461            ASSERT(m_tree.openElements()->inScope(token.name()));
    14351462            processEndTag(token);
    14361463            return;
    14371464        }
    1438         generateImpliedEndTagsWithExclusion(token.name());
    1439         if (!currentElement()->hasLocalName(token.name()))
    1440             parseError(token);
    1441         m_openElements.popUntil(token.name());
    1442         m_openElements.pop();
     1465        m_tree.generateImpliedEndTagsWithExclusion(token.name());
     1466        if (!m_tree.currentElement()->hasLocalName(token.name()))
     1467            parseError(token);
     1468        m_tree.openElements()->popUntil(token.name());
     1469        m_tree.openElements()->pop();
    14431470        return;
    14441471    }
    14451472    if (token.name() == liTag) {
    1446         if (!m_openElements.inListItemScope(token.name())) {
    1447             parseError(token);
    1448             return;
    1449         }
    1450         generateImpliedEndTagsWithExclusion(token.name());
    1451         if (!currentElement()->hasLocalName(token.name()))
    1452             parseError(token);
    1453         m_openElements.popUntil(token.name());
    1454         m_openElements.pop();
     1473        if (!m_tree.openElements()->inListItemScope(token.name())) {
     1474            parseError(token);
     1475            return;
     1476        }
     1477        m_tree.generateImpliedEndTagsWithExclusion(token.name());
     1478        if (!m_tree.currentElement()->hasLocalName(token.name()))
     1479            parseError(token);
     1480        m_tree.openElements()->popUntil(token.name());
     1481        m_tree.openElements()->pop();
    14551482        return;
    14561483    }
    14571484    if (token.name() == ddTag || token.name() == dtTag) {
    1458         if (!m_openElements.inScope(token.name())) {
    1459             parseError(token);
    1460             return;
    1461         }
    1462         generateImpliedEndTagsWithExclusion(token.name());
    1463         if (!currentElement()->hasLocalName(token.name()))
    1464             parseError(token);
    1465         m_openElements.popUntil(token.name());
    1466         m_openElements.pop();
     1485        if (!m_tree.openElements()->inScope(token.name())) {
     1486            parseError(token);
     1487            return;
     1488        }
     1489        m_tree.generateImpliedEndTagsWithExclusion(token.name());
     1490        if (!m_tree.currentElement()->hasLocalName(token.name()))
     1491            parseError(token);
     1492        m_tree.openElements()->popUntil(token.name());
     1493        m_tree.openElements()->pop();
    14671494        return;
    14681495    }
    14691496    if (isNumberedHeaderTag(token.name())) {
    1470         if (!m_openElements.inScope(token.name())) {
    1471             parseError(token);
    1472             return;
    1473         }
    1474         generateImpliedEndTags();
    1475         if (!currentElement()->hasLocalName(token.name()))
    1476             parseError(token);
    1477         m_openElements.popUntil(token.name());
    1478         m_openElements.pop();
     1497        if (!m_tree.openElements()->inScope(token.name())) {
     1498            parseError(token);
     1499            return;
     1500        }
     1501        m_tree.generateImpliedEndTags();
     1502        if (!m_tree.currentElement()->hasLocalName(token.name()))
     1503            parseError(token);
     1504        m_tree.openElements()->popUntil(token.name());
     1505        m_tree.openElements()->pop();
    14791506        return;
    14801507    }
     
    14881515    }
    14891516    if (token.name() == appletTag || token.name() == marqueeTag || token.name() == objectTag) {
    1490         if (!m_openElements.inScope(token.name())) {
    1491             parseError(token);
    1492             return;
    1493         }
    1494         generateImpliedEndTags();
    1495         if (currentElement()->tagQName() != token.name())
    1496             parseError(token);
    1497         m_openElements.popUntil(token.name());
    1498         m_openElements.pop();
    1499         m_activeFormattingElements.clearToLastMarker();
     1517        if (!m_tree.openElements()->inScope(token.name())) {
     1518            parseError(token);
     1519            return;
     1520        }
     1521        m_tree.generateImpliedEndTags();
     1522        if (!m_tree.currentElement()->hasLocalName(token.name()))
     1523            parseError(token);
     1524        m_tree.openElements()->popUntil(token.name());
     1525        m_tree.openElements()->pop();
     1526        m_tree.activeFormattingElements()->clearToLastMarker();
    15001527        return;
    15011528    }
    15021529    if (token.name() == brTag) {
    15031530        parseError(token);
    1504         reconstructTheActiveFormattingElements();
     1531        m_tree.reconstructTheActiveFormattingElements();
    15051532        // Notice that we lose the attributes.
    15061533        AtomicHTMLToken startBr(HTMLToken::StartTag, token.name());
    1507         insertSelfClosingElement(startBr);
     1534        m_tree.insertSelfClosingElement(startBr);
    15081535        m_framesetOk = false;
    15091536        return;
     
    15141541bool HTMLTreeBuilder::processCaptionEndTagForInCaption()
    15151542{
    1516     if (!m_openElements.inTableScope(captionTag.localName())) {
     1543    if (!m_tree.openElements()->inTableScope(captionTag.localName())) {
    15171544        ASSERT(m_isParsingFragment);
    15181545        // FIXME: parse error
    15191546        return false;
    15201547    }
    1521     generateImpliedEndTags();
    1522     // FIXME: parse error if (!currentElement()->hasTagName(captionTag))
    1523     m_openElements.popUntil(captionTag.localName());
    1524     m_openElements.pop();
    1525     m_activeFormattingElements.clearToLastMarker();
     1548    m_tree.generateImpliedEndTags();
     1549    // FIXME: parse error if (!m_tree.currentElement()->hasTagName(captionTag))
     1550    m_tree.openElements()->popUntil(captionTag.localName());
     1551    m_tree.openElements()->pop();
     1552    m_tree.activeFormattingElements()->clearToLastMarker();
    15261553    m_insertionMode = InTableMode;
    15271554    return true;
     
    15301557bool HTMLTreeBuilder::processTrEndTagForInRow()
    15311558{
    1532     if (!m_openElements.inTableScope(trTag.localName())) {
     1559    if (!m_tree.openElements()->inTableScope(trTag.localName())) {
    15331560        ASSERT(m_isParsingFragment);
    15341561        // FIXME: parse error
    15351562        return false;
    15361563    }
    1537     m_openElements.popUntilTableRowScopeMarker();
    1538     ASSERT(currentElement()->hasTagName(trTag));
    1539     m_openElements.pop();
     1564    m_tree.openElements()->popUntilTableRowScopeMarker();
     1565    ASSERT(m_tree.currentElement()->hasTagName(trTag));
     1566    m_tree.openElements()->pop();
    15401567    m_insertionMode = InTableBodyMode;
    15411568    return true;
     
    15461573    ASSERT(token.type() == HTMLToken::EndTag);
    15471574    if (token.name() == tableTag) {
    1548         if (!m_openElements.inTableScope(token.name())) {
     1575        if (!m_tree.openElements()->inTableScope(token.name())) {
    15491576            ASSERT(m_isParsingFragment);
    15501577            parseError(token);
    15511578            return;
    15521579        }
    1553         m_openElements.popUntil(tableTag.localName());
    1554         m_openElements.pop();
     1580        m_tree.openElements()->popUntil(tableTag.localName());
     1581        m_tree.openElements()->pop();
    15551582        resetInsertionModeAppropriately();
    15561583        return;
     
    15911618        ASSERT(insertionMode() == InHeadMode);
    15921619        if (token.name() == headTag) {
    1593             m_openElements.popHTMLHeadElement();
     1620            m_tree.openElements()->popHTMLHeadElement();
    15941621            setInsertionMode(AfterHeadMode);
    15951622            return;
     
    16701697        }
    16711698        if (isTableBodyContextTag(token.name())) {
    1672             if (!m_openElements.inTableScope(token.name())) {
     1699            if (!m_tree.openElements()->inTableScope(token.name())) {
    16731700                parseError(token);
    16741701                return;
     
    16881715        ASSERT(insertionMode() == InCellMode);
    16891716        if (token.name() == thTag || token.name() == tdTag) {
    1690             if (!m_openElements.inTableScope(token.name())) {
     1717            if (!m_tree.openElements()->inTableScope(token.name())) {
    16911718                parseError(token);
    16921719                return;
    16931720            }
    1694             generateImpliedEndTags();
    1695             if (!currentElement()->hasLocalName(token.name()))
     1721            m_tree.generateImpliedEndTags();
     1722            if (!m_tree.currentElement()->hasLocalName(token.name()))
    16961723                parseError(token);
    1697             m_openElements.popUntil(token.name());
    1698             m_openElements.pop();
    1699             m_activeFormattingElements.clearToLastMarker();
     1724            m_tree.openElements()->popUntil(token.name());
     1725            m_tree.openElements()->pop();
     1726            m_tree.activeFormattingElements()->clearToLastMarker();
    17001727            m_insertionMode = InRowMode;
    1701             ASSERT(currentElement()->hasTagName(trTag));
     1728            ASSERT(m_tree.currentElement()->hasTagName(trTag));
    17021729            return;
    17031730        }
     
    17071734        }
    17081735        if (token.name() == tableTag || token.name() == trTag || isTableBodyContextTag(token.name())) {
    1709             if (!m_openElements.inTableScope(token.name())) {
     1736            if (!m_tree.openElements()->inTableScope(token.name())) {
    17101737                ASSERT(m_isParsingFragment);
    17111738                // FIXME: It is unclear what the exact ASSERT should be.
     
    17231750        ASSERT(insertionMode() == InTableBodyMode);
    17241751        if (isTableBodyContextTag(token.name())) {
    1725             if (!m_openElements.inTableScope(token.name())) {
     1752            if (!m_tree.openElements()->inTableScope(token.name())) {
    17261753                parseError(token);
    17271754                return;
    17281755            }
    1729             m_openElements.popUntilTableBodyScopeMarker();
    1730             m_openElements.pop();
     1756            m_tree.openElements()->popUntilTableBodyScopeMarker();
     1757            m_tree.openElements()->pop();
    17311758            m_insertionMode = InTableMode;
    17321759            return;
     
    17341761        if (token.name() == tableTag) {
    17351762            // FIXME: This is slow.
    1736             if (!m_openElements.inTableScope(tbodyTag.localName()) && !m_openElements.inTableScope(theadTag.localName()) && !m_openElements.inTableScope(tfootTag.localName())) {
     1763            if (!m_tree.openElements()->inTableScope(tbodyTag.localName()) && !m_tree.openElements()->inTableScope(theadTag.localName()) && !m_tree.openElements()->inTableScope(tfootTag.localName())) {
    17371764                ASSERT(m_isParsingFragment);
    17381765                parseError(token);
    17391766                return;
    17401767            }
    1741             m_openElements.popUntilTableBodyScopeMarker();
    1742             ASSERT(isTableBodyContextTag(currentElement()->localName()));
    1743             processFakeEndTag(currentElement()->tagQName());
     1768            m_tree.openElements()->popUntilTableBodyScopeMarker();
     1769            ASSERT(isTableBodyContextTag(m_tree.currentElement()->localName()));
     1770            processFakeEndTag(m_tree.currentElement()->tagQName());
    17441771            processEndTag(token);
    17451772            return;
     
    17711798        ASSERT(insertionMode() == InHeadNoscriptMode);
    17721799        if (token.name() == noscriptTag) {
    1773             ASSERT(currentElement()->tagQName() == noscriptTag);
    1774             m_openElements.pop();
    1775             ASSERT(currentElement()->tagQName() == headTag);
     1800            ASSERT(m_tree.currentElement()->hasTagName(noscriptTag));
     1801            m_tree.openElements()->pop();
     1802            ASSERT(m_tree.currentElement()->hasTagName(headTag));
    17761803            setInsertionMode(InHeadMode);
    17771804            return;
     
    17881815            // Pause ourselves so that parsing stops until the script can be processed by the caller.
    17891816            m_isPaused = true;
    1790             ASSERT(currentElement()->tagQName() == scriptTag);
    1791             m_scriptToProcess = currentElement();
    1792             m_openElements.pop();
     1817            ASSERT(m_tree.currentElement()->hasTagName(scriptTag));
     1818            m_scriptToProcess = m_tree.currentElement();
     1819            m_tree.openElements()->pop();
    17931820            m_insertionMode = m_originalInsertionMode;
    17941821            return;
    17951822        }
    1796         m_openElements.pop();
     1823        m_tree.openElements()->pop();
    17971824        m_insertionMode = m_originalInsertionMode;
    17981825        break;
     
    18001827        ASSERT(insertionMode() == InFramesetMode);
    18011828        if (token.name() == framesetTag) {
    1802             if (currentElement() == m_openElements.htmlElement()) {
     1829            if (m_tree.currentElement() == m_tree.openElements()->htmlElement()) {
    18031830                parseError(token);
    18041831                return;
    18051832            }
    1806             m_openElements.pop();
    1807             if (!m_isParsingFragment && !currentElement()->hasTagName(framesetTag))
     1833            m_tree.openElements()->pop();
     1834            if (!m_isParsingFragment && !m_tree.currentElement()->hasTagName(framesetTag))
    18081835                m_insertionMode = AfterFramesetMode;
    18091836            return;
     
    18251852        if (token.name() == captionTag || token.name() == tableTag || isTableBodyContextTag(token.name()) || token.name() == trTag || token.name() == tdTag || token.name() == thTag) {
    18261853            parseError(token);
    1827             if (m_openElements.inTableScope(token.name())) {
     1854            if (m_tree.openElements()->inTableScope(token.name())) {
    18281855                AtomicHTMLToken endSelect(HTMLToken::EndTag, selectTag.localName());
    18291856                processEndTag(endSelect);
     
    18361863        ASSERT(insertionMode() == InSelectMode || insertionMode() == InSelectInTableMode);
    18371864        if (token.name() == optgroupTag) {
    1838             if (currentElement()->hasTagName(optionTag))
     1865            if (m_tree.currentElement()->hasTagName(optionTag))
    18391866                notImplemented();
    1840             if (currentElement()->hasTagName(optgroupTag)) {
    1841                 m_openElements.pop();
     1867            if (m_tree.currentElement()->hasTagName(optgroupTag)) {
     1868                m_tree.openElements()->pop();
    18421869                return;
    18431870            }
     
    18461873        }
    18471874        if (token.name() == optionTag) {
    1848             if (currentElement()->hasTagName(optionTag)) {
    1849                 m_openElements.pop();
     1875            if (m_tree.currentElement()->hasTagName(optionTag)) {
     1876                m_tree.openElements()->pop();
    18501877                return;
    18511878            }
     
    18551882        if (token.name() == selectTag) {
    18561883            notImplemented(); // fragment case
    1857             m_openElements.popUntil(selectTag.localName());
    1858             m_openElements.pop();
     1884            m_tree.openElements()->popUntil(selectTag.localName());
     1885            m_tree.openElements()->pop();
    18591886            resetInsertionModeAppropriately();
    18601887            return;
     
    18721899    ASSERT(token.type() == HTMLToken::Comment);
    18731900    if (m_insertionMode == InitialMode || m_insertionMode == BeforeHTMLMode || m_insertionMode == AfterAfterBodyMode || m_insertionMode == AfterAfterFramesetMode) {
    1874         insertCommentOnDocument(token);
     1901        m_tree.insertCommentOnDocument(token);
    18751902        return;
    18761903    }
    18771904    if (m_insertionMode == AfterBodyMode) {
    1878         insertCommentOnHTMLHtmlElement(token);
    1879         return;
    1880     }
    1881     insertComment(token);
     1905        m_tree.insertCommentOnHTMLHtmlElement(token);
     1906        return;
     1907    }
     1908    m_tree.insertComment(token);
    18821909}
    18831910
     
    19171944        ASSERT(insertionMode() == InBodyMode || insertionMode() == InCaptionMode || insertionMode() == InCellMode);
    19181945        notImplemented();
    1919         insertTextNode(token);
     1946        m_tree.insertTextNode(token);
    19201947        break;
    19211948    case InTableMode:
     
    19241951        ASSERT(insertionMode() == InTableMode || insertionMode() == InTableBodyMode || insertionMode() == InRowMode);
    19251952        notImplemented(); // Crazy pending characters.
    1926         insertTextNode(token);
     1953        m_tree.insertTextNode(token);
    19271954        break;
    19281955    case InColumnGroupMode:
     
    19391966    case TextMode:
    19401967        notImplemented();
    1941         insertTextNode(token);
     1968        m_tree.insertTextNode(token);
    19421969        break;
    19431970    case InHeadNoscriptMode:
     
    19551982    case InSelectMode:
    19561983        ASSERT(insertionMode() == InSelectMode || insertionMode() == InSelectInTableMode);
    1957         insertTextNode(token);
     1984        m_tree.insertTextNode(token);
    19581985        break;
    19591986    case InTableTextMode:
     
    20132040    case InSelectMode:
    20142041        ASSERT(insertionMode() == InSelectMode || insertionMode() == InSelectInTableMode || insertionMode() == InTableMode || insertionMode() == InFramesetMode || insertionMode() == InTableBodyMode);
    2015         if (currentElement() != m_openElements.htmlElement())
     2042        if (m_tree.currentElement() != m_tree.openElements()->htmlElement())
    20162043            parseError(token);
    20172044        break;
    20182045    case InColumnGroupMode:
    2019         if (currentElement() == m_openElements.htmlElement()) {
     2046        if (m_tree.currentElement() == m_tree.openElements()->htmlElement()) {
    20202047            ASSERT(m_isParsingFragment);
    20212048            return;
     
    20472074{
    20482075    AtomicHTMLToken startHTML(HTMLToken::StartTag, htmlTag.localName());
    2049     insertHTMLStartTagBeforeHTML(startHTML);
     2076    m_tree.insertHTMLHtmlStartTagBeforeHTML(startHTML);
    20502077    setInsertionMode(BeforeHeadMode);
    20512078}
     
    20802107    ASSERT(token.type() == HTMLToken::StartTag);
    20812108    if (token.name() == htmlTag) {
    2082         insertHTMLStartTagInBody(token);
     2109        m_tree.insertHTMLHtmlStartTagInBody(token);
    20832110        return true;
    20842111    }
    20852112    // FIXME: Atomize "command".
    20862113    if (token.name() == baseTag || token.name() == "command" || token.name() == linkTag || token.name() == metaTag) {
    2087         insertSelfClosingElement(token);
     2114        m_tree.insertSelfClosingElement(token);
    20882115        // Note: The custom processing for the <meta> tag is done in HTMLMetaElement::process().
    20892116        return true;
    20902117    }
    20912118    if (token.name() == titleTag) {
    2092         insertGenericRCDATAElement(token);
     2119        processGenericRCDATAStartTag(token);
    20932120        return true;
    20942121    }
    20952122    if (token.name() == noscriptTag) {
    20962123        if (isScriptingFlagEnabled(m_document->frame())) {
    2097             insertGenericRawTextElement(token);
     2124            processGenericRawTextStartTag(token);
    20982125            return true;
    20992126        }
    2100         insertElement(token);
     2127        m_tree.insertElement(token);
    21012128        setInsertionMode(InHeadNoscriptMode);
    21022129        return true;
    21032130    }
    21042131    if (token.name() == noframesTag || token.name() == styleTag) {
    2105         insertGenericRawTextElement(token);
     2132        processGenericRawTextStartTag(token);
    21062133        return true;
    21072134    }
    21082135    if (token.name() == scriptTag) {
    2109         insertScriptElement(token);
     2136        processScriptStartTag(token);
    21102137        return true;
    21112138    }
     
    21172144}
    21182145
    2119 void HTMLTreeBuilder::insertDoctype(AtomicHTMLToken& token)
     2146void HTMLConstructionSite::insertDoctype(AtomicHTMLToken& token)
    21202147{
    21212148    ASSERT(token.type() == HTMLToken::DOCTYPE);
     
    21272154}
    21282155
    2129 void HTMLTreeBuilder::insertComment(AtomicHTMLToken& token)
     2156void HTMLConstructionSite::insertComment(AtomicHTMLToken& token)
    21302157{
    21312158    ASSERT(token.type() == HTMLToken::Comment);
     
    21332160}
    21342161
    2135 void HTMLTreeBuilder::insertCommentOnDocument(AtomicHTMLToken& token)
     2162void HTMLConstructionSite::insertCommentOnDocument(AtomicHTMLToken& token)
    21362163{
    21372164    ASSERT(token.type() == HTMLToken::Comment);
     
    21392166}
    21402167
    2141 void HTMLTreeBuilder::insertCommentOnHTMLHtmlElement(AtomicHTMLToken& token)
     2168void HTMLConstructionSite::insertCommentOnHTMLHtmlElement(AtomicHTMLToken& token)
    21422169{
    21432170    ASSERT(token.type() == HTMLToken::Comment);
     
    21452172}
    21462173
    2147 PassRefPtr<Element> HTMLTreeBuilder::createElementAndAttachToCurrent(AtomicHTMLToken& token)
     2174PassRefPtr<Element> HTMLConstructionSite::createElementAndAttachToCurrent(AtomicHTMLToken& token)
    21482175{
    21492176    ASSERT(token.type() == HTMLToken::StartTag);
     
    21512178}
    21522179
    2153 void HTMLTreeBuilder::insertHTMLHtmlElement(AtomicHTMLToken& token)
     2180void HTMLConstructionSite::insertHTMLHtmlElement(AtomicHTMLToken& token)
    21542181{
    21552182    m_openElements.pushHTMLHtmlElement(createElementAndAttachToCurrent(token));
    21562183}
    21572184
    2158 void HTMLTreeBuilder::insertHTMLHeadElement(AtomicHTMLToken& token)
    2159 {
    2160     m_headElement = createElementAndAttachToCurrent(token);
    2161     m_openElements.pushHTMLHeadElement(m_headElement);
    2162 }
    2163 
    2164 void HTMLTreeBuilder::insertHTMLBodyElement(AtomicHTMLToken& token)
     2185void HTMLConstructionSite::insertHTMLHeadElement(AtomicHTMLToken& token)
     2186{
     2187    m_head = createElementAndAttachToCurrent(token);
     2188    m_openElements.pushHTMLHeadElement(m_head);
     2189}
     2190
     2191void HTMLConstructionSite::insertHTMLBodyElement(AtomicHTMLToken& token)
    21652192{
    21662193    m_openElements.pushHTMLBodyElement(createElementAndAttachToCurrent(token));
    21672194}
    21682195
    2169 void HTMLTreeBuilder::insertElement(AtomicHTMLToken& token)
     2196void HTMLConstructionSite::insertElement(AtomicHTMLToken& token)
    21702197{
    21712198    m_openElements.push(createElementAndAttachToCurrent(token));
    21722199}
    21732200
    2174 void HTMLTreeBuilder::insertSelfClosingElement(AtomicHTMLToken& token)
     2201void HTMLConstructionSite::insertSelfClosingElement(AtomicHTMLToken& token)
    21752202{
    21762203    ASSERT(token.type() == HTMLToken::StartTag);
     
    21802207}
    21812208
    2182 void HTMLTreeBuilder::insertFormattingElement(AtomicHTMLToken& token)
     2209void HTMLConstructionSite::insertFormattingElement(AtomicHTMLToken& token)
    21832210{
    21842211    // http://www.whatwg.org/specs/web-apps/current-work/multipage/parsing.html#the-stack-of-open-elements
     
    21892216}
    21902217
    2191 void HTMLTreeBuilder::insertGenericRCDATAElement(AtomicHTMLToken& token)
    2192 {
    2193     insertElement(token);
     2218void HTMLTreeBuilder::processGenericRCDATAStartTag(AtomicHTMLToken& token)
     2219{
     2220    ASSERT(token.type() == HTMLToken::StartTag);
     2221    m_tree.insertElement(token);
    21942222    m_tokenizer->setState(HTMLTokenizer::RCDATAState);
    21952223    m_originalInsertionMode = m_insertionMode;
     
    21972225}
    21982226
    2199 void HTMLTreeBuilder::insertGenericRawTextElement(AtomicHTMLToken& token)
    2200 {
    2201     insertElement(token);
     2227void HTMLTreeBuilder::processGenericRawTextStartTag(AtomicHTMLToken& token)
     2228{
     2229    ASSERT(token.type() == HTMLToken::StartTag);
     2230    m_tree.insertElement(token);
    22022231    m_tokenizer->setState(HTMLTokenizer::RAWTEXTState);
    22032232    m_originalInsertionMode = m_insertionMode;
     
    22052234}
    22062235
    2207 void HTMLTreeBuilder::insertScriptElement(AtomicHTMLToken& token)
    2208 {
    2209     ASSERT_UNUSED(token, token.type() == HTMLToken::StartTag);
     2236void HTMLConstructionSite::insertScriptElement(AtomicHTMLToken& token)
     2237{
    22102238    RefPtr<HTMLScriptElement> element = HTMLScriptElement::create(scriptTag, m_document, true);
    22112239    element->setAttributeMap(token.takeAtributes(), m_fragmentScriptingPermission);
    22122240    m_openElements.push(attach(currentElement(), element.release()));
     2241}
     2242
     2243void HTMLTreeBuilder::processScriptStartTag(AtomicHTMLToken& token)
     2244{
     2245    ASSERT(token.type() == HTMLToken::StartTag);
     2246    m_tree.insertScriptElement(token);
    22132247    m_tokenizer->setState(HTMLTokenizer::ScriptDataState);
    22142248    m_originalInsertionMode = m_insertionMode;
     
    22162250}
    22172251
    2218 void HTMLTreeBuilder::insertTextNode(AtomicHTMLToken& token)
     2252void HTMLConstructionSite::insertTextNode(AtomicHTMLToken& token)
    22192253{
    22202254    if (Node* lastChild = currentElement()->lastChild()) {
     
    22302264}
    22312265
    2232 PassRefPtr<Element> HTMLTreeBuilder::createElement(AtomicHTMLToken& token)
     2266PassRefPtr<Element> HTMLConstructionSite::createElement(AtomicHTMLToken& token)
    22332267{
    22342268    RefPtr<Element> element = HTMLElementFactory::createHTMLElement(QualifiedName(nullAtom, token.name(), xhtmlNamespaceURI), m_document, 0);
     
    22372271}
    22382272
    2239 bool HTMLTreeBuilder::indexOfFirstUnopenFormattingElement(unsigned& firstUnopenElementIndex) const
     2273bool HTMLConstructionSite::indexOfFirstUnopenFormattingElement(unsigned& firstUnopenElementIndex) const
    22402274{
    22412275    if (m_activeFormattingElements.isEmpty())
     
    22442278    do {
    22452279        --index;
    2246         const HTMLFormattingElementList::Entry& entry = m_activeFormattingElements[index];
     2280        const HTMLFormattingElementList::Entry& entry = m_activeFormattingElements.at(index);
    22472281        if (entry.isMarker() || m_openElements.contains(entry.element())) {
    22482282            firstUnopenElementIndex = index + 1;
     
    22542288}
    22552289
    2256 void HTMLTreeBuilder::reconstructTheActiveFormattingElements()
     2290void HTMLConstructionSite::reconstructTheActiveFormattingElements()
    22572291{
    22582292    unsigned firstUnopenElementIndex;
     
    22632297    ASSERT(unopenEntryIndex < m_activeFormattingElements.size());
    22642298    for (; unopenEntryIndex < m_activeFormattingElements.size(); ++unopenEntryIndex) {
    2265         HTMLFormattingElementList::Entry& unopenedEntry = m_activeFormattingElements[unopenEntryIndex];
     2299        HTMLFormattingElementList::Entry& unopenedEntry = m_activeFormattingElements.at(unopenEntryIndex);
    22662300        // FIXME: We're supposed to save the original token in the entry.
    22672301        AtomicHTMLToken fakeToken(HTMLToken::StartTag, unopenedEntry.element()->localName());
     
    22872321}
    22882322
    2289 void HTMLTreeBuilder::generateImpliedEndTagsWithExclusion(const AtomicString& tagName)
     2323void HTMLConstructionSite::generateImpliedEndTagsWithExclusion(const AtomicString& tagName)
    22902324{
    22912325    while (hasImpliedEndTag(currentElement()) && !currentElement()->hasLocalName(tagName))
     
    22932327}
    22942328
    2295 void HTMLTreeBuilder::generateImpliedEndTags()
     2329void HTMLConstructionSite::generateImpliedEndTags()
    22962330{
    22972331    while (hasImpliedEndTag(currentElement()))
  • trunk/WebCore/html/HTMLTreeBuilder.h

    r62573 r62599  
    4949class LegacyHTMLTreeBuilder;
    5050class Node;
     51
     52class HTMLConstructionSite : public Noncopyable {
     53public:
     54    HTMLConstructionSite(Document*, FragmentScriptingPermission);
     55
     56    void insertDoctype(AtomicHTMLToken&);
     57    void insertComment(AtomicHTMLToken&);
     58    void insertCommentOnDocument(AtomicHTMLToken&);
     59    void insertCommentOnHTMLHtmlElement(AtomicHTMLToken&);
     60    void insertElement(AtomicHTMLToken&);
     61    void insertSelfClosingElement(AtomicHTMLToken&);
     62    void insertFormattingElement(AtomicHTMLToken&);
     63    void insertHTMLHtmlElement(AtomicHTMLToken&);
     64    void insertHTMLHeadElement(AtomicHTMLToken&);
     65    void insertHTMLBodyElement(AtomicHTMLToken&);
     66    void insertScriptElement(AtomicHTMLToken&);
     67    void insertTextNode(AtomicHTMLToken&);
     68
     69    void insertHTMLHtmlStartTagBeforeHTML(AtomicHTMLToken&);
     70    void insertHTMLHtmlStartTagInBody(AtomicHTMLToken&);
     71    void insertHTMLBodyStartTagInBody(AtomicHTMLToken&);
     72
     73    PassRefPtr<Element> createElement(AtomicHTMLToken&);
     74
     75    bool indexOfFirstUnopenFormattingElement(unsigned& firstUnopenElementIndex) const;
     76    void reconstructTheActiveFormattingElements();
     77
     78    void generateImpliedEndTags();
     79    void generateImpliedEndTagsWithExclusion(const AtomicString& tagName);
     80
     81    Element* currentElement() const { return m_openElements.top(); }
     82    HTMLElementStack* openElements() const { return &m_openElements; }
     83    HTMLFormattingElementList* activeFormattingElements() const { return &m_activeFormattingElements; }
     84
     85    Element* head() const { return m_head.get(); }
     86
     87    Element* form() const { return m_form.get(); }
     88    PassRefPtr<Element> takeForm() { return m_form.release(); }
     89
     90    void setForm(PassRefPtr<Element> form) { m_form = form; }
     91
     92private:
     93    template<typename ChildType>
     94    PassRefPtr<ChildType> attach(Node* parent, PassRefPtr<ChildType> prpChild);
     95
     96    PassRefPtr<Element> createElementAndAttachToCurrent(AtomicHTMLToken&);
     97    void mergeAttributesFromTokenIntoElement(AtomicHTMLToken&, Element*);
     98
     99    Document* m_document;
     100    RefPtr<Element> m_head;
     101    RefPtr<Element> m_form;
     102    mutable HTMLElementStack m_openElements;
     103    mutable HTMLFormattingElementList m_activeFormattingElements;
     104    FragmentScriptingPermission m_fragmentScriptingPermission;
     105};
    51106
    52107class HTMLTreeBuilder : public Noncopyable {
     
    134189    void processFakePEndTagIfPInScope();
    135190
     191    void processGenericRCDATAStartTag(AtomicHTMLToken&);
     192    void processGenericRawTextStartTag(AtomicHTMLToken&);
     193    void processScriptStartTag(AtomicHTMLToken&);
     194
    136195    // Default processing for the different insertion modes.
    137196    // FIXME: These functions need to be renamed to remove "process" from their names.
     
    152211    void closeTheCell();
    153212
    154     template<typename ChildType>
    155     PassRefPtr<ChildType> attach(Node* parent, PassRefPtr<ChildType> prpChild)
    156     {
    157         RefPtr<ChildType> child = prpChild;
    158         parent->parserAddChild(child);
    159         // It's slightly unfortunate that we need to hold a reference to child
    160         // here to call attach().  We should investigate whether we can rely on
    161         // |parent| to hold a ref at this point.  In the common case (at least
    162         // for elements), however, we'll get to use this ref in the stack of
    163         // open elements.
    164         child->attach();
    165         return child.release();
    166     }
    167 
    168     void insertDoctype(AtomicHTMLToken&);
    169     void insertComment(AtomicHTMLToken&);
    170     void insertCommentOnDocument(AtomicHTMLToken&);
    171     void insertCommentOnHTMLHtmlElement(AtomicHTMLToken&);
    172     void insertHTMLHtmlElement(AtomicHTMLToken&);
    173     void insertHTMLHeadElement(AtomicHTMLToken&);
    174     void insertHTMLBodyElement(AtomicHTMLToken&);
    175     void insertElement(AtomicHTMLToken&);
    176     void insertSelfClosingElement(AtomicHTMLToken&);
    177     void insertFormattingElement(AtomicHTMLToken&);
    178     void insertGenericRCDATAElement(AtomicHTMLToken&);
    179     void insertGenericRawTextElement(AtomicHTMLToken&);
    180     void insertScriptElement(AtomicHTMLToken&);
    181     void insertTextNode(AtomicHTMLToken&);
    182 
    183     void insertHTMLStartTagBeforeHTML(AtomicHTMLToken&);
    184     void insertHTMLStartTagInBody(AtomicHTMLToken&);
    185 
    186     PassRefPtr<Element> createElement(AtomicHTMLToken&);
    187     PassRefPtr<Element> createElementAndAttachToCurrent(AtomicHTMLToken&);
    188 
    189     void mergeAttributesFromTokenIntoElement(AtomicHTMLToken&, Element*);
    190 
    191     bool indexOfFirstUnopenFormattingElement(unsigned& firstUnopenElementIndex) const;
    192     void reconstructTheActiveFormattingElements();
    193 
    194     void generateImpliedEndTags();
    195     void generateImpliedEndTagsWithExclusion(const AtomicString& tagName);
    196 
    197     Element* currentElement() { return m_openElements.top(); }
    198 
    199     RefPtr<Element> m_headElement;
    200     RefPtr<Element> m_formElement;
    201     HTMLElementStack m_openElements;
    202     HTMLFormattingElementList m_activeFormattingElements;
    203213    bool m_framesetOk;
    204214
     
    217227    static bool isScriptingFlagEnabled(Frame* frame);
    218228
    219     Document* m_document; // This is only used by the m_legacyParser for now.
     229    Document* m_document;
     230    HTMLConstructionSite m_tree;
     231
    220232    bool m_reportErrors;
    221233    bool m_isPaused;
Note: See TracChangeset for help on using the changeset viewer.