Module: wine Branch: master Commit: 110155099b3b51a4ce7f6b979eb56f14b8d8f950 URL: http://source.winehq.org/git/wine.git/?a=commit;h=110155099b3b51a4ce7f6b979e...
Author: Jacek Caban jacek@codeweavers.com Date: Wed Mar 2 13:34:04 2011 +0100
mshtml: Reuse attribute objects.
---
dlls/mshtml/htmlattr.c | 7 ++++++- dlls/mshtml/htmlelem.c | 7 +++++++ dlls/mshtml/htmlelem3.c | 30 +++++++++++++++++++++--------- dlls/mshtml/mshtml_private.h | 6 +++++- dlls/mshtml/tests/dom.c | 1 - 5 files changed, 39 insertions(+), 12 deletions(-)
diff --git a/dlls/mshtml/htmlattr.c b/dlls/mshtml/htmlattr.c index 9fef7d8..bd0f6a2 100644 --- a/dlls/mshtml/htmlattr.c +++ b/dlls/mshtml/htmlattr.c @@ -18,6 +18,7 @@
#include <stdarg.h> +#include <assert.h>
#define COBJMACROS
@@ -78,6 +79,7 @@ static ULONG WINAPI HTMLDOMAttribute_Release(IHTMLDOMAttribute *iface) TRACE("(%p) ref=%d\n", This, ref);
if(!ref) { + assert(!This->elem); nsIDOMAttr_Release(This->nsattr); release_dispex(&This->dispex); heap_free(This); @@ -189,7 +191,7 @@ static dispex_static_data_t HTMLDOMAttribute_dispex = { HTMLDOMAttribute_iface_tids };
-HRESULT HTMLDOMAttribute_Create(HTMLDocumentNode *doc, nsIDOMAttr *nsattr, HTMLDOMAttribute **attr) +HRESULT HTMLDOMAttribute_Create(HTMLElement *elem, nsIDOMAttr *nsattr, HTMLDOMAttribute **attr) { HTMLDOMAttribute *ret;
@@ -203,6 +205,9 @@ HRESULT HTMLDOMAttribute_Create(HTMLDocumentNode *doc, nsIDOMAttr *nsattr, HTMLD nsIDOMAttr_AddRef(nsattr); ret->nsattr = nsattr;
+ ret->elem = elem; + list_add_tail(&elem->attrs, &ret->entry); + init_dispex(&ret->dispex, (IUnknown*)&ret->IHTMLDOMAttribute_iface, &HTMLDOMAttribute_dispex);
diff --git a/dlls/mshtml/htmlelem.c b/dlls/mshtml/htmlelem.c index 897a7c5..c4d5607 100644 --- a/dlls/mshtml/htmlelem.c +++ b/dlls/mshtml/htmlelem.c @@ -1647,6 +1647,12 @@ HRESULT HTMLElement_QI(HTMLDOMNode *iface, REFIID riid, void **ppv) void HTMLElement_destructor(HTMLDOMNode *iface) { HTMLElement *This = impl_from_HTMLDOMNode(iface); + HTMLDOMAttribute *attr; + + LIST_FOR_EACH_ENTRY(attr, &This->attrs, HTMLDOMAttribute, entry) { + attr->elem = NULL; + IHTMLDOMAttribute_Release(&attr->IHTMLDOMAttribute_iface); + }
ConnectionPointContainer_Destroy(&This->cp_container);
@@ -1742,6 +1748,7 @@ void HTMLElement_Init(HTMLElement *This, HTMLDocumentNode *doc, nsIDOMHTMLElemen if(nselem) nsIDOMHTMLElement_AddRef(nselem); This->nselem = nselem; + list_init(&This->attrs);
HTMLDOMNode_Init(doc, &This->node, (nsIDOMNode*)nselem);
diff --git a/dlls/mshtml/htmlelem3.c b/dlls/mshtml/htmlelem3.c index 7841346..02015e5 100644 --- a/dlls/mshtml/htmlelem3.c +++ b/dlls/mshtml/htmlelem3.c @@ -560,7 +560,7 @@ static HRESULT WINAPI HTMLElement4_normalize(IHTMLElement4 *iface) static HRESULT WINAPI HTMLElement4_getAttributeNode(IHTMLElement4 *iface, BSTR bstrname, IHTMLDOMAttribute **ppAttribute) { HTMLElement *This = impl_from_IHTMLElement4(iface); - HTMLDOMAttribute *attr; + HTMLDOMAttribute *attr = NULL, *iter; nsAString name_str; nsIDOMAttr *nsattr; nsresult nsres; @@ -576,16 +576,28 @@ static HRESULT WINAPI HTMLElement4_getAttributeNode(IHTMLElement4 *iface, BSTR b return E_FAIL; }
- if(nsattr) { - hres = HTMLDOMAttribute_Create(This->node.doc, nsattr, &attr); - nsIDOMAttr_Release(nsattr); - if(FAILED(hres)) - return hres; - - *ppAttribute = &attr->IHTMLDOMAttribute_iface; - }else { + if(!nsattr) { *ppAttribute = NULL; + return S_OK; + } + + LIST_FOR_EACH_ENTRY(iter, &This->attrs, HTMLDOMAttribute, entry) { + if(iter->nsattr == nsattr) { + attr = iter; + break; + } } + + if(!attr) { + hres = HTMLDOMAttribute_Create(This, nsattr, &attr); + if(FAILED(hres)) { + nsIDOMAttr_Release(nsattr); + return hres; + } + } + + IHTMLDOMAttribute_AddRef(&attr->IHTMLDOMAttribute_iface); + *ppAttribute = &attr->IHTMLDOMAttribute_iface; return S_OK; }
diff --git a/dlls/mshtml/mshtml_private.h b/dlls/mshtml/mshtml_private.h index 0adb344..b39ad75 100644 --- a/dlls/mshtml/mshtml_private.h +++ b/dlls/mshtml/mshtml_private.h @@ -561,6 +561,7 @@ typedef struct {
nsIDOMHTMLElement *nselem; HTMLStyle *style; + struct list attrs; } HTMLElement;
#define HTMLELEMENT_TIDS \ @@ -749,9 +750,12 @@ typedef struct {
LONG ref; nsIDOMAttr *nsattr; + + HTMLElement *elem; + struct list entry; } HTMLDOMAttribute;
-HRESULT HTMLDOMAttribute_Create(HTMLDocumentNode*,nsIDOMAttr*,HTMLDOMAttribute**); +HRESULT HTMLDOMAttribute_Create(HTMLElement*,nsIDOMAttr*,HTMLDOMAttribute**);
HRESULT HTMLElement_Create(HTMLDocumentNode*,nsIDOMNode*,BOOL,HTMLElement**); HRESULT HTMLCommentElement_Create(HTMLDocumentNode*,nsIDOMNode*,HTMLElement**); diff --git a/dlls/mshtml/tests/dom.c b/dlls/mshtml/tests/dom.c index 85bac69..88d8790 100644 --- a/dlls/mshtml/tests/dom.c +++ b/dlls/mshtml/tests/dom.c @@ -6812,7 +6812,6 @@ static void test_attr(IHTMLElement *elem) test_no_iface((IUnknown*)attr, &IID_IHTMLDOMNode);
attr2 = get_elem_attr_node((IUnknown*)elem, "id", TRUE); - todo_wine ok(iface_cmp((IUnknown*)attr, (IUnknown*)attr2), "attr != attr2\n"); IHTMLDOMAttribute_Release(attr2);