1ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block/*
2ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block * Copyright (C) 2010 Google, Inc. All Rights Reserved.
381bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch * Copyright (C) 2011 Apple Inc. All rights reserved.
4ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block *
5ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block * Redistribution and use in source and binary forms, with or without
6ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block * modification, are permitted provided that the following conditions
7ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block * are met:
8ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block * 1. Redistributions of source code must retain the above copyright
9ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block *    notice, this list of conditions and the following disclaimer.
10ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block * 2. Redistributions in binary form must reproduce the above copyright
11ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block *    notice, this list of conditions and the following disclaimer in the
12ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block *    documentation and/or other materials provided with the distribution.
13ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block *
14ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block * THIS SOFTWARE IS PROVIDED BY GOOGLE INC. ``AS IS'' AND ANY
15ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
17ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL GOOGLE INC. OR
18ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
19ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
20ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
21ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
22ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
23ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
24ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
25ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block */
26ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block
27ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block#include "config.h"
28ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block#include "HTMLElementStack.h"
29ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block
3081bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch#include "DocumentFragment.h"
31ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block#include "Element.h"
32ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block#include "HTMLNames.h"
3368513a70bcd92384395513322f1b801e7bf9c729Steve Block#include "MathMLNames.h"
3468513a70bcd92384395513322f1b801e7bf9c729Steve Block#include "SVGNames.h"
35ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block#include <wtf/PassOwnPtr.h>
36ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block
37ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Blocknamespace WebCore {
38ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block
39ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Blockusing namespace HTMLNames;
40ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block
41ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Blocknamespace {
42ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block
4381bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdochinline bool isNumberedHeaderElement(ContainerNode* node)
440617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen{
4581bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch    return node->hasTagName(h1Tag)
4681bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch        || node->hasTagName(h2Tag)
4781bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch        || node->hasTagName(h3Tag)
4881bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch        || node->hasTagName(h4Tag)
4981bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch        || node->hasTagName(h5Tag)
5081bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch        || node->hasTagName(h6Tag);
5181bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch}
5281bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch
532bde8e466a4451c7319e3a072d118917957d6554Steve Blockinline bool isRootNode(ContainerNode* node)
5481bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch{
5581bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch    return node->nodeType() == Node::DOCUMENT_FRAGMENT_NODE
5681bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch        || node->hasTagName(htmlTag);
570617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen}
580617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen
5981bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdochinline bool isScopeMarker(ContainerNode* node)
60ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block{
6181bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch    return node->hasTagName(appletTag)
6281bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch        || node->hasTagName(captionTag)
6381bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch        || node->hasTagName(marqueeTag)
6481bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch        || node->hasTagName(objectTag)
6581bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch        || node->hasTagName(tableTag)
6681bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch        || node->hasTagName(tdTag)
6781bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch        || node->hasTagName(thTag)
6881bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch        || node->hasTagName(MathMLNames::miTag)
6981bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch        || node->hasTagName(MathMLNames::moTag)
7081bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch        || node->hasTagName(MathMLNames::mnTag)
7181bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch        || node->hasTagName(MathMLNames::msTag)
7281bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch        || node->hasTagName(MathMLNames::mtextTag)
7381bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch        || node->hasTagName(MathMLNames::annotation_xmlTag)
7481bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch        || node->hasTagName(SVGNames::foreignObjectTag)
7581bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch        || node->hasTagName(SVGNames::descTag)
7681bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch        || node->hasTagName(SVGNames::titleTag)
772bde8e466a4451c7319e3a072d118917957d6554Steve Block        || isRootNode(node);
78ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block}
79ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block
8081bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdochinline bool isListItemScopeMarker(ContainerNode* node)
81ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block{
8281bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch    return isScopeMarker(node)
8381bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch        || node->hasTagName(olTag)
8481bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch        || node->hasTagName(ulTag);
85ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block}
86e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarke
8781bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdochinline bool isTableScopeMarker(ContainerNode* node)
88ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block{
8981bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch    return node->hasTagName(tableTag)
902bde8e466a4451c7319e3a072d118917957d6554Steve Block        || isRootNode(node);
91ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block}
92ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block
9381bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdochinline bool isTableBodyScopeMarker(ContainerNode* node)
94ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block{
9581bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch    return node->hasTagName(tbodyTag)
9681bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch        || node->hasTagName(tfootTag)
9781bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch        || node->hasTagName(theadTag)
982bde8e466a4451c7319e3a072d118917957d6554Steve Block        || isRootNode(node);
99ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block}
100ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block
10181bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdochinline bool isTableRowScopeMarker(ContainerNode* node)
102e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarke{
10381bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch    return node->hasTagName(trTag)
1042bde8e466a4451c7319e3a072d118917957d6554Steve Block        || isRootNode(node);
105e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarke}
106e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarke
1072bde8e466a4451c7319e3a072d118917957d6554Steve Blockinline bool isForeignContentScopeMarker(ContainerNode* node)
10868513a70bcd92384395513322f1b801e7bf9c729Steve Block{
1092bde8e466a4451c7319e3a072d118917957d6554Steve Block    return node->hasTagName(MathMLNames::miTag)
1102bde8e466a4451c7319e3a072d118917957d6554Steve Block        || node->hasTagName(MathMLNames::moTag)
1112bde8e466a4451c7319e3a072d118917957d6554Steve Block        || node->hasTagName(MathMLNames::mnTag)
1122bde8e466a4451c7319e3a072d118917957d6554Steve Block        || node->hasTagName(MathMLNames::msTag)
1132bde8e466a4451c7319e3a072d118917957d6554Steve Block        || node->hasTagName(MathMLNames::mtextTag)
1142bde8e466a4451c7319e3a072d118917957d6554Steve Block        || node->hasTagName(SVGNames::foreignObjectTag)
1152bde8e466a4451c7319e3a072d118917957d6554Steve Block        || node->hasTagName(SVGNames::descTag)
1162bde8e466a4451c7319e3a072d118917957d6554Steve Block        || node->hasTagName(SVGNames::titleTag)
1172bde8e466a4451c7319e3a072d118917957d6554Steve Block        || isInHTMLNamespace(node);
11868513a70bcd92384395513322f1b801e7bf9c729Steve Block}
11968513a70bcd92384395513322f1b801e7bf9c729Steve Block
12081bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdochinline bool isButtonScopeMarker(ContainerNode* node)
1210617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen{
12281bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch    return isScopeMarker(node)
12381bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch        || node->hasTagName(buttonTag);
1240617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen}
1250617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen
12681bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdochinline bool isSelectScopeMarker(ContainerNode* node)
127a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch{
12881bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch    return !node->hasTagName(optgroupTag)
12981bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch        && !node->hasTagName(optionTag);
130a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch}
131a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch
132ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block}
133ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block
13481bc750723a18f21cd17d1b173cd2a4dda9cea6eBen MurdochHTMLElementStack::ElementRecord::ElementRecord(PassRefPtr<ContainerNode> node, PassOwnPtr<ElementRecord> next)
13581bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch    : m_node(node)
136ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    , m_next(next)
137ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block{
13881bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch    ASSERT(m_node);
139ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block}
140ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block
141ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve BlockHTMLElementStack::ElementRecord::~ElementRecord()
142ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block{
143ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block}
144ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block
145ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Blockvoid HTMLElementStack::ElementRecord::replaceElement(PassRefPtr<Element> element)
146ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block{
147ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    ASSERT(element);
14881bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch    ASSERT(!m_node || m_node->isElementNode());
149ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    // FIXME: Should this call finishParsingChildren?
15081bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch    m_node = element;
151ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block}
152ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block
153ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Blockbool HTMLElementStack::ElementRecord::isAbove(ElementRecord* other) const
154ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block{
155ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    for (ElementRecord* below = next(); below; below = below->next()) {
156ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block        if (below == other)
157ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block            return true;
158ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    }
159ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    return false;
160ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block}
161ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block
162ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve BlockHTMLElementStack::HTMLElementStack()
16381bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch    : m_rootNode(0)
164ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    , m_headElement(0)
165ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    , m_bodyElement(0)
166ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block{
167ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block}
168ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block
169ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve BlockHTMLElementStack::~HTMLElementStack()
170ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block{
171ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block}
172ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block
173dd8bb3de4f353a81954234999f1fea748aee2ea9Ben Murdochbool HTMLElementStack::hasOnlyOneElement() const
174dd8bb3de4f353a81954234999f1fea748aee2ea9Ben Murdoch{
175dd8bb3de4f353a81954234999f1fea748aee2ea9Ben Murdoch    return !topRecord()->next();
176dd8bb3de4f353a81954234999f1fea748aee2ea9Ben Murdoch}
177dd8bb3de4f353a81954234999f1fea748aee2ea9Ben Murdoch
178dd8bb3de4f353a81954234999f1fea748aee2ea9Ben Murdochbool HTMLElementStack::secondElementIsHTMLBodyElement() const
179dd8bb3de4f353a81954234999f1fea748aee2ea9Ben Murdoch{
180dd8bb3de4f353a81954234999f1fea748aee2ea9Ben Murdoch    // This is used the fragment case of <body> and <frameset> in the "in body"
181dd8bb3de4f353a81954234999f1fea748aee2ea9Ben Murdoch    // insertion mode.
182dd8bb3de4f353a81954234999f1fea748aee2ea9Ben Murdoch    // http://www.whatwg.org/specs/web-apps/current-work/multipage/tokenization.html#parsing-main-inbody
18381bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch    ASSERT(m_rootNode);
184dd8bb3de4f353a81954234999f1fea748aee2ea9Ben Murdoch    // If we have a body element, it must always be the second element on the
185dd8bb3de4f353a81954234999f1fea748aee2ea9Ben Murdoch    // stack, as we always start with an html element, and any other element
186dd8bb3de4f353a81954234999f1fea748aee2ea9Ben Murdoch    // would cause the implicit creation of a body element.
187dd8bb3de4f353a81954234999f1fea748aee2ea9Ben Murdoch    return !!m_bodyElement;
188dd8bb3de4f353a81954234999f1fea748aee2ea9Ben Murdoch}
189dd8bb3de4f353a81954234999f1fea748aee2ea9Ben Murdoch
190ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Blockvoid HTMLElementStack::popHTMLHeadElement()
191ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block{
192ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    ASSERT(top() == m_headElement);
193ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    m_headElement = 0;
194ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    popCommon();
195ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block}
196ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block
197ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Blockvoid HTMLElementStack::popHTMLBodyElement()
198ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block{
199ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    ASSERT(top() == m_bodyElement);
200ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    m_bodyElement = 0;
201ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    popCommon();
202ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block}
203ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block
204967717af5423377c967781471ee106e2bb4e11c8Ben Murdochvoid HTMLElementStack::popAll()
205967717af5423377c967781471ee106e2bb4e11c8Ben Murdoch{
20681bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch    m_rootNode = 0;
207967717af5423377c967781471ee106e2bb4e11c8Ben Murdoch    m_headElement = 0;
208967717af5423377c967781471ee106e2bb4e11c8Ben Murdoch    m_bodyElement = 0;
209967717af5423377c967781471ee106e2bb4e11c8Ben Murdoch    while (m_top) {
21081bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch        topNode()->finishParsingChildren();
211967717af5423377c967781471ee106e2bb4e11c8Ben Murdoch        m_top = m_top->releaseNext();
212967717af5423377c967781471ee106e2bb4e11c8Ben Murdoch    }
213967717af5423377c967781471ee106e2bb4e11c8Ben Murdoch}
214967717af5423377c967781471ee106e2bb4e11c8Ben Murdoch
215ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Blockvoid HTMLElementStack::pop()
216ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block{
217ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    ASSERT(!top()->hasTagName(HTMLNames::headTag));
218ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    popCommon();
219ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block}
220ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block
221ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Blockvoid HTMLElementStack::popUntil(const AtomicString& tagName)
222ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block{
223ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    while (!top()->hasLocalName(tagName)) {
224ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block        // pop() will ASSERT at <body> if callers fail to check that there is an
225ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block        // element with localName |tagName| on the stack of open elements.
226ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block        pop();
227ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    }
228ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block}
229ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block
230e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarkevoid HTMLElementStack::popUntilPopped(const AtomicString& tagName)
231e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarke{
232e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarke    popUntil(tagName);
233e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarke    pop();
234e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarke}
235e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarke
2360617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsenvoid HTMLElementStack::popUntilNumberedHeaderElementPopped()
2370617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen{
23881bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch    while (!isNumberedHeaderElement(topNode()))
2390617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen        pop();
2400617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen    pop();
2410617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen}
2420617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen
243ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Blockvoid HTMLElementStack::popUntil(Element* element)
244ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block{
245ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    while (top() != element)
246ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block        pop();
247ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block}
248ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block
249e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarkevoid HTMLElementStack::popUntilPopped(Element* element)
250e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarke{
251e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarke    popUntil(element);
252e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarke    pop();
253e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarke}
254e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarke
255ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Blockvoid HTMLElementStack::popUntilTableScopeMarker()
256ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block{
257ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    // http://www.whatwg.org/specs/web-apps/current-work/multipage/tokenization.html#clear-the-stack-back-to-a-table-context
25881bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch    while (!isTableScopeMarker(topNode()))
259ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block        pop();
260ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block}
261ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block
262ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Blockvoid HTMLElementStack::popUntilTableBodyScopeMarker()
263ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block{
264ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    // http://www.whatwg.org/specs/web-apps/current-work/multipage/tokenization.html#clear-the-stack-back-to-a-table-body-context
26581bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch    while (!isTableBodyScopeMarker(topNode()))
266ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block        pop();
267ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block}
268ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block
269e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarkevoid HTMLElementStack::popUntilTableRowScopeMarker()
270e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarke{
271e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarke    // http://www.whatwg.org/specs/web-apps/current-work/multipage/tokenization.html#clear-the-stack-back-to-a-table-row-context
27281bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch    while (!isTableRowScopeMarker(topNode()))
273e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarke        pop();
274e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarke}
275e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarke
27668513a70bcd92384395513322f1b801e7bf9c729Steve Blockvoid HTMLElementStack::popUntilForeignContentScopeMarker()
27768513a70bcd92384395513322f1b801e7bf9c729Steve Block{
2782bde8e466a4451c7319e3a072d118917957d6554Steve Block    while (!isForeignContentScopeMarker(topNode()))
27968513a70bcd92384395513322f1b801e7bf9c729Steve Block        pop();
28068513a70bcd92384395513322f1b801e7bf9c729Steve Block}
28181bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch
28281bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdochvoid HTMLElementStack::pushRootNode(PassRefPtr<ContainerNode> rootNode)
28381bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch{
28481bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch    ASSERT(rootNode->nodeType() == Node::DOCUMENT_FRAGMENT_NODE);
28581bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch    pushRootNodeCommon(rootNode);
28681bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch}
28768513a70bcd92384395513322f1b801e7bf9c729Steve Block
288ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Blockvoid HTMLElementStack::pushHTMLHtmlElement(PassRefPtr<Element> element)
289ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block{
290ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    ASSERT(element->hasTagName(HTMLNames::htmlTag));
29181bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch    pushRootNodeCommon(element);
29281bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch}
29381bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch
29481bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdochvoid HTMLElementStack::pushRootNodeCommon(PassRefPtr<ContainerNode> rootNode)
29581bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch{
29681bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch    ASSERT(!m_top);
29781bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch    ASSERT(!m_rootNode);
29881bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch    m_rootNode = rootNode.get();
29981bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch    pushCommon(rootNode);
300ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block}
301ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block
302ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Blockvoid HTMLElementStack::pushHTMLHeadElement(PassRefPtr<Element> element)
303ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block{
304ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    ASSERT(element->hasTagName(HTMLNames::headTag));
305ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    ASSERT(!m_headElement);
306ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    m_headElement = element.get();
307ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    pushCommon(element);
308ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block}
309ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block
310ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Blockvoid HTMLElementStack::pushHTMLBodyElement(PassRefPtr<Element> element)
311ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block{
312ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    ASSERT(element->hasTagName(HTMLNames::bodyTag));
313ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    ASSERT(!m_bodyElement);
314ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    m_bodyElement = element.get();
315ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    pushCommon(element);
316ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block}
317ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block
318ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Blockvoid HTMLElementStack::push(PassRefPtr<Element> element)
319ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block{
320ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    ASSERT(!element->hasTagName(HTMLNames::htmlTag));
321ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    ASSERT(!element->hasTagName(HTMLNames::headTag));
322ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    ASSERT(!element->hasTagName(HTMLNames::bodyTag));
32381bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch    ASSERT(m_rootNode);
324ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    pushCommon(element);
325ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block}
326ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block
327ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Blockvoid HTMLElementStack::insertAbove(PassRefPtr<Element> element, ElementRecord* recordBelow)
328ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block{
329ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    ASSERT(element);
330ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    ASSERT(recordBelow);
331ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    ASSERT(m_top);
332ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    ASSERT(!element->hasTagName(HTMLNames::htmlTag));
333ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    ASSERT(!element->hasTagName(HTMLNames::headTag));
334ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    ASSERT(!element->hasTagName(HTMLNames::bodyTag));
33581bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch    ASSERT(m_rootNode);
336ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    if (recordBelow == m_top) {
337ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block        push(element);
338ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block        return;
339ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    }
340ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block
341ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    for (ElementRecord* recordAbove = m_top.get(); recordAbove; recordAbove = recordAbove->next()) {
342ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block        if (recordAbove->next() != recordBelow)
343ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block            continue;
344ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block
345e8b154fd68f9b33be40a3590e58347f353835f5cSteve Block        recordAbove->setNext(adoptPtr(new ElementRecord(element, recordAbove->releaseNext())));
346ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block        recordAbove->next()->element()->beginParsingChildren();
347ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block        return;
348ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    }
349ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    ASSERT_NOT_REACHED();
350ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block}
351ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block
352ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve BlockHTMLElementStack::ElementRecord* HTMLElementStack::topRecord() const
353ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block{
354e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarke    ASSERT(m_top);
355ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    return m_top.get();
356ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block}
357ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block
358e458d70a0d18538346f41b503114c9ebe6b2ce12Leon ClarkeElement* HTMLElementStack::oneBelowTop() const
359e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarke{
360e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarke    // We should never be calling this if it could be 0.
361e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarke    ASSERT(m_top);
362e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarke    ASSERT(m_top->next());
363e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarke    return m_top->next()->element();
364e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarke}
365e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarke
366ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve BlockElement* HTMLElementStack::bottom() const
367ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block{
368ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    return htmlElement();
369ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block}
370ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block
371ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Blockvoid HTMLElementStack::removeHTMLHeadElement(Element* element)
372ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block{
373ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    ASSERT(m_headElement == element);
374ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    if (m_top->element() == element) {
375ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block        popHTMLHeadElement();
376ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block        return;
377ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    }
378ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    m_headElement = 0;
379ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    removeNonTopCommon(element);
380ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block}
381ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block
382ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Blockvoid HTMLElementStack::remove(Element* element)
383ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block{
384ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    ASSERT(!element->hasTagName(HTMLNames::headTag));
385ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    if (m_top->element() == element) {
386ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block        pop();
387ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block        return;
388ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    }
389ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    removeNonTopCommon(element);
390ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block}
391ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block
392ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve BlockHTMLElementStack::ElementRecord* HTMLElementStack::find(Element* element) const
393ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block{
394ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    for (ElementRecord* pos = m_top.get(); pos; pos = pos->next()) {
39581bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch        if (pos->node() == element)
396ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block            return pos;
397ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    }
398ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    return 0;
399ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block}
400ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block
401ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve BlockHTMLElementStack::ElementRecord* HTMLElementStack::topmost(const AtomicString& tagName) const
402ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block{
403ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    for (ElementRecord* pos = m_top.get(); pos; pos = pos->next()) {
40481bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch        if (pos->node()->hasLocalName(tagName))
405ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block            return pos;
406ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    }
407ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    return 0;
408ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block}
409ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block
410ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Blockbool HTMLElementStack::contains(Element* element) const
411ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block{
412ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    return !!find(element);
413ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block}
414ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block
415967717af5423377c967781471ee106e2bb4e11c8Ben Murdochbool HTMLElementStack::contains(const AtomicString& tagName) const
416967717af5423377c967781471ee106e2bb4e11c8Ben Murdoch{
417967717af5423377c967781471ee106e2bb4e11c8Ben Murdoch    return !!topmost(tagName);
418967717af5423377c967781471ee106e2bb4e11c8Ben Murdoch}
419967717af5423377c967781471ee106e2bb4e11c8Ben Murdoch
42081bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdochtemplate <bool isMarker(ContainerNode*)>
421ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Blockbool inScopeCommon(HTMLElementStack::ElementRecord* top, const AtomicString& targetTag)
422ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block{
423ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    for (HTMLElementStack::ElementRecord* pos = top; pos; pos = pos->next()) {
42481bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch        ContainerNode* node = pos->node();
42581bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch        if (node->hasLocalName(targetTag))
426ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block            return true;
42781bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch        if (isMarker(node))
428ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block            return false;
429ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    }
430ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    ASSERT_NOT_REACHED(); // <html> is always on the stack and is a scope marker.
431ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    return false;
432ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block}
433ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block
434e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarkebool HTMLElementStack::hasOnlyHTMLElementsInScope() const
435e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarke{
436e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarke    for (ElementRecord* record = m_top.get(); record; record = record->next()) {
4372bde8e466a4451c7319e3a072d118917957d6554Steve Block        ContainerNode* node = record->node();
4382bde8e466a4451c7319e3a072d118917957d6554Steve Block        if (!isInHTMLNamespace(node))
439e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarke            return false;
4402bde8e466a4451c7319e3a072d118917957d6554Steve Block        if (isScopeMarker(node))
441e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarke            return true;
442e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarke    }
443e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarke    ASSERT_NOT_REACHED(); // <html> is always on the stack and is a scope marker.
444e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarke    return true;
445e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarke}
446e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarke
4470617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsenbool HTMLElementStack::hasNumberedHeaderElementInScope() const
4480617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen{
4490617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen    for (ElementRecord* record = m_top.get(); record; record = record->next()) {
45081bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch        ContainerNode* node = record->node();
45181bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch        if (isNumberedHeaderElement(node))
4520617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen            return true;
45381bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch        if (isScopeMarker(node))
4540617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen            return false;
4550617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen    }
4560617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen    ASSERT_NOT_REACHED(); // <html> is always on the stack and is a scope marker.
4570617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen    return false;
4580617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen}
4590617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen
460ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Blockbool HTMLElementStack::inScope(Element* targetElement) const
461ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block{
462ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    for (ElementRecord* pos = m_top.get(); pos; pos = pos->next()) {
4632bde8e466a4451c7319e3a072d118917957d6554Steve Block        ContainerNode* node = pos->node();
4642bde8e466a4451c7319e3a072d118917957d6554Steve Block        if (node == targetElement)
465ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block            return true;
4662bde8e466a4451c7319e3a072d118917957d6554Steve Block        if (isScopeMarker(node))
467ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block            return false;
468ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    }
469ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    ASSERT_NOT_REACHED(); // <html> is always on the stack and is a scope marker.
470ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    return false;
471ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block}
472ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block
473ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Blockbool HTMLElementStack::inScope(const AtomicString& targetTag) const
474ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block{
475ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    return inScopeCommon<isScopeMarker>(m_top.get(), targetTag);
476ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block}
477ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block
478e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarkebool HTMLElementStack::inScope(const QualifiedName& tagName) const
479e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarke{
480e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarke    // FIXME: Is localName() right for non-html elements?
481e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarke    return inScope(tagName.localName());
482e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarke}
483e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarke
484ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Blockbool HTMLElementStack::inListItemScope(const AtomicString& targetTag) const
485ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block{
486ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    return inScopeCommon<isListItemScopeMarker>(m_top.get(), targetTag);
487ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block}
488ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block
489e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarkebool HTMLElementStack::inListItemScope(const QualifiedName& tagName) const
490e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarke{
491e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarke    // FIXME: Is localName() right for non-html elements?
492e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarke    return inListItemScope(tagName.localName());
493e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarke}
494e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarke
495ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Blockbool HTMLElementStack::inTableScope(const AtomicString& targetTag) const
496ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block{
497ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    return inScopeCommon<isTableScopeMarker>(m_top.get(), targetTag);
498ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block}
499ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block
500e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarkebool HTMLElementStack::inTableScope(const QualifiedName& tagName) const
501e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarke{
502e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarke    // FIXME: Is localName() right for non-html elements?
503e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarke    return inTableScope(tagName.localName());
504e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarke}
505e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarke
5060617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsenbool HTMLElementStack::inButtonScope(const AtomicString& targetTag) const
5070617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen{
5080617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen    return inScopeCommon<isButtonScopeMarker>(m_top.get(), targetTag);
5090617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen}
5100617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen
5110617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsenbool HTMLElementStack::inButtonScope(const QualifiedName& tagName) const
5120617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen{
5130617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen    // FIXME: Is localName() right for non-html elements?
5140617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen    return inButtonScope(tagName.localName());
5150617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen}
5160617145a89917ae7735fe1c9538688ab9a577df5Kristian Monsen
517a94275402997c11dd2e778633dacf4b7e630a35dBen Murdochbool HTMLElementStack::inSelectScope(const AtomicString& targetTag) const
518a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch{
519a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch    return inScopeCommon<isSelectScopeMarker>(m_top.get(), targetTag);
520a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch}
521a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch
522a94275402997c11dd2e778633dacf4b7e630a35dBen Murdochbool HTMLElementStack::inSelectScope(const QualifiedName& tagName) const
523a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch{
524a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch    // FIXME: Is localName() right for non-html elements?
525a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch    return inSelectScope(tagName.localName());
526a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch}
527a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch
528ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve BlockElement* HTMLElementStack::htmlElement() const
529ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block{
53081bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch    ASSERT(m_rootNode);
53181bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch    return toElement(m_rootNode);
532ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block}
533ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block
534ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve BlockElement* HTMLElementStack::headElement() const
535ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block{
536ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    ASSERT(m_headElement);
537ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    return m_headElement;
538ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block}
539ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block
540ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve BlockElement* HTMLElementStack::bodyElement() const
541ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block{
542ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    ASSERT(m_bodyElement);
543ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    return m_bodyElement;
544ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block}
54581bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch
54681bc750723a18f21cd17d1b173cd2a4dda9cea6eBen MurdochContainerNode* HTMLElementStack::rootNode() const
54781bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch{
54881bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch    ASSERT(m_rootNode);
54981bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch    return m_rootNode;
55081bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch}
551ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block
55281bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdochvoid HTMLElementStack::pushCommon(PassRefPtr<ContainerNode> node)
553ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block{
55481bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch    ASSERT(m_rootNode);
55581bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch    m_top = adoptPtr(new ElementRecord(node, m_top.release()));
55681bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch    topNode()->beginParsingChildren();
557ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block}
558ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block
559ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Blockvoid HTMLElementStack::popCommon()
560ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block{
561ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    ASSERT(!top()->hasTagName(HTMLNames::htmlTag));
562ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    ASSERT(!top()->hasTagName(HTMLNames::headTag) || !m_headElement);
563ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    ASSERT(!top()->hasTagName(HTMLNames::bodyTag) || !m_bodyElement);
564ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    top()->finishParsingChildren();
565ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    m_top = m_top->releaseNext();
566ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block}
567ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block
568ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Blockvoid HTMLElementStack::removeNonTopCommon(Element* element)
569ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block{
570ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    ASSERT(!element->hasTagName(HTMLNames::htmlTag));
571ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    ASSERT(!element->hasTagName(HTMLNames::bodyTag));
572ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    ASSERT(top() != element);
573ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    for (ElementRecord* pos = m_top.get(); pos; pos = pos->next()) {
574ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block        if (pos->next()->element() == element) {
575ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block            // FIXME: Is it OK to call finishParsingChildren()
576ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block            // when the children aren't actually finished?
577ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block            element->finishParsingChildren();
578ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block            pos->setNext(pos->next()->releaseNext());
579ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block            return;
580ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block        }
581ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    }
582ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block    ASSERT_NOT_REACHED();
583ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block}
584ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block
585e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarke#ifndef NDEBUG
586e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarke
587e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarkevoid HTMLElementStack::show()
588e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarke{
589e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarke    for (ElementRecord* record = m_top.get(); record; record = record->next())
590e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarke        record->element()->showNode();
591e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarke}
592e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarke
593e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarke#endif
594e458d70a0d18538346f41b503114c9ebe6b2ce12Leon Clarke
595ca9cb53ed1119a3fd98fafa0972ffeb56dee1c24Steve Block}
596