[SCM] WebKit Debian packaging branch, debian/unstable, updated. debian/1.1.15-1-40151-g37bb677
mjs
mjs at 268f45cc-cd09-0410-ab3c-d52691b4dbfc
Sat Sep 26 08:09:25 UTC 2009
The following commit has been merged in the debian/unstable branch:
commit 66976e2378e4ffd0e46ce158b570794c8bf206ce
Author: mjs <mjs at 268f45cc-cd09-0410-ab3c-d52691b4dbfc>
Date: Wed Nov 5 20:00:33 2003 +0000
Reviewed by Darin.
- fixed 3473906 - getElementById takes about 44% of time on particular slow intel page
I fixed this by adding a per-document id --> element hash
table. This speeds up my local copy of the intel page by 60% (50
sec to 20 sec!) and does not cause any PLT slowdown.
* khtml/xml/dom_docimpl.h: New QDict field for id to element hash table.
* khtml/xml/dom_docimpl.cpp:
(DocumentImpl::getElementById): Just look it up in the newly
added hash table.
(DocumentImpl::addElementById): New method. Add to hash table if
no other element is set for that key (this lets the first element
of several with matching ids win).
(DocumentImpl::removeElementById): New method. Remove from hash
table only if the key and value both match.
These Element changes to keep the id --> element hashtable working
seem needlessly tricky, due to lack of bottlenecks in attribute
changing.
* khtml/xml/dom_elementimpl.cpp:
(ElementImpl::updateId): New method that removes element from
hash table for old it
(ElementImpl::setAttribute): If setting id, call updateId.
(ElementImpl::setAttributeMap): If either the old or the new map
includes id, call updateId.
(ElementImpl::attach): If we have an id, call updateId to set it
after attaching.
(ElementImpl::detach): Newly added. If we have an id, call
updateId to clear it before detaching.
(NamedAttrMapImpl::setNamedItem): If the name is id, call updateId on
our element.
(NamedAttrMapImpl::removeNamedItem): If the name is id, call updateId on
our element.
(NamedAttrMapImpl::operator=): If old or new contents include id attribute,
call updateId on our element.
* khtml/xml/dom_elementimpl.h: Prototype new methods.
git-svn-id: http://svn.webkit.org/repository/webkit/trunk@5391 268f45cc-cd09-0410-ab3c-d52691b4dbfc
diff --git a/WebCore/ChangeLog-2005-08-23 b/WebCore/ChangeLog-2005-08-23
index 6c39c67..0db1d24 100644
--- a/WebCore/ChangeLog-2005-08-23
+++ b/WebCore/ChangeLog-2005-08-23
@@ -1,3 +1,45 @@
+2003-11-05 Maciej Stachowiak <mjs at apple.com>
+
+ Reviewed by Darin.
+
+ - fixed 3473906 - getElementById takes about 44% of time on particular slow intel page
+
+ I fixed this by adding a per-document id --> element hash
+ table. This speeds up my local copy of the intel page by 60% (50
+ sec to 20 sec!) and does not cause any PLT slowdown.
+
+ * khtml/xml/dom_docimpl.h: New QDict field for id to element hash table.
+ * khtml/xml/dom_docimpl.cpp:
+ (DocumentImpl::getElementById): Just look it up in the newly
+ added hash table.
+ (DocumentImpl::addElementById): New method. Add to hash table if
+ no other element is set for that key (this lets the first element
+ of several with matching ids win).
+ (DocumentImpl::removeElementById): New method. Remove from hash
+ table only if the key and value both match.
+
+ These Element changes to keep the id --> element hashtable working
+ seem needlessly tricky, due to lack of bottlenecks in attribute
+ changing.
+
+ * khtml/xml/dom_elementimpl.cpp:
+ (ElementImpl::updateId): New method that removes element from
+ hash table for old it
+ (ElementImpl::setAttribute): If setting id, call updateId.
+ (ElementImpl::setAttributeMap): If either the old or the new map
+ includes id, call updateId.
+ (ElementImpl::attach): If we have an id, call updateId to set it
+ after attaching.
+ (ElementImpl::detach): Newly added. If we have an id, call
+ updateId to clear it before detaching.
+ (NamedAttrMapImpl::setNamedItem): If the name is id, call updateId on
+ our element.
+ (NamedAttrMapImpl::removeNamedItem): If the name is id, call updateId on
+ our element.
+ (NamedAttrMapImpl::operator=): If old or new contents include id attribute,
+ call updateId on our element.
+ * khtml/xml/dom_elementimpl.h: Prototype new methods.
+
2003-11-05 Ken Kocienda <kocienda at apple.com>
Reviewed by Maciej
diff --git a/WebCore/khtml/xml/dom_docimpl.cpp b/WebCore/khtml/xml/dom_docimpl.cpp
index 837cd82..528081c 100644
--- a/WebCore/khtml/xml/dom_docimpl.cpp
+++ b/WebCore/khtml/xml/dom_docimpl.cpp
@@ -524,43 +524,29 @@ ElementImpl *DocumentImpl::getElementById( const DOMString &elementId ) const
return 0;
}
- QPtrStack<NodeImpl> nodeStack;
- NodeImpl *current = _first;
+ return m_elementsById.find(elementId.string());
+}
- while(1)
- {
- if(!current)
- {
- if(nodeStack.isEmpty()) break;
- current = nodeStack.pop();
- current = current->nextSibling();
- }
- else
- {
- if(current->isElementNode())
- {
- ElementImpl *e = static_cast<ElementImpl *>(current);
- if(e->getAttribute(ATTR_ID) == elementId)
- return e;
- }
- NodeImpl *child = current->firstChild();
- if(child)
- {
- nodeStack.push(current);
- current = child;
- }
- else
- {
- current = current->nextSibling();
- }
- }
+void DocumentImpl::addElementById(const DOMString &elementId, ElementImpl *element)
+{
+ QString qId = elementId.string();
+
+ if (m_elementsById.find(qId) == NULL) {
+ m_elementsById.insert(qId, element);
}
+}
- //kdDebug() << "WARNING: *DocumentImpl::getElementById not found " << elementId.string() << endl;
- return 0;
+void DocumentImpl::removeElementById(const DOMString &elementId, ElementImpl *element)
+{
+ QString qId = elementId.string();
+
+ if (m_elementsById.find(qId) == element) {
+ m_elementsById.remove(qId);
+ }
}
+
void DocumentImpl::setTitle(DOMString _title)
{
m_title = _title;
diff --git a/WebCore/khtml/xml/dom_docimpl.h b/WebCore/khtml/xml/dom_docimpl.h
index 04f7e80..b4ea5f1 100644
--- a/WebCore/khtml/xml/dom_docimpl.h
+++ b/WebCore/khtml/xml/dom_docimpl.h
@@ -460,6 +460,9 @@ public:
// and make it sensitive to the type of document.
static bool isValidName(const DOMString &);
+ void addElementById(const DOMString &elementId, ElementImpl *element);
+ void removeElementById(const DOMString &elementId, ElementImpl *element);
+
signals:
void finishedParsing();
@@ -582,7 +585,9 @@ private:
int m_secureForms;
khtml::Decoder *m_decoder;
-
+
+ QDict<ElementImpl> m_elementsById;
+
bool m_createRenderers;
#endif
};
diff --git a/WebCore/khtml/xml/dom_elementimpl.cpp b/WebCore/khtml/xml/dom_elementimpl.cpp
index 56304fc..213ab4b 100644
--- a/WebCore/khtml/xml/dom_elementimpl.cpp
+++ b/WebCore/khtml/xml/dom_elementimpl.cpp
@@ -227,6 +227,10 @@ void ElementImpl::setAttribute(NodeImpl::Id id, DOMStringImpl* value, int &excep
exceptioncode = DOMException::NO_MODIFICATION_ALLOWED_ERR;
return;
}
+
+ if (id == ATTR_ID) {
+ updateId(old ? old->val() : 0, value);
+ }
if (old && !value)
namedAttrMap->removeAttribute(id);
@@ -240,6 +244,16 @@ void ElementImpl::setAttribute(NodeImpl::Id id, DOMStringImpl* value, int &excep
void ElementImpl::setAttributeMap( NamedAttrMapImpl* list )
{
+ // If setting the whole map changes the id attribute, we need to
+ // call updateId.
+
+ AttributeImpl *oldId = namedAttrMap ? namedAttrMap->getAttributeItem(ATTR_ID) : 0;
+ AttributeImpl *newId = list ? list->getAttributeItem(ATTR_ID) : 0;
+
+ if (oldId || newId) {
+ updateId(oldId ? oldId->val() : 0, newId ? newId->val() : 0);
+ }
+
if(namedAttrMap)
namedAttrMap->deref();
@@ -334,6 +348,28 @@ void ElementImpl::attach()
createRendererIfNeeded();
#endif
NodeBaseImpl::attach();
+
+ NamedAttrMapImpl *attrs = attributes(true);
+
+ if (attrs) {
+ AttributeImpl *idAttr = attrs->getAttributeItem(ATTR_ID);
+ if (idAttr && idAttr->val()) {
+ updateId(0, idAttr->val());
+ }
+ }
+}
+
+void ElementImpl::detach()
+{
+ NamedAttrMapImpl *attrs = attributes(true);
+ if (attrs) {
+ AttributeImpl *idAttr = attrs->getAttributeItem(ATTR_ID);
+ if (idAttr && idAttr->val()) {
+ updateId(idAttr->val(), 0);
+ }
+ }
+
+ NodeBaseImpl::detach();
}
void ElementImpl::recalcStyle( StyleChange change )
@@ -458,6 +494,30 @@ void ElementImpl::dispatchAttrAdditionEvent(AttributeImpl *attr)
// attr->value(),getDocument()->attrName(attr->id()),MutationEvent::ADDITION),exceptioncode);
}
+
+void ElementImpl::updateId(DOMStringImpl* oldId, DOMStringImpl* newId)
+{
+ if (!attached())
+ return;
+
+ if (oldId == newId)
+ return;
+
+ DOMString oldIdStr(oldId);
+ DOMString newIdStr(newId);
+
+ DocumentImpl* doc = getDocument();
+
+ if (oldIdStr == newIdStr)
+ return;
+
+ if (!oldIdStr.isEmpty())
+ doc->removeElementById(oldIdStr, this);
+
+ if (!newIdStr.isEmpty())
+ doc->addElementById(newIdStr, this);
+}
+
#ifndef NDEBUG
void ElementImpl::dump(QTextStream *stream, QString ind) const
{
@@ -603,6 +663,10 @@ Node NamedAttrMapImpl::setNamedItem ( NodeImpl* arg, int &exceptioncode )
return 0;
}
+ if (a->id() == ATTR_ID) {
+ element->updateId(old ? old->val() : 0, a->val());
+ }
+
// ### slightly inefficient - resizes attribute array twice.
Node r;
if (old) {
@@ -611,6 +675,7 @@ Node NamedAttrMapImpl::setNamedItem ( NodeImpl* arg, int &exceptioncode )
r = old->_impl;
removeAttribute(a->id());
}
+
addAttribute(a);
return r;
}
@@ -635,6 +700,11 @@ Node NamedAttrMapImpl::removeNamedItem ( NodeImpl::Id id, int &exceptioncode )
if (!a->attrImpl()) a->allocateImpl(element);
Node r(a->attrImpl());
+
+ if (id == ATTR_ID) {
+ element->updateId(a->val(), 0);
+ }
+
removeAttribute(id);
return r;
}
@@ -701,6 +771,16 @@ NamedAttrMapImpl& NamedAttrMapImpl::operator=(const NamedAttrMapImpl& other)
// clone all attributes in the other map, but attach to our element
if (!element) return *this;
+ // If assigning the map changes the id attribute, we need to call
+ // updateId.
+
+ AttributeImpl *oldId = getAttributeItem(ATTR_ID);
+ AttributeImpl *newId = other.getAttributeItem(ATTR_ID);
+
+ if (oldId || newId) {
+ element->updateId(oldId ? oldId->val() : 0, newId ? newId->val() : 0);
+ }
+
clearAttributes();
len = other.len;
attrs = new AttributeImpl* [len];
diff --git a/WebCore/khtml/xml/dom_elementimpl.h b/WebCore/khtml/xml/dom_elementimpl.h
index d61f2cb..f9da3f8 100644
--- a/WebCore/khtml/xml/dom_elementimpl.h
+++ b/WebCore/khtml/xml/dom_elementimpl.h
@@ -192,6 +192,7 @@ public:
virtual QString state() { return QString::null; }
virtual void attach();
+ virtual void detach();
virtual khtml::RenderStyle *styleForRenderer(khtml::RenderObject *parent);
virtual khtml::RenderObject *createRenderer(RenderArena *, khtml::RenderStyle *);
virtual void recalcStyle( StyleChange = NoChange );
@@ -227,6 +228,8 @@ private:
// in the DTD
virtual NamedAttrMapImpl* defaultMap() const;
+ void updateId(DOMStringImpl* oldId, DOMStringImpl* newId);
+
protected: // member variables
mutable NamedAttrMapImpl *namedAttrMap;
--
WebKit Debian packaging
More information about the Pkg-webkit-commits
mailing list