1/*
2 * Copyright (C) 1999 Lars Knoll (knoll@kde.org)
3 *           (C) 1999 Antti Koivisto (koivisto@kde.org)
4 *           (C) 2001 Dirk Mueller (mueller@kde.org)
5 * Copyright (C) 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011 Apple Inc. All rights reserved.
6 * Copyright (C) 2008 Nokia Corporation and/or its subsidiary(-ies)
7 * Copyright (C) 2009 Torch Mobile Inc. All rights reserved. (http://www.torchmobile.com/)
8 *
9 * This library is free software; you can redistribute it and/or
10 * modify it under the terms of the GNU Library General Public
11 * License as published by the Free Software Foundation; either
12 * version 2 of the License, or (at your option) any later version.
13 *
14 * This library is distributed in the hope that it will be useful,
15 * but WITHOUT ANY WARRANTY; without even the implied warranty of
16 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
17 * Library General Public License for more details.
18 *
19 * You should have received a copy of the GNU Library General Public License
20 * along with this library; see the file COPYING.LIB.  If not, write to
21 * the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
22 * Boston, MA 02110-1301, USA.
23 */
24
25#include "config.h"
26#include "core/dom/Node.h"
27
28#include "HTMLNames.h"
29#include "XMLNames.h"
30#include "bindings/v8/ExceptionState.h"
31#include "bindings/v8/ExceptionStatePlaceholder.h"
32#include "core/accessibility/AXObjectCache.h"
33#include "core/dom/Attr.h"
34#include "core/dom/Attribute.h"
35#include "core/dom/BeforeLoadEvent.h"
36#include "core/dom/ChildListMutationScope.h"
37#include "core/dom/ChildNodeList.h"
38#include "core/dom/ClassNodeList.h"
39#include "core/dom/DOMImplementation.h"
40#include "core/dom/Document.h"
41#include "core/dom/DocumentFragment.h"
42#include "core/dom/DocumentType.h"
43#include "core/dom/Element.h"
44#include "core/dom/ElementRareData.h"
45#include "core/dom/Event.h"
46#include "core/dom/EventDispatchMediator.h"
47#include "core/dom/EventDispatcher.h"
48#include "core/dom/EventListener.h"
49#include "core/dom/EventNames.h"
50#include "core/dom/ExceptionCode.h"
51#include "core/dom/GestureEvent.h"
52#include "core/dom/KeyboardEvent.h"
53#include "core/dom/LiveNodeList.h"
54#include "core/dom/MouseEvent.h"
55#include "core/dom/MutationEvent.h"
56#include "core/dom/NameNodeList.h"
57#include "core/dom/NodeRareData.h"
58#include "core/dom/NodeTraversal.h"
59#include "core/dom/ProcessingInstruction.h"
60#include "core/dom/SelectorQuery.h"
61#include "core/dom/TagNodeList.h"
62#include "core/dom/TemplateContentDocumentFragment.h"
63#include "core/dom/Text.h"
64#include "core/dom/TextEvent.h"
65#include "core/dom/TouchEvent.h"
66#include "core/dom/TreeScopeAdopter.h"
67#include "core/dom/UIEvent.h"
68#include "core/dom/UserActionElementSet.h"
69#include "core/dom/WheelEvent.h"
70#include "core/dom/shadow/ElementShadow.h"
71#include "core/dom/shadow/InsertionPoint.h"
72#include "core/dom/shadow/ShadowRoot.h"
73#include "core/editing/htmlediting.h"
74#include "core/html/HTMLFrameOwnerElement.h"
75#include "core/html/HTMLStyleElement.h"
76#include "core/html/RadioNodeList.h"
77#include "core/inspector/InspectorCounters.h"
78#include "core/page/ContextMenuController.h"
79#include "core/page/EventHandler.h"
80#include "core/page/Frame.h"
81#include "core/page/Page.h"
82#include "core/page/Settings.h"
83#include "core/platform/Partitions.h"
84#include "core/rendering/FlowThreadController.h"
85#include "core/rendering/RenderBox.h"
86#include "wtf/HashSet.h"
87#include "wtf/PassOwnPtr.h"
88#include "wtf/RefCountedLeakCounter.h"
89#include "wtf/UnusedParam.h"
90#include "wtf/Vector.h"
91#include "wtf/text/CString.h"
92#include "wtf/text/StringBuilder.h"
93
94using namespace std;
95
96namespace WebCore {
97
98using namespace HTMLNames;
99
100void* Node::operator new(size_t size)
101{
102    ASSERT(isMainThread());
103    return partitionAlloc(Partitions::getObjectModelPartition(), size);
104}
105
106void Node::operator delete(void* ptr)
107{
108    ASSERT(isMainThread());
109    partitionFree(ptr);
110}
111
112bool Node::isSupported(const String& feature, const String& version)
113{
114    return DOMImplementation::hasFeature(feature, version);
115}
116
117#if DUMP_NODE_STATISTICS
118static HashSet<Node*> liveNodeSet;
119#endif
120
121void Node::dumpStatistics()
122{
123#if DUMP_NODE_STATISTICS
124    size_t nodesWithRareData = 0;
125
126    size_t elementNodes = 0;
127    size_t attrNodes = 0;
128    size_t textNodes = 0;
129    size_t cdataNodes = 0;
130    size_t commentNodes = 0;
131    size_t entityNodes = 0;
132    size_t piNodes = 0;
133    size_t documentNodes = 0;
134    size_t docTypeNodes = 0;
135    size_t fragmentNodes = 0;
136    size_t notationNodes = 0;
137    size_t xpathNSNodes = 0;
138    size_t shadowRootNodes = 0;
139
140    HashMap<String, size_t> perTagCount;
141
142    size_t attributes = 0;
143    size_t attributesWithAttr = 0;
144    size_t elementsWithAttributeStorage = 0;
145    size_t elementsWithRareData = 0;
146    size_t elementsWithNamedNodeMap = 0;
147
148    for (HashSet<Node*>::iterator it = liveNodeSet.begin(); it != liveNodeSet.end(); ++it) {
149        Node* node = *it;
150
151        if (node->hasRareData()) {
152            ++nodesWithRareData;
153            if (node->isElementNode()) {
154                ++elementsWithRareData;
155                if (toElement(node)->hasNamedNodeMap())
156                    ++elementsWithNamedNodeMap;
157            }
158        }
159
160        switch (node->nodeType()) {
161            case ELEMENT_NODE: {
162                ++elementNodes;
163
164                // Tag stats
165                Element* element = toElement(node);
166                HashMap<String, size_t>::AddResult result = perTagCount.add(element->tagName(), 1);
167                if (!result.isNewEntry)
168                    result.iterator->value++;
169
170                if (ElementData* elementData = element->elementData()) {
171                    attributes += elementData->length();
172                    ++elementsWithAttributeStorage;
173                    for (unsigned i = 0; i < elementData->length(); ++i) {
174                        Attribute* attr = elementData->attributeItem(i);
175                        if (attr->attr())
176                            ++attributesWithAttr;
177                    }
178                }
179                break;
180            }
181            case ATTRIBUTE_NODE: {
182                ++attrNodes;
183                break;
184            }
185            case TEXT_NODE: {
186                ++textNodes;
187                break;
188            }
189            case CDATA_SECTION_NODE: {
190                ++cdataNodes;
191                break;
192            }
193            case COMMENT_NODE: {
194                ++commentNodes;
195                break;
196            }
197            case ENTITY_NODE: {
198                ++entityNodes;
199                break;
200            }
201            case PROCESSING_INSTRUCTION_NODE: {
202                ++piNodes;
203                break;
204            }
205            case DOCUMENT_NODE: {
206                ++documentNodes;
207                break;
208            }
209            case DOCUMENT_TYPE_NODE: {
210                ++docTypeNodes;
211                break;
212            }
213            case DOCUMENT_FRAGMENT_NODE: {
214                if (node->isShadowRoot())
215                    ++shadowRootNodes;
216                else
217                    ++fragmentNodes;
218                break;
219            }
220            case NOTATION_NODE: {
221                ++notationNodes;
222                break;
223            }
224            case XPATH_NAMESPACE_NODE: {
225                ++xpathNSNodes;
226                break;
227            }
228        }
229    }
230
231    printf("Number of Nodes: %d\n\n", liveNodeSet.size());
232    printf("Number of Nodes with RareData: %zu\n\n", nodesWithRareData);
233
234    printf("NodeType distribution:\n");
235    printf("  Number of Element nodes: %zu\n", elementNodes);
236    printf("  Number of Attribute nodes: %zu\n", attrNodes);
237    printf("  Number of Text nodes: %zu\n", textNodes);
238    printf("  Number of CDATASection nodes: %zu\n", cdataNodes);
239    printf("  Number of Comment nodes: %zu\n", commentNodes);
240    printf("  Number of Entity nodes: %zu\n", entityNodes);
241    printf("  Number of ProcessingInstruction nodes: %zu\n", piNodes);
242    printf("  Number of Document nodes: %zu\n", documentNodes);
243    printf("  Number of DocumentType nodes: %zu\n", docTypeNodes);
244    printf("  Number of DocumentFragment nodes: %zu\n", fragmentNodes);
245    printf("  Number of Notation nodes: %zu\n", notationNodes);
246    printf("  Number of XPathNS nodes: %zu\n", xpathNSNodes);
247    printf("  Number of ShadowRoot nodes: %zu\n", shadowRootNodes);
248
249    printf("Element tag name distibution:\n");
250    for (HashMap<String, size_t>::iterator it = perTagCount.begin(); it != perTagCount.end(); ++it)
251        printf("  Number of <%s> tags: %zu\n", it->key.utf8().data(), it->value);
252
253    printf("Attributes:\n");
254    printf("  Number of Attributes (non-Node and Node): %zu [%zu]\n", attributes, sizeof(Attribute));
255    printf("  Number of Attributes with an Attr: %zu\n", attributesWithAttr);
256    printf("  Number of Elements with attribute storage: %zu [%zu]\n", elementsWithAttributeStorage, sizeof(ElementData));
257    printf("  Number of Elements with RareData: %zu\n", elementsWithRareData);
258    printf("  Number of Elements with NamedNodeMap: %zu [%zu]\n", elementsWithNamedNodeMap, sizeof(NamedNodeMap));
259#endif
260}
261
262DEFINE_DEBUG_ONLY_GLOBAL(WTF::RefCountedLeakCounter, nodeCounter, ("WebCoreNode"));
263
264Node::StyleChange Node::diff(const RenderStyle* s1, const RenderStyle* s2, Document* doc)
265{
266    StyleChange ch = NoInherit;
267    EDisplay display1 = s1 ? s1->display() : NONE;
268    bool fl1 = s1 && s1->hasPseudoStyle(FIRST_LETTER);
269    EDisplay display2 = s2 ? s2->display() : NONE;
270    bool fl2 = s2 && s2->hasPseudoStyle(FIRST_LETTER);
271
272    // We just detach if a renderer acquires or loses a column-span, since spanning elements
273    // typically won't contain much content.
274    bool colSpan1 = s1 && s1->columnSpan();
275    bool colSpan2 = s2 && s2->columnSpan();
276
277    bool specifiesColumns1 = s1 && (!s1->hasAutoColumnCount() || !s1->hasAutoColumnWidth());
278    bool specifiesColumns2 = s2 && (!s2->hasAutoColumnCount() || !s2->hasAutoColumnWidth());
279
280    if (display1 != display2 || fl1 != fl2 || colSpan1 != colSpan2
281        || (specifiesColumns1 != specifiesColumns2 && doc->settings()->regionBasedColumnsEnabled())
282        || (s1 && s2 && !s1->contentDataEquivalent(s2)))
283        ch = Detach;
284    else if (!s1 || !s2)
285        ch = Inherit;
286    else if (*s1 == *s2)
287        ch = NoChange;
288    else if (s1->inheritedNotEqual(s2))
289        ch = Inherit;
290    else if (s1->hasExplicitlyInheritedProperties() || s2->hasExplicitlyInheritedProperties())
291        ch = Inherit;
292
293    // If the pseudoStyles have changed, we want any StyleChange that is not NoChange
294    // because setStyle will do the right thing with anything else.
295    if (ch == NoChange && s1->hasAnyPublicPseudoStyles()) {
296        for (PseudoId pseudoId = FIRST_PUBLIC_PSEUDOID; ch == NoChange && pseudoId < FIRST_INTERNAL_PSEUDOID; pseudoId = static_cast<PseudoId>(pseudoId + 1)) {
297            if (s1->hasPseudoStyle(pseudoId)) {
298                RenderStyle* ps2 = s2->getCachedPseudoStyle(pseudoId);
299                if (!ps2)
300                    ch = NoInherit;
301                else {
302                    RenderStyle* ps1 = s1->getCachedPseudoStyle(pseudoId);
303                    ch = ps1 && *ps1 == *ps2 ? NoChange : NoInherit;
304                }
305            }
306        }
307    }
308
309    // When text-combine property has been changed, we need to prepare a separate renderer object.
310    // When text-combine is on, we use RenderCombineText, otherwise RenderText.
311    // https://bugs.webkit.org/show_bug.cgi?id=55069
312    if ((s1 && s2) && (s1->hasTextCombine() != s2->hasTextCombine()))
313        ch = Detach;
314
315    // We need to reattach the node, so that it is moved to the correct RenderFlowThread.
316    if ((s1 && s2) && (s1->flowThread() != s2->flowThread()))
317        ch = Detach;
318
319    // When the region thread has changed, we need to prepare a separate render region object.
320    if ((s1 && s2) && (s1->regionThread() != s2->regionThread()))
321        ch = Detach;
322
323    return ch;
324}
325
326void Node::trackForDebugging()
327{
328#ifndef NDEBUG
329    nodeCounter.increment();
330#endif
331
332#if DUMP_NODE_STATISTICS
333    liveNodeSet.add(this);
334#endif
335}
336
337Node::~Node()
338{
339#ifndef NDEBUG
340    nodeCounter.decrement();
341#endif
342
343#if DUMP_NODE_STATISTICS
344    liveNodeSet.remove(this);
345#endif
346
347    if (hasRareData())
348        clearRareData();
349
350    if (renderer())
351        detach();
352
353    if (!isContainerNode()) {
354        if (Document* document = documentInternal())
355            willBeDeletedFrom(document);
356    }
357
358    if (m_previous)
359        m_previous->setNextSibling(0);
360    if (m_next)
361        m_next->setPreviousSibling(0);
362
363    m_treeScope->guardDeref();
364
365    InspectorCounters::decrementCounter(InspectorCounters::NodeCounter);
366}
367
368void Node::willBeDeletedFrom(Document* document)
369{
370    if (hasEventTargetData()) {
371        if (document)
372            document->didRemoveEventTargetNode(this);
373        clearEventTargetData();
374    }
375
376    if (document) {
377        if (AXObjectCache* cache = document->existingAXObjectCache())
378            cache->remove(this);
379    }
380}
381
382NodeRareData* Node::rareData() const
383{
384    ASSERT(hasRareData());
385    return static_cast<NodeRareData*>(m_data.m_rareData);
386}
387
388NodeRareData* Node::ensureRareData()
389{
390    if (hasRareData())
391        return rareData();
392
393    NodeRareData* data;
394    if (isElementNode())
395        data = ElementRareData::create(m_data.m_renderer).leakPtr();
396    else
397        data = NodeRareData::create(m_data.m_renderer).leakPtr();
398    ASSERT(data);
399
400    m_data.m_rareData = data;
401    setFlag(HasRareDataFlag);
402    return data;
403}
404
405void Node::clearRareData()
406{
407    ASSERT(hasRareData());
408    ASSERT(!transientMutationObserverRegistry() || transientMutationObserverRegistry()->isEmpty());
409
410    RenderObject* renderer = m_data.m_rareData->renderer();
411    if (isElementNode())
412        delete static_cast<ElementRareData*>(m_data.m_rareData);
413    else
414        delete static_cast<NodeRareData*>(m_data.m_rareData);
415    m_data.m_renderer = renderer;
416    clearFlag(HasRareDataFlag);
417}
418
419Node* Node::toNode()
420{
421    return this;
422}
423
424short Node::tabIndex() const
425{
426    return 0;
427}
428
429String Node::nodeValue() const
430{
431    return String();
432}
433
434void Node::setNodeValue(const String&)
435{
436    // By default, setting nodeValue has no effect.
437}
438
439PassRefPtr<NodeList> Node::childNodes()
440{
441    return ensureRareData()->ensureNodeLists()->ensureChildNodeList(this);
442}
443
444Node *Node::lastDescendant() const
445{
446    Node *n = const_cast<Node *>(this);
447    while (n && n->lastChild())
448        n = n->lastChild();
449    return n;
450}
451
452Node* Node::firstDescendant() const
453{
454    Node *n = const_cast<Node *>(this);
455    while (n && n->firstChild())
456        n = n->firstChild();
457    return n;
458}
459
460Node* Node::pseudoAwarePreviousSibling() const
461{
462    if (parentElement() && !previousSibling()) {
463        Element* parent = parentElement();
464        if (isAfterPseudoElement() && parent->lastChild())
465            return parent->lastChild();
466        if (!isBeforePseudoElement())
467            return parent->pseudoElement(BEFORE);
468    }
469    return previousSibling();
470}
471
472Node* Node::pseudoAwareNextSibling() const
473{
474    if (parentElement() && !nextSibling()) {
475        Element* parent = parentElement();
476        if (isBeforePseudoElement() && parent->firstChild())
477            return parent->firstChild();
478        if (!isAfterPseudoElement())
479            return parent->pseudoElement(AFTER);
480    }
481    return nextSibling();
482}
483
484Node* Node::pseudoAwareFirstChild() const
485{
486    if (isElementNode()) {
487        const Element* currentElement = toElement(this);
488        Node* first = currentElement->pseudoElement(BEFORE);
489        if (first)
490            return first;
491        first = currentElement->firstChild();
492        if (!first)
493            first = currentElement->pseudoElement(AFTER);
494        return first;
495    }
496
497    return firstChild();
498}
499
500Node* Node::pseudoAwareLastChild() const
501{
502    if (isElementNode()) {
503        const Element* currentElement = toElement(this);
504        Node* last = currentElement->pseudoElement(AFTER);
505        if (last)
506            return last;
507        last = currentElement->lastChild();
508        if (!last)
509            last = currentElement->pseudoElement(BEFORE);
510        return last;
511    }
512
513    return lastChild();
514}
515
516void Node::insertBefore(PassRefPtr<Node> newChild, Node* refChild, ExceptionState& es, AttachBehavior attachBehavior)
517{
518    if (isContainerNode())
519        toContainerNode(this)->insertBefore(newChild, refChild, es, attachBehavior);
520    else
521        es.throwDOMException(HierarchyRequestError);
522}
523
524void Node::replaceChild(PassRefPtr<Node> newChild, Node* oldChild, ExceptionState& es, AttachBehavior attachBehavior)
525{
526    if (isContainerNode())
527        toContainerNode(this)->replaceChild(newChild, oldChild, es, attachBehavior);
528    else
529        es.throwDOMException(HierarchyRequestError);
530}
531
532void Node::removeChild(Node* oldChild, ExceptionState& es)
533{
534    if (isContainerNode())
535        toContainerNode(this)->removeChild(oldChild, es);
536    else
537        es.throwDOMException(NotFoundError);
538}
539
540void Node::appendChild(PassRefPtr<Node> newChild, ExceptionState& es, AttachBehavior attachBehavior)
541{
542    if (isContainerNode())
543        toContainerNode(this)->appendChild(newChild, es, attachBehavior);
544    else
545        es.throwDOMException(HierarchyRequestError);
546}
547
548void Node::remove(ExceptionState& es)
549{
550    if (ContainerNode* parent = parentNode())
551        parent->removeChild(this, es);
552}
553
554void Node::normalize()
555{
556    // Go through the subtree beneath us, normalizing all nodes. This means that
557    // any two adjacent text nodes are merged and any empty text nodes are removed.
558
559    RefPtr<Node> node = this;
560    while (Node* firstChild = node->firstChild())
561        node = firstChild;
562    while (node) {
563        NodeType type = node->nodeType();
564        if (type == ELEMENT_NODE)
565            toElement(node.get())->normalizeAttributes();
566
567        if (node == this)
568            break;
569
570        if (type != TEXT_NODE) {
571            node = NodeTraversal::nextPostOrder(node.get());
572            continue;
573        }
574
575        RefPtr<Text> text = toText(node.get());
576
577        // Remove empty text nodes.
578        if (!text->length()) {
579            // Care must be taken to get the next node before removing the current node.
580            node = NodeTraversal::nextPostOrder(node.get());
581            text->remove(IGNORE_EXCEPTION);
582            continue;
583        }
584
585        // Merge text nodes.
586        while (Node* nextSibling = node->nextSibling()) {
587            if (nextSibling->nodeType() != TEXT_NODE)
588                break;
589            RefPtr<Text> nextText = toText(nextSibling);
590
591            // Remove empty text nodes.
592            if (!nextText->length()) {
593                nextText->remove(IGNORE_EXCEPTION);
594                continue;
595            }
596
597            // Both non-empty text nodes. Merge them.
598            unsigned offset = text->length();
599            text->appendData(nextText->data());
600            document()->textNodesMerged(nextText.get(), offset);
601            nextText->remove(IGNORE_EXCEPTION);
602        }
603
604        node = NodeTraversal::nextPostOrder(node.get());
605    }
606}
607
608const AtomicString& Node::prefix() const
609{
610    // For nodes other than elements and attributes, the prefix is always null
611    return nullAtom;
612}
613
614void Node::setPrefix(const AtomicString& /*prefix*/, ExceptionState& es)
615{
616    // The spec says that for nodes other than elements and attributes, prefix is always null.
617    // It does not say what to do when the user tries to set the prefix on another type of
618    // node, however Mozilla throws a NamespaceError exception.
619    es.throwDOMException(NamespaceError);
620}
621
622const AtomicString& Node::localName() const
623{
624    return nullAtom;
625}
626
627const AtomicString& Node::namespaceURI() const
628{
629    return nullAtom;
630}
631
632bool Node::isContentEditable(UserSelectAllTreatment treatment)
633{
634    document()->updateStyleIfNeeded();
635    return rendererIsEditable(Editable, treatment);
636}
637
638bool Node::isContentRichlyEditable()
639{
640    document()->updateStyleIfNeeded();
641    return rendererIsEditable(RichlyEditable, UserSelectAllIsAlwaysNonEditable);
642}
643
644bool Node::rendererIsEditable(EditableLevel editableLevel, UserSelectAllTreatment treatment) const
645{
646    if (isPseudoElement())
647        return false;
648
649    // Ideally we'd call ASSERT(!needsStyleRecalc()) here, but
650    // ContainerNode::setFocus() calls setNeedsStyleRecalc(), so the assertion
651    // would fire in the middle of Document::setFocusedNode().
652
653    for (const Node* node = this; node; node = node->parentNode()) {
654        if ((node->isHTMLElement() || node->isDocumentNode()) && node->renderer()) {
655            // Elements with user-select: all style are considered atomic
656            // therefore non editable.
657            if (Position::nodeIsUserSelectAll(node) && treatment == UserSelectAllIsAlwaysNonEditable)
658                return false;
659            switch (node->renderer()->style()->userModify()) {
660            case READ_ONLY:
661                return false;
662            case READ_WRITE:
663                return true;
664            case READ_WRITE_PLAINTEXT_ONLY:
665                return editableLevel != RichlyEditable;
666            }
667            ASSERT_NOT_REACHED();
668            return false;
669        }
670    }
671
672    return false;
673}
674
675bool Node::isEditableToAccessibility(EditableLevel editableLevel) const
676{
677    if (rendererIsEditable(editableLevel))
678        return true;
679
680    // FIXME: Respect editableLevel for ARIA editable elements.
681    if (editableLevel == RichlyEditable)
682        return false;
683
684    ASSERT(document());
685    ASSERT(AXObjectCache::accessibilityEnabled());
686    ASSERT(document()->existingAXObjectCache());
687
688    if (document()) {
689        if (AXObjectCache* cache = document()->existingAXObjectCache())
690            return cache->rootAXEditableElement(this);
691    }
692
693    return false;
694}
695
696bool Node::shouldUseInputMethod()
697{
698    return isContentEditable(UserSelectAllIsAlwaysNonEditable);
699}
700
701RenderBox* Node::renderBox() const
702{
703    RenderObject* renderer = this->renderer();
704    return renderer && renderer->isBox() ? toRenderBox(renderer) : 0;
705}
706
707RenderBoxModelObject* Node::renderBoxModelObject() const
708{
709    RenderObject* renderer = this->renderer();
710    return renderer && renderer->isBoxModelObject() ? toRenderBoxModelObject(renderer) : 0;
711}
712
713LayoutRect Node::boundingBox() const
714{
715    if (renderer())
716        return renderer()->absoluteBoundingBoxRect();
717    return LayoutRect();
718}
719
720LayoutRect Node::renderRect(bool* isReplaced)
721{
722    RenderObject* hitRenderer = this->renderer();
723    ASSERT(hitRenderer);
724    RenderObject* renderer = hitRenderer;
725    while (renderer && !renderer->isBody() && !renderer->isRoot()) {
726        if (renderer->isRenderBlock() || renderer->isInlineBlockOrInlineTable() || renderer->isReplaced()) {
727            *isReplaced = renderer->isReplaced();
728            return renderer->absoluteBoundingBoxRect();
729        }
730        renderer = renderer->parent();
731    }
732    return LayoutRect();
733}
734
735bool Node::hasNonEmptyBoundingBox() const
736{
737    // Before calling absoluteRects, check for the common case where the renderer
738    // is non-empty, since this is a faster check and almost always returns true.
739    RenderBoxModelObject* box = renderBoxModelObject();
740    if (!box)
741        return false;
742    if (!box->borderBoundingBox().isEmpty())
743        return true;
744
745    Vector<IntRect> rects;
746    FloatPoint absPos = renderer()->localToAbsolute();
747    renderer()->absoluteRects(rects, flooredLayoutPoint(absPos));
748    size_t n = rects.size();
749    for (size_t i = 0; i < n; ++i)
750        if (!rects[i].isEmpty())
751            return true;
752
753    return false;
754}
755
756inline static ShadowRoot* oldestShadowRootFor(const Node* node)
757{
758    if (!node->isElementNode())
759        return 0;
760    if (ElementShadow* shadow = toElement(node)->shadow())
761        return shadow->oldestShadowRoot();
762    return 0;
763}
764
765void Node::recalcDistribution()
766{
767    if (isElementNode()) {
768        if (ElementShadow* shadow = toElement(this)->shadow())
769            shadow->distributeIfNeeded();
770    }
771
772    for (Node* child = firstChild(); child; child = child->nextSibling()) {
773        if (child->childNeedsDistributionRecalc())
774            child->recalcDistribution();
775    }
776
777    for (ShadowRoot* root = youngestShadowRoot(); root; root = root->olderShadowRoot()) {
778        if (root->childNeedsDistributionRecalc())
779            root->recalcDistribution();
780    }
781
782    clearChildNeedsDistributionRecalc();
783}
784
785void Node::markAncestorsWithChildNeedsDistributionRecalc()
786{
787    for (Node* node = this; node && !node->childNeedsDistributionRecalc(); node = node->parentOrShadowHostNode())
788        node->setChildNeedsDistributionRecalc();
789    if (document()->childNeedsDistributionRecalc())
790        document()->scheduleStyleRecalc();
791}
792
793inline void Node::setStyleChange(StyleChangeType changeType)
794{
795    m_nodeFlags = (m_nodeFlags & ~StyleChangeMask) | changeType;
796}
797
798inline void Node::markAncestorsWithChildNeedsStyleRecalc()
799{
800    for (ContainerNode* p = parentOrShadowHostNode(); p && !p->childNeedsStyleRecalc(); p = p->parentOrShadowHostNode())
801        p->setChildNeedsStyleRecalc();
802
803    if (document()->needsStyleRecalc() || document()->childNeedsStyleRecalc())
804        document()->scheduleStyleRecalc();
805}
806
807void Node::refEventTarget()
808{
809    ref();
810}
811
812void Node::derefEventTarget()
813{
814    deref();
815}
816
817void Node::setNeedsStyleRecalc(StyleChangeType changeType, StyleChangeSource source)
818{
819    ASSERT(changeType != NoStyleChange);
820    if (!attached()) // changed compared to what?
821        return;
822
823    if (source == StyleChangeFromRenderer)
824        setFlag(NotifyRendererWithIdenticalStyles);
825
826    StyleChangeType existingChangeType = styleChangeType();
827    if (changeType > existingChangeType)
828        setStyleChange(changeType);
829
830    if (existingChangeType == NoStyleChange)
831        markAncestorsWithChildNeedsStyleRecalc();
832}
833
834void Node::lazyAttach(ShouldSetAttached shouldSetAttached)
835{
836    markAncestorsWithChildNeedsStyleRecalc();
837    for (Node* node = this; node; node = NodeTraversal::next(node, this)) {
838        node->setStyleChange(LazyAttachStyleChange);
839        node->setChildNeedsStyleRecalc();
840        // FIXME: This flag is only used by HTMLFrameElementBase and doesn't look needed.
841        if (shouldSetAttached == SetAttached)
842            node->setAttached();
843        for (ShadowRoot* root = node->youngestShadowRoot(); root; root = root->olderShadowRoot())
844            root->lazyAttach(shouldSetAttached);
845    }
846}
847
848Node* Node::focusDelegate()
849{
850    return this;
851}
852
853bool Node::shouldHaveFocusAppearance() const
854{
855    ASSERT(focused());
856    return true;
857}
858
859unsigned Node::nodeIndex() const
860{
861    Node *_tempNode = previousSibling();
862    unsigned count=0;
863    for ( count=0; _tempNode; count++ )
864        _tempNode = _tempNode->previousSibling();
865    return count;
866}
867
868template<unsigned type>
869bool shouldInvalidateNodeListCachesForAttr(const unsigned nodeListCounts[], const QualifiedName& attrName)
870{
871    if (nodeListCounts[type] && LiveNodeListBase::shouldInvalidateTypeOnAttributeChange(static_cast<NodeListInvalidationType>(type), attrName))
872        return true;
873    return shouldInvalidateNodeListCachesForAttr<type + 1>(nodeListCounts, attrName);
874}
875
876template<>
877bool shouldInvalidateNodeListCachesForAttr<numNodeListInvalidationTypes>(const unsigned[], const QualifiedName&)
878{
879    return false;
880}
881
882bool Document::shouldInvalidateNodeListCaches(const QualifiedName* attrName) const
883{
884    if (attrName)
885        return shouldInvalidateNodeListCachesForAttr<DoNotInvalidateOnAttributeChanges + 1>(m_nodeListCounts, *attrName);
886
887    for (int type = 0; type < numNodeListInvalidationTypes; type++) {
888        if (m_nodeListCounts[type])
889            return true;
890    }
891
892    return false;
893}
894
895void Document::invalidateNodeListCaches(const QualifiedName* attrName)
896{
897    HashSet<LiveNodeListBase*>::iterator end = m_listsInvalidatedAtDocument.end();
898    for (HashSet<LiveNodeListBase*>::iterator it = m_listsInvalidatedAtDocument.begin(); it != end; ++it)
899        (*it)->invalidateCache(attrName);
900}
901
902void Node::invalidateNodeListCachesInAncestors(const QualifiedName* attrName, Element* attributeOwnerElement)
903{
904    if (hasRareData() && (!attrName || isAttributeNode())) {
905        if (NodeListsNodeData* lists = rareData()->nodeLists())
906            lists->clearChildNodeListCache();
907    }
908
909    // Modifications to attributes that are not associated with an Element can't invalidate NodeList caches.
910    if (attrName && !attributeOwnerElement)
911        return;
912
913    if (!document()->shouldInvalidateNodeListCaches(attrName))
914        return;
915
916    document()->invalidateNodeListCaches(attrName);
917
918    for (Node* node = this; node; node = node->parentNode()) {
919        if (!node->hasRareData())
920            continue;
921        NodeRareData* data = node->rareData();
922        if (data->nodeLists())
923            data->nodeLists()->invalidateCaches(attrName);
924    }
925}
926
927NodeListsNodeData* Node::nodeLists()
928{
929    return hasRareData() ? rareData()->nodeLists() : 0;
930}
931
932void Node::clearNodeLists()
933{
934    rareData()->clearNodeLists();
935}
936
937void Node::checkSetPrefix(const AtomicString& prefix, ExceptionState& es)
938{
939    // Perform error checking as required by spec for setting Node.prefix. Used by
940    // Element::setPrefix() and Attr::setPrefix()
941
942    if (!prefix.isEmpty() && !Document::isValidName(prefix)) {
943        es.throwDOMException(InvalidCharacterError);
944        return;
945    }
946
947    // FIXME: Raise NamespaceError if prefix is malformed per the Namespaces in XML specification.
948
949    const AtomicString& nodeNamespaceURI = namespaceURI();
950    if ((nodeNamespaceURI.isEmpty() && !prefix.isEmpty())
951        || (prefix == xmlAtom && nodeNamespaceURI != XMLNames::xmlNamespaceURI)) {
952        es.throwDOMException(NamespaceError);
953        return;
954    }
955    // Attribute-specific checks are in Attr::setPrefix().
956}
957
958bool Node::isDescendantOf(const Node *other) const
959{
960    // Return true if other is an ancestor of this, otherwise false
961    if (!other || !other->hasChildNodes() || inDocument() != other->inDocument())
962        return false;
963    if (other->treeScope() != treeScope())
964        return false;
965    if (other->isTreeScope())
966        return !isTreeScope();
967    for (const ContainerNode* n = parentNode(); n; n = n->parentNode()) {
968        if (n == other)
969            return true;
970    }
971    return false;
972}
973
974bool Node::contains(const Node* node) const
975{
976    if (!node)
977        return false;
978    return this == node || node->isDescendantOf(this);
979}
980
981bool Node::containsIncludingShadowDOM(const Node* node) const
982{
983    if (!node)
984        return false;
985
986    if (this == node)
987        return true;
988
989    if (document() != node->document())
990        return false;
991
992    if (inDocument() != node->inDocument())
993        return false;
994
995    bool hasChildren = isContainerNode() && toContainerNode(this)->hasChildNodes();
996    bool hasShadow = isElementNode() && toElement(this)->shadow();
997    if (!hasChildren && !hasShadow)
998        return false;
999
1000    for (; node; node = node->shadowHost()) {
1001        if (treeScope() == node->treeScope())
1002            return contains(node);
1003    }
1004
1005    return false;
1006}
1007
1008bool Node::containsIncludingHostElements(const Node* node) const
1009{
1010    while (node) {
1011        if (node == this)
1012            return true;
1013        if (node->isDocumentFragment() && static_cast<const DocumentFragment*>(node)->isTemplateContent())
1014            node = static_cast<const TemplateContentDocumentFragment*>(node)->host();
1015        else
1016            node = node->parentOrShadowHostNode();
1017    }
1018    return false;
1019}
1020
1021void Node::reattach(const AttachContext& context)
1022{
1023    // FIXME: Text::updateTextRenderer calls reattach outside a style recalc.
1024    ASSERT(document()->inStyleRecalc() || isTextNode());
1025    AttachContext reattachContext(context);
1026    reattachContext.performingReattach = true;
1027
1028    if (attached())
1029        detach(reattachContext);
1030    attach(reattachContext);
1031}
1032
1033void Node::attach(const AttachContext&)
1034{
1035    ASSERT(!attached());
1036    ASSERT(!renderer() || (renderer()->style() && (renderer()->parent() || renderer()->isRenderView())));
1037
1038    // If this node got a renderer it may be the previousRenderer() of sibling text nodes and thus affect the
1039    // result of Text::textRendererIsNeeded() for those nodes.
1040    // FIXME: This loop is no longer required once we lazy attach all the time.
1041    if (renderer() && !document()->inStyleRecalc()) {
1042        for (Node* next = nextSibling(); next; next = next->nextSibling()) {
1043            if (next->renderer())
1044                break;
1045            if (!next->attached())
1046                break; // Assume this means none of the following siblings are attached.
1047            if (!next->isTextNode())
1048                continue;
1049            ASSERT(!next->renderer());
1050            toText(next)->reattach();
1051            // If we again decided not to create a renderer for next, we can bail out the loop,
1052            // because it won't affect the result of Text::textRendererIsNeeded() for the rest
1053            // of sibling nodes.
1054            if (!next->renderer())
1055                break;
1056        }
1057    }
1058
1059    setAttached();
1060    clearNeedsStyleRecalc();
1061
1062    if (Document* doc = documentInternal()) {
1063        if (AXObjectCache* cache = doc->axObjectCache())
1064            cache->updateCacheAfterNodeIsAttached(this);
1065    }
1066}
1067
1068#ifndef NDEBUG
1069static Node* detachingNode;
1070
1071bool Node::inDetach() const
1072{
1073    return detachingNode == this;
1074}
1075#endif
1076
1077void Node::detach(const AttachContext& context)
1078{
1079#ifndef NDEBUG
1080    ASSERT(!detachingNode);
1081    detachingNode = this;
1082#endif
1083
1084    if (renderer())
1085        renderer()->destroyAndCleanupAnonymousWrappers();
1086    setRenderer(0);
1087
1088    // Do not remove the element's hovered and active status
1089    // if performing a reattach.
1090    if (!context.performingReattach) {
1091        Document* doc = document();
1092        if (isUserActionElement()) {
1093            if (hovered())
1094                doc->hoveredNodeDetached(this);
1095            if (inActiveChain())
1096                doc->activeChainNodeDetached(this);
1097            doc->userActionElements().didDetach(this);
1098        }
1099    }
1100
1101    clearFlag(IsAttachedFlag);
1102
1103#ifndef NDEBUG
1104    detachingNode = 0;
1105#endif
1106}
1107
1108// FIXME: This code is used by editing.  Seems like it could move over there and not pollute Node.
1109Node *Node::previousNodeConsideringAtomicNodes() const
1110{
1111    if (previousSibling()) {
1112        Node *n = previousSibling();
1113        while (!isAtomicNode(n) && n->lastChild())
1114            n = n->lastChild();
1115        return n;
1116    }
1117    else if (parentNode()) {
1118        return parentNode();
1119    }
1120    else {
1121        return 0;
1122    }
1123}
1124
1125Node *Node::nextNodeConsideringAtomicNodes() const
1126{
1127    if (!isAtomicNode(this) && firstChild())
1128        return firstChild();
1129    if (nextSibling())
1130        return nextSibling();
1131    const Node *n = this;
1132    while (n && !n->nextSibling())
1133        n = n->parentNode();
1134    if (n)
1135        return n->nextSibling();
1136    return 0;
1137}
1138
1139Node *Node::previousLeafNode() const
1140{
1141    Node *node = previousNodeConsideringAtomicNodes();
1142    while (node) {
1143        if (isAtomicNode(node))
1144            return node;
1145        node = node->previousNodeConsideringAtomicNodes();
1146    }
1147    return 0;
1148}
1149
1150Node *Node::nextLeafNode() const
1151{
1152    Node *node = nextNodeConsideringAtomicNodes();
1153    while (node) {
1154        if (isAtomicNode(node))
1155            return node;
1156        node = node->nextNodeConsideringAtomicNodes();
1157    }
1158    return 0;
1159}
1160
1161RenderStyle* Node::virtualComputedStyle(PseudoId pseudoElementSpecifier)
1162{
1163    return parentOrShadowHostNode() ? parentOrShadowHostNode()->computedStyle(pseudoElementSpecifier) : 0;
1164}
1165
1166int Node::maxCharacterOffset() const
1167{
1168    ASSERT_NOT_REACHED();
1169    return 0;
1170}
1171
1172// FIXME: Shouldn't these functions be in the editing code?  Code that asks questions about HTML in the core DOM class
1173// is obviously misplaced.
1174bool Node::canStartSelection() const
1175{
1176    if (rendererIsEditable())
1177        return true;
1178
1179    if (renderer()) {
1180        RenderStyle* style = renderer()->style();
1181        // We allow selections to begin within an element that has -webkit-user-select: none set,
1182        // but if the element is draggable then dragging should take priority over selection.
1183        if (style->userDrag() == DRAG_ELEMENT && style->userSelect() == SELECT_NONE)
1184            return false;
1185    }
1186    return parentOrShadowHostNode() ? parentOrShadowHostNode()->canStartSelection() : true;
1187}
1188
1189bool Node::isRegisteredWithNamedFlow() const
1190{
1191    return document()->renderView()->flowThreadController()->isContentNodeRegisteredWithAnyNamedFlow(this);
1192}
1193
1194Element* Node::shadowHost() const
1195{
1196    if (ShadowRoot* root = containingShadowRoot())
1197        return root->host();
1198    return 0;
1199}
1200
1201Node* Node::deprecatedShadowAncestorNode() const
1202{
1203    if (ShadowRoot* root = containingShadowRoot())
1204        return root->host();
1205
1206    return const_cast<Node*>(this);
1207}
1208
1209ShadowRoot* Node::containingShadowRoot() const
1210{
1211    Node* root = treeScope()->rootNode();
1212    return root && root->isShadowRoot() ? toShadowRoot(root) : 0;
1213}
1214
1215Node* Node::nonBoundaryShadowTreeRootNode()
1216{
1217    ASSERT(!isShadowRoot());
1218    Node* root = this;
1219    while (root) {
1220        if (root->isShadowRoot())
1221            return root;
1222        Node* parent = root->parentNodeGuaranteedHostFree();
1223        if (parent && parent->isShadowRoot())
1224            return root;
1225        root = parent;
1226    }
1227    return 0;
1228}
1229
1230ContainerNode* Node::nonShadowBoundaryParentNode() const
1231{
1232    ContainerNode* parent = parentNode();
1233    return parent && !parent->isShadowRoot() ? parent : 0;
1234}
1235
1236Element* Node::parentOrShadowHostElement() const
1237{
1238    ContainerNode* parent = parentOrShadowHostNode();
1239    if (!parent)
1240        return 0;
1241
1242    if (parent->isShadowRoot())
1243        return toShadowRoot(parent)->host();
1244
1245    if (!parent->isElementNode())
1246        return 0;
1247
1248    return toElement(parent);
1249}
1250
1251bool Node::isBlockFlowElement() const
1252{
1253    return isElementNode() && renderer() && renderer()->isBlockFlow();
1254}
1255
1256Element *Node::enclosingBlockFlowElement() const
1257{
1258    Node *n = const_cast<Node *>(this);
1259    if (isBlockFlowElement())
1260        return toElement(n);
1261
1262    while (1) {
1263        n = n->parentNode();
1264        if (!n)
1265            break;
1266        if (n->isBlockFlowElement() || n->hasTagName(bodyTag))
1267            return toElement(n);
1268    }
1269    return 0;
1270}
1271
1272bool Node::isRootEditableElement() const
1273{
1274    return rendererIsEditable() && isElementNode() && (!parentNode() || !parentNode()->rendererIsEditable()
1275        || !parentNode()->isElementNode() || hasTagName(bodyTag));
1276}
1277
1278Element* Node::rootEditableElement(EditableType editableType) const
1279{
1280    if (editableType == HasEditableAXRole) {
1281        if (AXObjectCache* cache = document()->existingAXObjectCache())
1282            return const_cast<Element*>(cache->rootAXEditableElement(this));
1283    }
1284
1285    return rootEditableElement();
1286}
1287
1288Element* Node::rootEditableElement() const
1289{
1290    Element* result = 0;
1291    for (Node* n = const_cast<Node*>(this); n && n->rendererIsEditable(); n = n->parentNode()) {
1292        if (n->isElementNode())
1293            result = toElement(n);
1294        if (n->hasTagName(bodyTag))
1295            break;
1296    }
1297    return result;
1298}
1299
1300bool Node::inSameContainingBlockFlowElement(Node *n)
1301{
1302    return n ? enclosingBlockFlowElement() == n->enclosingBlockFlowElement() : false;
1303}
1304
1305// FIXME: End of obviously misplaced HTML editing functions.  Try to move these out of Node.
1306
1307PassRefPtr<NodeList> Node::getElementsByTagName(const AtomicString& localName)
1308{
1309    if (localName.isNull())
1310        return 0;
1311
1312    if (document()->isHTMLDocument())
1313        return ensureRareData()->ensureNodeLists()->addCacheWithAtomicName<HTMLTagNodeList>(this, HTMLTagNodeListType, localName);
1314    return ensureRareData()->ensureNodeLists()->addCacheWithAtomicName<TagNodeList>(this, TagNodeListType, localName);
1315}
1316
1317PassRefPtr<NodeList> Node::getElementsByTagNameNS(const AtomicString& namespaceURI, const AtomicString& localName)
1318{
1319    if (localName.isNull())
1320        return 0;
1321
1322    if (namespaceURI == starAtom)
1323        return getElementsByTagName(localName);
1324
1325    return ensureRareData()->ensureNodeLists()->addCacheWithQualifiedName(this, namespaceURI.isEmpty() ? nullAtom : namespaceURI, localName);
1326}
1327
1328PassRefPtr<NodeList> Node::getElementsByName(const String& elementName)
1329{
1330    return ensureRareData()->ensureNodeLists()->addCacheWithAtomicName<NameNodeList>(this, NameNodeListType, elementName);
1331}
1332
1333PassRefPtr<NodeList> Node::getElementsByClassName(const String& classNames)
1334{
1335    return ensureRareData()->ensureNodeLists()->addCacheWithName<ClassNodeList>(this, ClassNodeListType, classNames);
1336}
1337
1338PassRefPtr<RadioNodeList> Node::radioNodeList(const AtomicString& name)
1339{
1340    ASSERT(hasTagName(formTag) || hasTagName(fieldsetTag));
1341    return ensureRareData()->ensureNodeLists()->addCacheWithAtomicName<RadioNodeList>(this, RadioNodeListType, name);
1342}
1343
1344PassRefPtr<Element> Node::querySelector(const AtomicString& selectors, ExceptionState& es)
1345{
1346    if (selectors.isEmpty()) {
1347        es.throwDOMException(SyntaxError);
1348        return 0;
1349    }
1350
1351    SelectorQuery* selectorQuery = document()->selectorQueryCache()->add(selectors, document(), es);
1352    if (!selectorQuery)
1353        return 0;
1354    return selectorQuery->queryFirst(this);
1355}
1356
1357PassRefPtr<NodeList> Node::querySelectorAll(const AtomicString& selectors, ExceptionState& es)
1358{
1359    if (selectors.isEmpty()) {
1360        es.throwDOMException(SyntaxError);
1361        return 0;
1362    }
1363
1364    SelectorQuery* selectorQuery = document()->selectorQueryCache()->add(selectors, document(), es);
1365    if (!selectorQuery)
1366        return 0;
1367    return selectorQuery->queryAll(this);
1368}
1369
1370Document *Node::ownerDocument() const
1371{
1372    Document *doc = document();
1373    return doc == this ? 0 : doc;
1374}
1375
1376KURL Node::baseURI() const
1377{
1378    return parentNode() ? parentNode()->baseURI() : KURL();
1379}
1380
1381bool Node::isEqualNode(Node* other) const
1382{
1383    if (!other)
1384        return false;
1385
1386    NodeType nodeType = this->nodeType();
1387    if (nodeType != other->nodeType())
1388        return false;
1389
1390    if (nodeName() != other->nodeName())
1391        return false;
1392
1393    if (localName() != other->localName())
1394        return false;
1395
1396    if (namespaceURI() != other->namespaceURI())
1397        return false;
1398
1399    if (prefix() != other->prefix())
1400        return false;
1401
1402    if (nodeValue() != other->nodeValue())
1403        return false;
1404
1405    if (isElementNode() && !toElement(this)->hasEquivalentAttributes(toElement(other)))
1406        return false;
1407
1408    Node* child = firstChild();
1409    Node* otherChild = other->firstChild();
1410
1411    while (child) {
1412        if (!child->isEqualNode(otherChild))
1413            return false;
1414
1415        child = child->nextSibling();
1416        otherChild = otherChild->nextSibling();
1417    }
1418
1419    if (otherChild)
1420        return false;
1421
1422    if (nodeType == DOCUMENT_TYPE_NODE) {
1423        const DocumentType* documentTypeThis = static_cast<const DocumentType*>(this);
1424        const DocumentType* documentTypeOther = static_cast<const DocumentType*>(other);
1425
1426        if (documentTypeThis->publicId() != documentTypeOther->publicId())
1427            return false;
1428
1429        if (documentTypeThis->systemId() != documentTypeOther->systemId())
1430            return false;
1431
1432        if (documentTypeThis->internalSubset() != documentTypeOther->internalSubset())
1433            return false;
1434
1435        // FIXME: We don't compare entities or notations because currently both are always empty.
1436    }
1437
1438    return true;
1439}
1440
1441bool Node::isDefaultNamespace(const AtomicString& namespaceURIMaybeEmpty) const
1442{
1443    const AtomicString& namespaceURI = namespaceURIMaybeEmpty.isEmpty() ? nullAtom : namespaceURIMaybeEmpty;
1444
1445    switch (nodeType()) {
1446        case ELEMENT_NODE: {
1447            const Element* elem = toElement(this);
1448
1449            if (elem->prefix().isNull())
1450                return elem->namespaceURI() == namespaceURI;
1451
1452            if (elem->hasAttributes()) {
1453                for (unsigned i = 0; i < elem->attributeCount(); i++) {
1454                    const Attribute* attr = elem->attributeItem(i);
1455
1456                    if (attr->localName() == xmlnsAtom)
1457                        return attr->value() == namespaceURI;
1458                }
1459            }
1460
1461            if (Element* ancestor = ancestorElement())
1462                return ancestor->isDefaultNamespace(namespaceURI);
1463
1464            return false;
1465        }
1466        case DOCUMENT_NODE:
1467            if (Element* de = toDocument(this)->documentElement())
1468                return de->isDefaultNamespace(namespaceURI);
1469            return false;
1470        case ENTITY_NODE:
1471        case NOTATION_NODE:
1472        case DOCUMENT_TYPE_NODE:
1473        case DOCUMENT_FRAGMENT_NODE:
1474            return false;
1475        case ATTRIBUTE_NODE: {
1476            const Attr* attr = toAttr(this);
1477            if (attr->ownerElement())
1478                return attr->ownerElement()->isDefaultNamespace(namespaceURI);
1479            return false;
1480        }
1481        default:
1482            if (Element* ancestor = ancestorElement())
1483                return ancestor->isDefaultNamespace(namespaceURI);
1484            return false;
1485    }
1486}
1487
1488String Node::lookupPrefix(const AtomicString &namespaceURI) const
1489{
1490    // Implemented according to
1491    // http://www.w3.org/TR/2004/REC-DOM-Level-3-Core-20040407/namespaces-algorithms.html#lookupNamespacePrefixAlgo
1492
1493    if (namespaceURI.isEmpty())
1494        return String();
1495
1496    switch (nodeType()) {
1497        case ELEMENT_NODE:
1498            return lookupNamespacePrefix(namespaceURI, toElement(this));
1499        case DOCUMENT_NODE:
1500            if (Element* de = toDocument(this)->documentElement())
1501                return de->lookupPrefix(namespaceURI);
1502            return String();
1503        case ENTITY_NODE:
1504        case NOTATION_NODE:
1505        case DOCUMENT_FRAGMENT_NODE:
1506        case DOCUMENT_TYPE_NODE:
1507            return String();
1508        case ATTRIBUTE_NODE: {
1509            const Attr *attr = static_cast<const Attr *>(this);
1510            if (attr->ownerElement())
1511                return attr->ownerElement()->lookupPrefix(namespaceURI);
1512            return String();
1513        }
1514        default:
1515            if (Element* ancestor = ancestorElement())
1516                return ancestor->lookupPrefix(namespaceURI);
1517            return String();
1518    }
1519}
1520
1521String Node::lookupNamespaceURI(const String &prefix) const
1522{
1523    // Implemented according to
1524    // http://www.w3.org/TR/2004/REC-DOM-Level-3-Core-20040407/namespaces-algorithms.html#lookupNamespaceURIAlgo
1525
1526    if (!prefix.isNull() && prefix.isEmpty())
1527        return String();
1528
1529    switch (nodeType()) {
1530        case ELEMENT_NODE: {
1531            const Element *elem = toElement(this);
1532
1533            if (!elem->namespaceURI().isNull() && elem->prefix() == prefix)
1534                return elem->namespaceURI();
1535
1536            if (elem->hasAttributes()) {
1537                for (unsigned i = 0; i < elem->attributeCount(); i++) {
1538                    const Attribute* attr = elem->attributeItem(i);
1539
1540                    if (attr->prefix() == xmlnsAtom && attr->localName() == prefix) {
1541                        if (!attr->value().isEmpty())
1542                            return attr->value();
1543
1544                        return String();
1545                    } else if (attr->localName() == xmlnsAtom && prefix.isNull()) {
1546                        if (!attr->value().isEmpty())
1547                            return attr->value();
1548
1549                        return String();
1550                    }
1551                }
1552            }
1553            if (Element* ancestor = ancestorElement())
1554                return ancestor->lookupNamespaceURI(prefix);
1555            return String();
1556        }
1557        case DOCUMENT_NODE:
1558            if (Element* de = toDocument(this)->documentElement())
1559                return de->lookupNamespaceURI(prefix);
1560            return String();
1561        case ENTITY_NODE:
1562        case NOTATION_NODE:
1563        case DOCUMENT_TYPE_NODE:
1564        case DOCUMENT_FRAGMENT_NODE:
1565            return String();
1566        case ATTRIBUTE_NODE: {
1567            const Attr *attr = static_cast<const Attr *>(this);
1568
1569            if (attr->ownerElement())
1570                return attr->ownerElement()->lookupNamespaceURI(prefix);
1571            else
1572                return String();
1573        }
1574        default:
1575            if (Element* ancestor = ancestorElement())
1576                return ancestor->lookupNamespaceURI(prefix);
1577            return String();
1578    }
1579}
1580
1581String Node::lookupNamespacePrefix(const AtomicString &_namespaceURI, const Element *originalElement) const
1582{
1583    if (_namespaceURI.isNull())
1584        return String();
1585
1586    if (originalElement->lookupNamespaceURI(prefix()) == _namespaceURI)
1587        return prefix();
1588
1589    ASSERT(isElementNode());
1590    const Element* thisElement = toElement(this);
1591    if (thisElement->hasAttributes()) {
1592        for (unsigned i = 0; i < thisElement->attributeCount(); i++) {
1593            const Attribute* attr = thisElement->attributeItem(i);
1594
1595            if (attr->prefix() == xmlnsAtom && attr->value() == _namespaceURI
1596                    && originalElement->lookupNamespaceURI(attr->localName()) == _namespaceURI)
1597                return attr->localName();
1598        }
1599    }
1600
1601    if (Element* ancestor = ancestorElement())
1602        return ancestor->lookupNamespacePrefix(_namespaceURI, originalElement);
1603    return String();
1604}
1605
1606static void appendTextContent(const Node* node, bool convertBRsToNewlines, bool& isNullString, StringBuilder& content)
1607{
1608    switch (node->nodeType()) {
1609    case Node::TEXT_NODE:
1610    case Node::CDATA_SECTION_NODE:
1611    case Node::COMMENT_NODE:
1612        isNullString = false;
1613        content.append(static_cast<const CharacterData*>(node)->data());
1614        break;
1615
1616    case Node::PROCESSING_INSTRUCTION_NODE:
1617        isNullString = false;
1618        content.append(static_cast<const ProcessingInstruction*>(node)->data());
1619        break;
1620
1621    case Node::ELEMENT_NODE:
1622        if (node->hasTagName(brTag) && convertBRsToNewlines) {
1623            isNullString = false;
1624            content.append('\n');
1625            break;
1626        }
1627    // Fall through.
1628    case Node::ATTRIBUTE_NODE:
1629    case Node::ENTITY_NODE:
1630    case Node::DOCUMENT_FRAGMENT_NODE:
1631        isNullString = false;
1632        for (Node* child = node->firstChild(); child; child = child->nextSibling()) {
1633            if (child->nodeType() == Node::COMMENT_NODE || child->nodeType() == Node::PROCESSING_INSTRUCTION_NODE)
1634                continue;
1635            appendTextContent(child, convertBRsToNewlines, isNullString, content);
1636        }
1637        break;
1638
1639    case Node::DOCUMENT_NODE:
1640    case Node::DOCUMENT_TYPE_NODE:
1641    case Node::NOTATION_NODE:
1642    case Node::XPATH_NAMESPACE_NODE:
1643        break;
1644    }
1645}
1646
1647String Node::textContent(bool convertBRsToNewlines) const
1648{
1649    StringBuilder content;
1650    bool isNullString = true;
1651    appendTextContent(this, convertBRsToNewlines, isNullString, content);
1652    return isNullString ? String() : content.toString();
1653}
1654
1655void Node::setTextContent(const String& text, ExceptionState& es)
1656{
1657    switch (nodeType()) {
1658        case TEXT_NODE:
1659        case CDATA_SECTION_NODE:
1660        case COMMENT_NODE:
1661        case PROCESSING_INSTRUCTION_NODE:
1662            setNodeValue(text);
1663            return;
1664        case ELEMENT_NODE:
1665        case ATTRIBUTE_NODE:
1666        case ENTITY_NODE:
1667        case DOCUMENT_FRAGMENT_NODE: {
1668            RefPtr<ContainerNode> container = toContainerNode(this);
1669            ChildListMutationScope mutation(this);
1670            container->removeChildren();
1671            if (!text.isEmpty())
1672                container->appendChild(document()->createTextNode(text), es, AttachLazily);
1673            return;
1674        }
1675        case DOCUMENT_NODE:
1676        case DOCUMENT_TYPE_NODE:
1677        case NOTATION_NODE:
1678        case XPATH_NAMESPACE_NODE:
1679            // Do nothing.
1680            return;
1681    }
1682    ASSERT_NOT_REACHED();
1683}
1684
1685Element* Node::ancestorElement() const
1686{
1687    // In theory, there can be EntityReference nodes between elements, but this is currently not supported.
1688    for (ContainerNode* n = parentNode(); n; n = n->parentNode()) {
1689        if (n->isElementNode())
1690            return toElement(n);
1691    }
1692    return 0;
1693}
1694
1695bool Node::offsetInCharacters() const
1696{
1697    return false;
1698}
1699
1700unsigned short Node::compareDocumentPosition(const Node* otherNode) const
1701{
1702    return compareDocumentPositionInternal(otherNode, TreatShadowTreesAsDisconnected);
1703}
1704
1705unsigned short Node::compareDocumentPositionInternal(const Node* otherNode, ShadowTreesTreatment treatment) const
1706{
1707    // It is not clear what should be done if |otherNode| is 0.
1708    if (!otherNode)
1709        return DOCUMENT_POSITION_DISCONNECTED;
1710
1711    if (otherNode == this)
1712        return DOCUMENT_POSITION_EQUIVALENT;
1713
1714    const Attr* attr1 = nodeType() == ATTRIBUTE_NODE ? toAttr(this) : 0;
1715    const Attr* attr2 = otherNode->nodeType() == ATTRIBUTE_NODE ? toAttr(otherNode) : 0;
1716
1717    const Node* start1 = attr1 ? attr1->ownerElement() : this;
1718    const Node* start2 = attr2 ? attr2->ownerElement() : otherNode;
1719
1720    // If either of start1 or start2 is null, then we are disconnected, since one of the nodes is
1721    // an orphaned attribute node.
1722    if (!start1 || !start2) {
1723        unsigned short direction = (this > otherNode) ? DOCUMENT_POSITION_PRECEDING : DOCUMENT_POSITION_FOLLOWING;
1724        return DOCUMENT_POSITION_DISCONNECTED | DOCUMENT_POSITION_IMPLEMENTATION_SPECIFIC | direction;
1725    }
1726
1727    Vector<const Node*, 16> chain1;
1728    Vector<const Node*, 16> chain2;
1729    if (attr1)
1730        chain1.append(attr1);
1731    if (attr2)
1732        chain2.append(attr2);
1733
1734    if (attr1 && attr2 && start1 == start2 && start1) {
1735        // We are comparing two attributes on the same node. Crawl our attribute map and see which one we hit first.
1736        const Element* owner1 = attr1->ownerElement();
1737        owner1->synchronizeAllAttributes();
1738        unsigned length = owner1->attributeCount();
1739        for (unsigned i = 0; i < length; ++i) {
1740            // If neither of the two determining nodes is a child node and nodeType is the same for both determining nodes, then an
1741            // implementation-dependent order between the determining nodes is returned. This order is stable as long as no nodes of
1742            // the same nodeType are inserted into or removed from the direct container. This would be the case, for example,
1743            // when comparing two attributes of the same element, and inserting or removing additional attributes might change
1744            // the order between existing attributes.
1745            const Attribute* attribute = owner1->attributeItem(i);
1746            if (attr1->qualifiedName() == attribute->name())
1747                return DOCUMENT_POSITION_IMPLEMENTATION_SPECIFIC | DOCUMENT_POSITION_FOLLOWING;
1748            if (attr2->qualifiedName() == attribute->name())
1749                return DOCUMENT_POSITION_IMPLEMENTATION_SPECIFIC | DOCUMENT_POSITION_PRECEDING;
1750        }
1751
1752        ASSERT_NOT_REACHED();
1753        return DOCUMENT_POSITION_DISCONNECTED;
1754    }
1755
1756    // If one node is in the document and the other is not, we must be disconnected.
1757    // If the nodes have different owning documents, they must be disconnected.  Note that we avoid
1758    // comparing Attr nodes here, since they return false from inDocument() all the time (which seems like a bug).
1759    if (start1->inDocument() != start2->inDocument() || (treatment == TreatShadowTreesAsDisconnected && start1->treeScope() != start2->treeScope())) {
1760        unsigned short direction = (this > otherNode) ? DOCUMENT_POSITION_PRECEDING : DOCUMENT_POSITION_FOLLOWING;
1761        return DOCUMENT_POSITION_DISCONNECTED | DOCUMENT_POSITION_IMPLEMENTATION_SPECIFIC | direction;
1762    }
1763
1764    // We need to find a common ancestor container, and then compare the indices of the two immediate children.
1765    const Node* current;
1766    for (current = start1; current; current = current->parentOrShadowHostNode())
1767        chain1.append(current);
1768    for (current = start2; current; current = current->parentOrShadowHostNode())
1769        chain2.append(current);
1770
1771    unsigned index1 = chain1.size();
1772    unsigned index2 = chain2.size();
1773
1774    // If the two elements don't have a common root, they're not in the same tree.
1775    if (chain1[index1 - 1] != chain2[index2 - 1]) {
1776        unsigned short direction = (this > otherNode) ? DOCUMENT_POSITION_PRECEDING : DOCUMENT_POSITION_FOLLOWING;
1777        return DOCUMENT_POSITION_DISCONNECTED | DOCUMENT_POSITION_IMPLEMENTATION_SPECIFIC | direction;
1778    }
1779
1780    unsigned connection = start1->treeScope() != start2->treeScope() ? DOCUMENT_POSITION_DISCONNECTED | DOCUMENT_POSITION_IMPLEMENTATION_SPECIFIC : 0;
1781
1782    // Walk the two chains backwards and look for the first difference.
1783    for (unsigned i = min(index1, index2); i; --i) {
1784        const Node* child1 = chain1[--index1];
1785        const Node* child2 = chain2[--index2];
1786        if (child1 != child2) {
1787            // If one of the children is an attribute, it wins.
1788            if (child1->nodeType() == ATTRIBUTE_NODE)
1789                return DOCUMENT_POSITION_FOLLOWING | connection;
1790            if (child2->nodeType() == ATTRIBUTE_NODE)
1791                return DOCUMENT_POSITION_PRECEDING | connection;
1792
1793            // If one of the children is a shadow root,
1794            if (child1->isShadowRoot() || child2->isShadowRoot()) {
1795                if (!child2->isShadowRoot())
1796                    return Node::DOCUMENT_POSITION_FOLLOWING | connection;
1797                if (!child1->isShadowRoot())
1798                    return Node::DOCUMENT_POSITION_PRECEDING | connection;
1799
1800                for (ShadowRoot* child = toShadowRoot(child2)->olderShadowRoot(); child; child = child->olderShadowRoot())
1801                    if (child == child1)
1802                        return Node::DOCUMENT_POSITION_FOLLOWING | connection;
1803
1804                return Node::DOCUMENT_POSITION_PRECEDING | connection;
1805            }
1806
1807            if (!child2->nextSibling())
1808                return DOCUMENT_POSITION_FOLLOWING | connection;
1809            if (!child1->nextSibling())
1810                return DOCUMENT_POSITION_PRECEDING | connection;
1811
1812            // Otherwise we need to see which node occurs first.  Crawl backwards from child2 looking for child1.
1813            for (Node* child = child2->previousSibling(); child; child = child->previousSibling()) {
1814                if (child == child1)
1815                    return DOCUMENT_POSITION_FOLLOWING | connection;
1816            }
1817            return DOCUMENT_POSITION_PRECEDING | connection;
1818        }
1819    }
1820
1821    // There was no difference between the two parent chains, i.e., one was a subset of the other.  The shorter
1822    // chain is the ancestor.
1823    return index1 < index2 ?
1824               DOCUMENT_POSITION_FOLLOWING | DOCUMENT_POSITION_CONTAINED_BY | connection :
1825               DOCUMENT_POSITION_PRECEDING | DOCUMENT_POSITION_CONTAINS | connection;
1826}
1827
1828FloatPoint Node::convertToPage(const FloatPoint& p) const
1829{
1830    // If there is a renderer, just ask it to do the conversion
1831    if (renderer())
1832        return renderer()->localToAbsolute(p, UseTransforms);
1833
1834    // Otherwise go up the tree looking for a renderer
1835    Element *parent = ancestorElement();
1836    if (parent)
1837        return parent->convertToPage(p);
1838
1839    // No parent - no conversion needed
1840    return p;
1841}
1842
1843FloatPoint Node::convertFromPage(const FloatPoint& p) const
1844{
1845    // If there is a renderer, just ask it to do the conversion
1846    if (renderer())
1847        return renderer()->absoluteToLocal(p, UseTransforms);
1848
1849    // Otherwise go up the tree looking for a renderer
1850    Element *parent = ancestorElement();
1851    if (parent)
1852        return parent->convertFromPage(p);
1853
1854    // No parent - no conversion needed
1855    return p;
1856}
1857
1858#ifndef NDEBUG
1859
1860String Node::debugName() const
1861{
1862    StringBuilder name;
1863    name.append(nodeName());
1864
1865    if (hasID()) {
1866        name.appendLiteral(" id=\'");
1867        name.append(toElement(this)->getIdAttribute());
1868        name.append('\'');
1869    }
1870
1871    if (hasClass()) {
1872        name.appendLiteral(" class=\'");
1873        for (size_t i = 0; i < toElement(this)->classNames().size(); ++i) {
1874            if (i > 0)
1875                name.append(' ');
1876            name.append(toElement(this)->classNames()[i]);
1877        }
1878        name.append('\'');
1879    }
1880
1881    return name.toString();
1882}
1883
1884static void appendAttributeDesc(const Node* node, StringBuilder& stringBuilder, const QualifiedName& name, const char* attrDesc)
1885{
1886    if (!node->isElementNode())
1887        return;
1888
1889    String attr = toElement(node)->getAttribute(name);
1890    if (attr.isEmpty())
1891        return;
1892
1893    stringBuilder.append(attrDesc);
1894    stringBuilder.append(attr);
1895}
1896
1897void Node::showNode(const char* prefix) const
1898{
1899    if (!prefix)
1900        prefix = "";
1901    if (isTextNode()) {
1902        String value = nodeValue();
1903        value.replaceWithLiteral('\\', "\\\\");
1904        value.replaceWithLiteral('\n', "\\n");
1905        fprintf(stderr, "%s%s\t%p \"%s\"\n", prefix, nodeName().utf8().data(), this, value.utf8().data());
1906    } else {
1907        StringBuilder attrs;
1908        appendAttributeDesc(this, attrs, classAttr, " CLASS=");
1909        appendAttributeDesc(this, attrs, styleAttr, " STYLE=");
1910        fprintf(stderr, "%s%s\t%p%s\n", prefix, nodeName().utf8().data(), this, attrs.toString().utf8().data());
1911    }
1912}
1913
1914void Node::showTreeForThis() const
1915{
1916    showTreeAndMark(this, "*");
1917}
1918
1919void Node::showNodePathForThis() const
1920{
1921    Vector<const Node*, 16> chain;
1922    const Node* node = this;
1923    while (node->parentOrShadowHostNode()) {
1924        chain.append(node);
1925        node = node->parentOrShadowHostNode();
1926    }
1927    for (unsigned index = chain.size(); index > 0; --index) {
1928        const Node* node = chain[index - 1];
1929        if (node->isShadowRoot()) {
1930            int count = 0;
1931            for (ShadowRoot* shadowRoot = toShadowRoot(node)->olderShadowRoot(); shadowRoot; shadowRoot = shadowRoot->olderShadowRoot())
1932                ++count;
1933            fprintf(stderr, "/#shadow-root[%d]", count);
1934            continue;
1935        }
1936
1937        switch (node->nodeType()) {
1938        case ELEMENT_NODE: {
1939            fprintf(stderr, "/%s", node->nodeName().utf8().data());
1940
1941            const Element* element = toElement(node);
1942            const AtomicString& idattr = element->getIdAttribute();
1943            bool hasIdAttr = !idattr.isNull() && !idattr.isEmpty();
1944            if (node->previousSibling() || node->nextSibling()) {
1945                int count = 0;
1946                for (Node* previous = node->previousSibling(); previous; previous = previous->previousSibling())
1947                    if (previous->nodeName() == node->nodeName())
1948                        ++count;
1949                if (hasIdAttr)
1950                    fprintf(stderr, "[@id=\"%s\" and position()=%d]", idattr.string().utf8().data(), count);
1951                else
1952                    fprintf(stderr, "[%d]", count);
1953            } else if (hasIdAttr)
1954                fprintf(stderr, "[@id=\"%s\"]", idattr.string().utf8().data());
1955            break;
1956        }
1957        case TEXT_NODE:
1958            fprintf(stderr, "/text()");
1959            break;
1960        case ATTRIBUTE_NODE:
1961            fprintf(stderr, "/@%s", node->nodeName().utf8().data());
1962            break;
1963        default:
1964            break;
1965        }
1966    }
1967    fprintf(stderr, "\n");
1968}
1969
1970static void traverseTreeAndMark(const String& baseIndent, const Node* rootNode, const Node* markedNode1, const char* markedLabel1, const Node* markedNode2, const char* markedLabel2)
1971{
1972    for (const Node* node = rootNode; node; node = NodeTraversal::next(node)) {
1973        if (node == markedNode1)
1974            fprintf(stderr, "%s", markedLabel1);
1975        if (node == markedNode2)
1976            fprintf(stderr, "%s", markedLabel2);
1977
1978        StringBuilder indent;
1979        indent.append(baseIndent);
1980        for (const Node* tmpNode = node; tmpNode && tmpNode != rootNode; tmpNode = tmpNode->parentOrShadowHostNode())
1981            indent.append('\t');
1982        fprintf(stderr, "%s", indent.toString().utf8().data());
1983        node->showNode();
1984        indent.append('\t');
1985        if (node->isShadowRoot()) {
1986            if (ShadowRoot* youngerShadowRoot = toShadowRoot(node)->youngerShadowRoot())
1987                traverseTreeAndMark(indent.toString(), youngerShadowRoot, markedNode1, markedLabel1, markedNode2, markedLabel2);
1988        } else if (ShadowRoot* oldestShadowRoot = oldestShadowRootFor(node))
1989            traverseTreeAndMark(indent.toString(), oldestShadowRoot, markedNode1, markedLabel1, markedNode2, markedLabel2);
1990    }
1991}
1992
1993void Node::showTreeAndMark(const Node* markedNode1, const char* markedLabel1, const Node* markedNode2, const char* markedLabel2) const
1994{
1995    const Node* rootNode;
1996    const Node* node = this;
1997    while (node->parentOrShadowHostNode() && !node->hasTagName(bodyTag))
1998        node = node->parentOrShadowHostNode();
1999    rootNode = node;
2000
2001    String startingIndent;
2002    traverseTreeAndMark(startingIndent, rootNode, markedNode1, markedLabel1, markedNode2, markedLabel2);
2003}
2004
2005void Node::formatForDebugger(char* buffer, unsigned length) const
2006{
2007    String result;
2008    String s;
2009
2010    s = nodeName();
2011    if (s.isEmpty())
2012        result = "<none>";
2013    else
2014        result = s;
2015
2016    strncpy(buffer, result.utf8().data(), length - 1);
2017}
2018
2019static ContainerNode* parentOrShadowHostOrFrameOwner(const Node* node)
2020{
2021    ContainerNode* parent = node->parentOrShadowHostNode();
2022    if (!parent && node->document() && node->document()->frame())
2023        parent = node->document()->frame()->ownerElement();
2024    return parent;
2025}
2026
2027static void showSubTreeAcrossFrame(const Node* node, const Node* markedNode, const String& indent)
2028{
2029    if (node == markedNode)
2030        fputs("*", stderr);
2031    fputs(indent.utf8().data(), stderr);
2032    node->showNode();
2033     if (node->isShadowRoot()) {
2034         if (ShadowRoot* youngerShadowRoot = toShadowRoot(node)->youngerShadowRoot())
2035             showSubTreeAcrossFrame(youngerShadowRoot, markedNode, indent + "\t");
2036     } else {
2037         if (node->isFrameOwnerElement())
2038             showSubTreeAcrossFrame(static_cast<const HTMLFrameOwnerElement*>(node)->contentDocument(), markedNode, indent + "\t");
2039         if (ShadowRoot* oldestShadowRoot = oldestShadowRootFor(node))
2040             showSubTreeAcrossFrame(oldestShadowRoot, markedNode, indent + "\t");
2041     }
2042    for (Node* child = node->firstChild(); child; child = child->nextSibling())
2043        showSubTreeAcrossFrame(child, markedNode, indent + "\t");
2044}
2045
2046void Node::showTreeForThisAcrossFrame() const
2047{
2048    Node* rootNode = const_cast<Node*>(this);
2049    while (parentOrShadowHostOrFrameOwner(rootNode))
2050        rootNode = parentOrShadowHostOrFrameOwner(rootNode);
2051    showSubTreeAcrossFrame(rootNode, this, "");
2052}
2053
2054#endif
2055
2056// --------
2057
2058void NodeListsNodeData::invalidateCaches(const QualifiedName* attrName)
2059{
2060    NodeListAtomicNameCacheMap::const_iterator atomicNameCacheEnd = m_atomicNameCaches.end();
2061    for (NodeListAtomicNameCacheMap::const_iterator it = m_atomicNameCaches.begin(); it != atomicNameCacheEnd; ++it)
2062        it->value->invalidateCache(attrName);
2063
2064    NodeListNameCacheMap::const_iterator nameCacheEnd = m_nameCaches.end();
2065    for (NodeListNameCacheMap::const_iterator it = m_nameCaches.begin(); it != nameCacheEnd; ++it)
2066        it->value->invalidateCache(attrName);
2067
2068    if (attrName)
2069        return;
2070
2071    TagNodeListCacheNS::iterator tagCacheEnd = m_tagNodeListCacheNS.end();
2072    for (TagNodeListCacheNS::iterator it = m_tagNodeListCacheNS.begin(); it != tagCacheEnd; ++it)
2073        it->value->invalidateCache();
2074}
2075
2076Node* Node::enclosingLinkEventParentOrSelf()
2077{
2078    for (Node* node = this; node; node = node->parentOrShadowHostNode()) {
2079        // For imagemaps, the enclosing link node is the associated area element not the image itself.
2080        // So we don't let images be the enclosingLinkNode, even though isLink sometimes returns true
2081        // for them.
2082        if (node->isLink() && !node->hasTagName(imgTag))
2083            return node;
2084    }
2085
2086    return 0;
2087}
2088
2089const AtomicString& Node::interfaceName() const
2090{
2091    return eventNames().interfaceForNode;
2092}
2093
2094ScriptExecutionContext* Node::scriptExecutionContext() const
2095{
2096    return document();
2097}
2098
2099void Node::didMoveToNewDocument(Document* oldDocument)
2100{
2101    TreeScopeAdopter::ensureDidMoveToNewDocumentWasCalled(oldDocument);
2102
2103    if (const EventTargetData* eventTargetData = this->eventTargetData()) {
2104        const EventListenerMap& listenerMap = eventTargetData->eventListenerMap;
2105        if (!listenerMap.isEmpty()) {
2106            Vector<AtomicString> types = listenerMap.eventTypes();
2107            for (unsigned i = 0; i < types.size(); ++i)
2108                document()->addListenerTypeIfNeeded(types[i]);
2109        }
2110    }
2111
2112    if (AXObjectCache::accessibilityEnabled() && oldDocument)
2113        if (AXObjectCache* cache = oldDocument->existingAXObjectCache())
2114            cache->remove(this);
2115
2116    const EventListenerVector& wheelListeners = getEventListeners(eventNames().mousewheelEvent);
2117    for (size_t i = 0; i < wheelListeners.size(); ++i) {
2118        oldDocument->didRemoveWheelEventHandler();
2119        document()->didAddWheelEventHandler();
2120    }
2121
2122    if (const TouchEventTargetSet* touchHandlers = oldDocument ? oldDocument->touchEventTargets() : 0) {
2123        while (touchHandlers->contains(this)) {
2124            oldDocument->didRemoveTouchEventHandler(this);
2125            document()->didAddTouchEventHandler(this);
2126        }
2127    }
2128
2129    if (Vector<OwnPtr<MutationObserverRegistration> >* registry = mutationObserverRegistry()) {
2130        for (size_t i = 0; i < registry->size(); ++i) {
2131            document()->addMutationObserverTypes(registry->at(i)->mutationTypes());
2132        }
2133    }
2134
2135    if (HashSet<MutationObserverRegistration*>* transientRegistry = transientMutationObserverRegistry()) {
2136        for (HashSet<MutationObserverRegistration*>::iterator iter = transientRegistry->begin(); iter != transientRegistry->end(); ++iter) {
2137            document()->addMutationObserverTypes((*iter)->mutationTypes());
2138        }
2139    }
2140}
2141
2142static inline bool tryAddEventListener(Node* targetNode, const AtomicString& eventType, PassRefPtr<EventListener> listener, bool useCapture)
2143{
2144    if (!targetNode->EventTarget::addEventListener(eventType, listener, useCapture))
2145        return false;
2146
2147    if (Document* document = targetNode->document()) {
2148        document->addListenerTypeIfNeeded(eventType);
2149        if (eventType == eventNames().mousewheelEvent)
2150            document->didAddWheelEventHandler();
2151        else if (eventNames().isTouchEventType(eventType))
2152            document->didAddTouchEventHandler(targetNode);
2153    }
2154
2155    return true;
2156}
2157
2158bool Node::addEventListener(const AtomicString& eventType, PassRefPtr<EventListener> listener, bool useCapture)
2159{
2160    return tryAddEventListener(this, eventType, listener, useCapture);
2161}
2162
2163static inline bool tryRemoveEventListener(Node* targetNode, const AtomicString& eventType, EventListener* listener, bool useCapture)
2164{
2165    if (!targetNode->EventTarget::removeEventListener(eventType, listener, useCapture))
2166        return false;
2167
2168    // FIXME: Notify Document that the listener has vanished. We need to keep track of a number of
2169    // listeners for each type, not just a bool - see https://bugs.webkit.org/show_bug.cgi?id=33861
2170    if (Document* document = targetNode->document()) {
2171        if (eventType == eventNames().mousewheelEvent)
2172            document->didRemoveWheelEventHandler();
2173        else if (eventNames().isTouchEventType(eventType))
2174            document->didRemoveTouchEventHandler(targetNode);
2175    }
2176
2177    return true;
2178}
2179
2180bool Node::removeEventListener(const AtomicString& eventType, EventListener* listener, bool useCapture)
2181{
2182    return tryRemoveEventListener(this, eventType, listener, useCapture);
2183}
2184
2185typedef HashMap<Node*, OwnPtr<EventTargetData> > EventTargetDataMap;
2186
2187static EventTargetDataMap& eventTargetDataMap()
2188{
2189    DEFINE_STATIC_LOCAL(EventTargetDataMap, map, ());
2190    return map;
2191}
2192
2193EventTargetData* Node::eventTargetData()
2194{
2195    return hasEventTargetData() ? eventTargetDataMap().get(this) : 0;
2196}
2197
2198EventTargetData* Node::ensureEventTargetData()
2199{
2200    if (hasEventTargetData())
2201        return eventTargetDataMap().get(this);
2202    setHasEventTargetData(true);
2203    EventTargetData* data = new EventTargetData;
2204    eventTargetDataMap().set(this, adoptPtr(data));
2205    return data;
2206}
2207
2208void Node::clearEventTargetData()
2209{
2210    eventTargetDataMap().remove(this);
2211}
2212
2213Vector<OwnPtr<MutationObserverRegistration> >* Node::mutationObserverRegistry()
2214{
2215    if (!hasRareData())
2216        return 0;
2217    NodeMutationObserverData* data = rareData()->mutationObserverData();
2218    if (!data)
2219        return 0;
2220    return &data->registry;
2221}
2222
2223HashSet<MutationObserverRegistration*>* Node::transientMutationObserverRegistry()
2224{
2225    if (!hasRareData())
2226        return 0;
2227    NodeMutationObserverData* data = rareData()->mutationObserverData();
2228    if (!data)
2229        return 0;
2230    return &data->transientRegistry;
2231}
2232
2233template<typename Registry>
2234static inline void collectMatchingObserversForMutation(HashMap<MutationObserver*, MutationRecordDeliveryOptions>& observers, Registry* registry, Node* target, MutationObserver::MutationType type, const QualifiedName* attributeName)
2235{
2236    if (!registry)
2237        return;
2238    for (typename Registry::iterator iter = registry->begin(); iter != registry->end(); ++iter) {
2239        const MutationObserverRegistration& registration = **iter;
2240        if (registration.shouldReceiveMutationFrom(target, type, attributeName)) {
2241            MutationRecordDeliveryOptions deliveryOptions = registration.deliveryOptions();
2242            HashMap<MutationObserver*, MutationRecordDeliveryOptions>::AddResult result = observers.add(registration.observer(), deliveryOptions);
2243            if (!result.isNewEntry)
2244                result.iterator->value |= deliveryOptions;
2245        }
2246    }
2247}
2248
2249void Node::getRegisteredMutationObserversOfType(HashMap<MutationObserver*, MutationRecordDeliveryOptions>& observers, MutationObserver::MutationType type, const QualifiedName* attributeName)
2250{
2251    ASSERT((type == MutationObserver::Attributes && attributeName) || !attributeName);
2252    collectMatchingObserversForMutation(observers, mutationObserverRegistry(), this, type, attributeName);
2253    collectMatchingObserversForMutation(observers, transientMutationObserverRegistry(), this, type, attributeName);
2254    for (Node* node = parentNode(); node; node = node->parentNode()) {
2255        collectMatchingObserversForMutation(observers, node->mutationObserverRegistry(), this, type, attributeName);
2256        collectMatchingObserversForMutation(observers, node->transientMutationObserverRegistry(), this, type, attributeName);
2257    }
2258}
2259
2260void Node::registerMutationObserver(MutationObserver* observer, MutationObserverOptions options, const HashSet<AtomicString>& attributeFilter)
2261{
2262    MutationObserverRegistration* registration = 0;
2263    Vector<OwnPtr<MutationObserverRegistration> >& registry = ensureRareData()->ensureMutationObserverData()->registry;
2264    for (size_t i = 0; i < registry.size(); ++i) {
2265        if (registry[i]->observer() == observer) {
2266            registration = registry[i].get();
2267            registration->resetObservation(options, attributeFilter);
2268        }
2269    }
2270
2271    if (!registration) {
2272        registry.append(MutationObserverRegistration::create(observer, this, options, attributeFilter));
2273        registration = registry.last().get();
2274    }
2275
2276    document()->addMutationObserverTypes(registration->mutationTypes());
2277}
2278
2279void Node::unregisterMutationObserver(MutationObserverRegistration* registration)
2280{
2281    Vector<OwnPtr<MutationObserverRegistration> >* registry = mutationObserverRegistry();
2282    ASSERT(registry);
2283    if (!registry)
2284        return;
2285
2286    size_t index = registry->find(registration);
2287    ASSERT(index != notFound);
2288    if (index == notFound)
2289        return;
2290
2291    // Deleting the registration may cause this node to be derefed, so we must make sure the Vector operation completes
2292    // before that, in case |this| is destroyed (see MutationObserverRegistration::m_registrationNodeKeepAlive).
2293    // FIXME: Simplify the registration/transient registration logic to make this understandable by humans.
2294    RefPtr<Node> protect(this);
2295    registry->remove(index);
2296}
2297
2298void Node::registerTransientMutationObserver(MutationObserverRegistration* registration)
2299{
2300    ensureRareData()->ensureMutationObserverData()->transientRegistry.add(registration);
2301}
2302
2303void Node::unregisterTransientMutationObserver(MutationObserverRegistration* registration)
2304{
2305    HashSet<MutationObserverRegistration*>* transientRegistry = transientMutationObserverRegistry();
2306    ASSERT(transientRegistry);
2307    if (!transientRegistry)
2308        return;
2309
2310    ASSERT(transientRegistry->contains(registration));
2311    transientRegistry->remove(registration);
2312}
2313
2314void Node::notifyMutationObserversNodeWillDetach()
2315{
2316    if (!document()->hasMutationObservers())
2317        return;
2318
2319    for (Node* node = parentNode(); node; node = node->parentNode()) {
2320        if (Vector<OwnPtr<MutationObserverRegistration> >* registry = node->mutationObserverRegistry()) {
2321            const size_t size = registry->size();
2322            for (size_t i = 0; i < size; ++i)
2323                registry->at(i)->observedSubtreeNodeWillDetach(this);
2324        }
2325
2326        if (HashSet<MutationObserverRegistration*>* transientRegistry = node->transientMutationObserverRegistry()) {
2327            for (HashSet<MutationObserverRegistration*>::iterator iter = transientRegistry->begin(); iter != transientRegistry->end(); ++iter)
2328                (*iter)->observedSubtreeNodeWillDetach(this);
2329        }
2330    }
2331}
2332
2333void Node::handleLocalEvents(Event* event)
2334{
2335    if (!hasEventTargetData())
2336        return;
2337
2338    if (isDisabledFormControl(this) && event->isMouseEvent())
2339        return;
2340
2341    fireEventListeners(event);
2342}
2343
2344void Node::dispatchScopedEvent(PassRefPtr<Event> event)
2345{
2346    dispatchScopedEventDispatchMediator(EventDispatchMediator::create(event));
2347}
2348
2349void Node::dispatchScopedEventDispatchMediator(PassRefPtr<EventDispatchMediator> eventDispatchMediator)
2350{
2351    EventDispatcher::dispatchScopedEvent(this, eventDispatchMediator);
2352}
2353
2354bool Node::dispatchEvent(PassRefPtr<Event> event)
2355{
2356    if (event->isMouseEvent())
2357        return EventDispatcher::dispatchEvent(this, MouseEventDispatchMediator::create(adoptRef(toMouseEvent(event.leakRef())), MouseEventDispatchMediator::SyntheticMouseEvent));
2358    if (event->isTouchEvent())
2359        return dispatchTouchEvent(adoptRef(toTouchEvent(event.leakRef())));
2360    return EventDispatcher::dispatchEvent(this, EventDispatchMediator::create(event));
2361}
2362
2363void Node::dispatchSubtreeModifiedEvent()
2364{
2365    if (isInShadowTree())
2366        return;
2367
2368    ASSERT(!NoEventDispatchAssertion::isEventDispatchForbidden());
2369
2370    if (!document()->hasListenerType(Document::DOMSUBTREEMODIFIED_LISTENER))
2371        return;
2372
2373    dispatchScopedEvent(MutationEvent::create(eventNames().DOMSubtreeModifiedEvent, true));
2374}
2375
2376bool Node::dispatchDOMActivateEvent(int detail, PassRefPtr<Event> underlyingEvent)
2377{
2378    ASSERT(!NoEventDispatchAssertion::isEventDispatchForbidden());
2379    RefPtr<UIEvent> event = UIEvent::create(eventNames().DOMActivateEvent, true, true, document()->defaultView(), detail);
2380    event->setUnderlyingEvent(underlyingEvent);
2381    dispatchScopedEvent(event);
2382    return event->defaultHandled();
2383}
2384
2385bool Node::dispatchKeyEvent(const PlatformKeyboardEvent& event)
2386{
2387    return EventDispatcher::dispatchEvent(this, KeyboardEventDispatchMediator::create(KeyboardEvent::create(event, document()->defaultView())));
2388}
2389
2390bool Node::dispatchMouseEvent(const PlatformMouseEvent& event, const AtomicString& eventType,
2391    int detail, Node* relatedTarget)
2392{
2393    return EventDispatcher::dispatchEvent(this, MouseEventDispatchMediator::create(MouseEvent::create(eventType, document()->defaultView(), event, detail, relatedTarget)));
2394}
2395
2396bool Node::dispatchGestureEvent(const PlatformGestureEvent& event)
2397{
2398    RefPtr<GestureEvent> gestureEvent = GestureEvent::create(document()->defaultView(), event);
2399    if (!gestureEvent.get())
2400        return false;
2401    return EventDispatcher::dispatchEvent(this, GestureEventDispatchMediator::create(gestureEvent));
2402}
2403
2404bool Node::dispatchTouchEvent(PassRefPtr<TouchEvent> event)
2405{
2406    return EventDispatcher::dispatchEvent(this, TouchEventDispatchMediator::create(event));
2407}
2408
2409void Node::dispatchSimulatedClick(Event* underlyingEvent, SimulatedClickMouseEventOptions eventOptions, SimulatedClickVisualOptions visualOptions)
2410{
2411    EventDispatcher::dispatchSimulatedClick(this, underlyingEvent, eventOptions, visualOptions);
2412}
2413
2414bool Node::dispatchBeforeLoadEvent(const String& sourceURL)
2415{
2416    if (!document()->hasListenerType(Document::BEFORELOAD_LISTENER))
2417        return true;
2418
2419    RefPtr<Node> protector(this);
2420    RefPtr<BeforeLoadEvent> beforeLoadEvent = BeforeLoadEvent::create(sourceURL);
2421    dispatchEvent(beforeLoadEvent.get());
2422    return !beforeLoadEvent->defaultPrevented();
2423}
2424
2425bool Node::dispatchWheelEvent(const PlatformWheelEvent& event)
2426{
2427    return EventDispatcher::dispatchEvent(this, WheelEventDispatchMediator::create(event, document()->defaultView()));
2428}
2429
2430void Node::dispatchChangeEvent()
2431{
2432    dispatchScopedEvent(Event::create(eventNames().changeEvent, true, false));
2433}
2434
2435void Node::dispatchInputEvent()
2436{
2437    dispatchScopedEvent(Event::create(eventNames().inputEvent, true, false));
2438}
2439
2440void Node::defaultEventHandler(Event* event)
2441{
2442    if (event->target() != this)
2443        return;
2444    const AtomicString& eventType = event->type();
2445    if (eventType == eventNames().keydownEvent || eventType == eventNames().keypressEvent) {
2446        if (event->isKeyboardEvent()) {
2447            if (Frame* frame = document()->frame())
2448                frame->eventHandler()->defaultKeyboardEventHandler(toKeyboardEvent(event));
2449        }
2450    } else if (eventType == eventNames().clickEvent) {
2451        int detail = event->isUIEvent() ? static_cast<UIEvent*>(event)->detail() : 0;
2452        if (dispatchDOMActivateEvent(detail, event))
2453            event->setDefaultHandled();
2454    } else if (eventType == eventNames().contextmenuEvent) {
2455        if (Frame* frame = document()->frame())
2456            if (Page* page = frame->page())
2457                page->contextMenuController()->handleContextMenuEvent(event);
2458    } else if (eventType == eventNames().textInputEvent) {
2459        if (event->hasInterface(eventNames().interfaceForTextEvent))
2460            if (Frame* frame = document()->frame())
2461                frame->eventHandler()->defaultTextInputEventHandler(static_cast<TextEvent*>(event));
2462#if OS(WINDOWS)
2463    } else if (eventType == eventNames().mousedownEvent && event->isMouseEvent()) {
2464        MouseEvent* mouseEvent = toMouseEvent(event);
2465        if (mouseEvent->button() == MiddleButton) {
2466            if (enclosingLinkEventParentOrSelf())
2467                return;
2468
2469            RenderObject* renderer = this->renderer();
2470            while (renderer && (!renderer->isBox() || !toRenderBox(renderer)->canBeScrolledAndHasScrollableArea()))
2471                renderer = renderer->parent();
2472
2473            if (renderer) {
2474                if (Frame* frame = document()->frame())
2475                    frame->eventHandler()->startPanScrolling(renderer);
2476            }
2477        }
2478#endif
2479    } else if (eventType == eventNames().mousewheelEvent && event->hasInterface(eventNames().interfaceForWheelEvent)) {
2480        WheelEvent* wheelEvent = static_cast<WheelEvent*>(event);
2481
2482        // If we don't have a renderer, send the wheel event to the first node we find with a renderer.
2483        // This is needed for <option> and <optgroup> elements so that <select>s get a wheel scroll.
2484        Node* startNode = this;
2485        while (startNode && !startNode->renderer())
2486            startNode = startNode->parentOrShadowHostNode();
2487
2488        if (startNode && startNode->renderer())
2489            if (Frame* frame = document()->frame())
2490                frame->eventHandler()->defaultWheelEventHandler(startNode, wheelEvent);
2491    } else if (event->type() == eventNames().webkitEditableContentChangedEvent) {
2492        dispatchInputEvent();
2493    }
2494}
2495
2496void Node::willCallDefaultEventHandler(const Event&)
2497{
2498}
2499
2500bool Node::willRespondToMouseMoveEvents()
2501{
2502    if (isDisabledFormControl(this))
2503        return false;
2504    return hasEventListeners(eventNames().mousemoveEvent) || hasEventListeners(eventNames().mouseoverEvent) || hasEventListeners(eventNames().mouseoutEvent);
2505}
2506
2507bool Node::willRespondToMouseClickEvents()
2508{
2509    if (isDisabledFormControl(this))
2510        return false;
2511    return isContentEditable(UserSelectAllIsAlwaysNonEditable) || hasEventListeners(eventNames().mouseupEvent) || hasEventListeners(eventNames().mousedownEvent) || hasEventListeners(eventNames().clickEvent) || hasEventListeners(eventNames().DOMActivateEvent);
2512}
2513
2514bool Node::willRespondToTouchEvents()
2515{
2516    if (isDisabledFormControl(this))
2517        return false;
2518    return hasEventListeners(eventNames().touchstartEvent) || hasEventListeners(eventNames().touchmoveEvent) || hasEventListeners(eventNames().touchcancelEvent) || hasEventListeners(eventNames().touchendEvent);
2519}
2520
2521// This is here for inlining
2522inline void TreeScope::removedLastRefToScope()
2523{
2524    ASSERT(!deletionHasBegun());
2525    if (m_guardRefCount) {
2526        // If removing a child removes the last self-only ref, we don't
2527        // want the scope to be destructed until after
2528        // removeDetachedChildren returns, so we guard ourselves with an
2529        // extra self-only ref.
2530        guardRef();
2531        dispose();
2532#ifndef NDEBUG
2533        // We need to do this right now since guardDeref() can delete this.
2534        rootNode()->m_inRemovedLastRefFunction = false;
2535#endif
2536        guardDeref();
2537    } else {
2538#ifndef NDEBUG
2539        rootNode()->m_inRemovedLastRefFunction = false;
2540        beginDeletion();
2541#endif
2542        delete this;
2543    }
2544}
2545
2546// It's important not to inline removedLastRef, because we don't want to inline the code to
2547// delete a Node at each deref call site.
2548void Node::removedLastRef()
2549{
2550    // An explicit check for Document here is better than a virtual function since it is
2551    // faster for non-Document nodes, and because the call to removedLastRef that is inlined
2552    // at all deref call sites is smaller if it's a non-virtual function.
2553    if (isTreeScope()) {
2554        treeScope()->removedLastRefToScope();
2555        return;
2556    }
2557
2558#ifndef NDEBUG
2559    m_deletionHasBegun = true;
2560#endif
2561    delete this;
2562}
2563
2564void Node::textRects(Vector<IntRect>& rects) const
2565{
2566    RefPtr<Range> range = Range::create(document());
2567    range->selectNodeContents(const_cast<Node*>(this), IGNORE_EXCEPTION);
2568    range->textRects(rects);
2569}
2570
2571unsigned Node::connectedSubframeCount() const
2572{
2573    return hasRareData() ? rareData()->connectedSubframeCount() : 0;
2574}
2575
2576void Node::incrementConnectedSubframeCount(unsigned amount)
2577{
2578    ASSERT(isContainerNode());
2579    ensureRareData()->incrementConnectedSubframeCount(amount);
2580}
2581
2582void Node::decrementConnectedSubframeCount(unsigned amount)
2583{
2584    rareData()->decrementConnectedSubframeCount(amount);
2585}
2586
2587void Node::updateAncestorConnectedSubframeCountForRemoval() const
2588{
2589    unsigned count = connectedSubframeCount();
2590
2591    if (!count)
2592        return;
2593
2594    for (Node* node = parentOrShadowHostNode(); node; node = node->parentOrShadowHostNode())
2595        node->decrementConnectedSubframeCount(count);
2596}
2597
2598void Node::updateAncestorConnectedSubframeCountForInsertion() const
2599{
2600    unsigned count = connectedSubframeCount();
2601
2602    if (!count)
2603        return;
2604
2605    for (Node* node = parentOrShadowHostNode(); node; node = node->parentOrShadowHostNode())
2606        node->incrementConnectedSubframeCount(count);
2607}
2608
2609PassRefPtr<NodeList> Node::getDestinationInsertionPoints()
2610{
2611    document()->updateDistributionForNodeIfNeeded(this);
2612    Vector<InsertionPoint*, 8> insertionPoints;
2613    collectInsertionPointsWhereNodeIsDistributed(this, insertionPoints);
2614    for (size_t i = 0; i < insertionPoints.size(); ++i) {
2615        InsertionPoint* insertionPoint = insertionPoints[i];
2616        ASSERT(insertionPoint->containingShadowRoot());
2617        if (insertionPoint->containingShadowRoot()->type() == ShadowRoot::UserAgentShadowRoot)
2618            return StaticNodeList::createEmpty();
2619    }
2620    Vector<RefPtr<Node> > asNodes;
2621    asNodes.appendRange(insertionPoints.begin(), insertionPoints.end());
2622    return StaticNodeList::adopt(asNodes);
2623}
2624
2625void Node::registerScopedHTMLStyleChild()
2626{
2627    setHasScopedHTMLStyleChild(true);
2628}
2629
2630void Node::unregisterScopedHTMLStyleChild()
2631{
2632    ASSERT(hasScopedHTMLStyleChild());
2633    setHasScopedHTMLStyleChild(numberOfScopedHTMLStyleChildren());
2634}
2635
2636size_t Node::numberOfScopedHTMLStyleChildren() const
2637{
2638    size_t count = 0;
2639    for (Node* child = firstChild(); child; child = child->nextSibling()) {
2640        if (child->hasTagName(HTMLNames::styleTag) && toHTMLStyleElement(child)->isRegisteredAsScoped())
2641            count++;
2642    }
2643
2644    return count;
2645}
2646
2647void Node::setFocus(bool flag)
2648{
2649    if (Document* document = this->document())
2650        document->userActionElements().setFocused(this, flag);
2651}
2652
2653void Node::setActive(bool flag, bool)
2654{
2655    if (Document* document = this->document())
2656        document->userActionElements().setActive(this, flag);
2657}
2658
2659void Node::setHovered(bool flag)
2660{
2661    if (Document* document = this->document())
2662        document->userActionElements().setHovered(this, flag);
2663}
2664
2665bool Node::isUserActionElementActive() const
2666{
2667    ASSERT(isUserActionElement());
2668    return document()->userActionElements().isActive(this);
2669}
2670
2671bool Node::isUserActionElementInActiveChain() const
2672{
2673    ASSERT(isUserActionElement());
2674    return document()->userActionElements().isInActiveChain(this);
2675}
2676
2677bool Node::isUserActionElementHovered() const
2678{
2679    ASSERT(isUserActionElement());
2680    return document()->userActionElements().isHovered(this);
2681}
2682
2683bool Node::isUserActionElementFocused() const
2684{
2685    ASSERT(isUserActionElement());
2686    return document()->userActionElements().isFocused(this);
2687}
2688
2689void Node::setCustomElementState(CustomElementState newState)
2690{
2691    CustomElementState oldState = customElementState();
2692
2693    switch (newState) {
2694    case NotCustomElement:
2695        ASSERT_NOT_REACHED(); // Everything starts in this state
2696        return;
2697
2698    case UpgradeCandidate:
2699        ASSERT(NotCustomElement == oldState);
2700        break;
2701
2702    case Defined:
2703        ASSERT(UpgradeCandidate == oldState || NotCustomElement == oldState);
2704        break;
2705
2706    case Upgraded:
2707        ASSERT(Defined == oldState);
2708        break;
2709    }
2710
2711    ASSERT(isHTMLElement() || isSVGElement());
2712    setFlag(newState & 1, CustomElementIsUpgradeCandidateOrUpgraded);
2713    setFlag(newState & 2, CustomElementHasDefinitionOrIsUpgraded);
2714
2715    if (oldState == NotCustomElement || newState == Upgraded)
2716        setNeedsStyleRecalc(); // :unresolved has changed
2717}
2718
2719} // namespace WebCore
2720
2721#ifndef NDEBUG
2722
2723void showTree(const WebCore::Node* node)
2724{
2725    if (node)
2726        node->showTreeForThis();
2727}
2728
2729void showNodePath(const WebCore::Node* node)
2730{
2731    if (node)
2732        node->showNodePathForThis();
2733}
2734
2735#endif
2736