2 * DOM Document implementation
4 * Copyright 2005 Mike McCormack
6 * This library is free software; you can redistribute it and/or
7 * modify it under the terms of the GNU Lesser General Public
8 * License as published by the Free Software Foundation; either
9 * version 2.1 of the License, or (at your option) any later version.
11 * This library is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 * Lesser General Public License for more details.
16 * You should have received a copy of the GNU Lesser General Public
17 * License along with this library; if not, write to the Free Software
18 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
22 #define NONAMELESSUNION
41 #include "wine/debug.h"
42 #include "wine/list.h"
44 #include "msxml_private.h"
46 WINE_DEFAULT_DEBUG_CHANNEL(msxml
);
50 static const WCHAR SZ_PROPERTY_SELECTION_LANGUAGE
[] = {'S','e','l','e','c','t','i','o','n','L','a','n','g','u','a','g','e',0};
51 static const WCHAR SZ_VALUE_XPATH
[] = {'X','P','a','t','h',0};
52 static const WCHAR SZ_VALUE_XSLPATTERN
[] = {'X','S','L','P','a','t','t','e','r','n',0};
54 typedef struct _domdoc
56 const struct IXMLDOMDocument2Vtbl
*lpVtbl
;
57 const struct IPersistStreamVtbl
*lpvtblIPersistStream
;
58 const struct IObjectWithSiteVtbl
*lpvtblIObjectWithSite
;
59 const struct IObjectSafetyVtbl
*lpvtblIObjectSafety
;
62 VARIANT_BOOL validating
;
63 VARIANT_BOOL resolving
;
64 VARIANT_BOOL preserving
;
68 IXMLDOMSchemaCollection
*schema
;
86 In native windows, the whole lifetime management of XMLDOMNodes is
87 managed automatically using reference counts. Wine emulates that by
88 maintaining a reference count to the document that is increased for
89 each IXMLDOMNode pointer passed out for this document. If all these
90 pointers are gone, the document is unreachable and gets freed, that
91 is, all nodes in the tree of the document get freed.
93 You are able to create nodes that are associated to a document (in
94 fact, in msxml's XMLDOM model, all nodes are associated to a document),
95 but not in the tree of that document, for example using the createFoo
96 functions from IXMLDOMDocument. These nodes do not get cleaned up
97 by libxml, so we have to do it ourselves.
99 To catch these nodes, a list of "orphan nodes" is introduced.
100 It contains pointers to all roots of node trees that are
101 associated with the document without being part of the document
102 tree. All nodes with parent==NULL (except for the document root nodes)
103 should be in the orphan node list of their document. All orphan nodes
104 get freed together with the document itself.
107 typedef struct _xmldoc_priv
{
112 typedef struct _orphan_entry
{
117 static inline xmldoc_priv
* priv_from_xmlDocPtr(xmlDocPtr doc
)
119 return doc
->_private
;
122 static xmldoc_priv
* create_priv(void)
125 priv
= HeapAlloc( GetProcessHeap(), 0, sizeof (*priv
) );
130 list_init( &priv
->orphans
);
136 static xmlDocPtr
doparse( char *ptr
, int len
)
138 #ifdef HAVE_XMLREADMEMORY
140 * use xmlReadMemory if possible so we can suppress
141 * writing errors to stderr
143 return xmlReadMemory( ptr
, len
, NULL
, NULL
,
144 XML_PARSE_NOERROR
| XML_PARSE_NOWARNING
| XML_PARSE_NOBLANKS
);
146 return xmlParseMemory( ptr
, len
);
150 LONG
xmldoc_add_ref(xmlDocPtr doc
)
152 LONG ref
= InterlockedIncrement(&priv_from_xmlDocPtr(doc
)->refs
);
157 LONG
xmldoc_release(xmlDocPtr doc
)
159 xmldoc_priv
*priv
= priv_from_xmlDocPtr(doc
);
160 LONG ref
= InterlockedDecrement(&priv
->refs
);
164 orphan_entry
*orphan
, *orphan2
;
165 TRACE("freeing docptr %p\n", doc
);
167 LIST_FOR_EACH_ENTRY_SAFE( orphan
, orphan2
, &priv
->orphans
, orphan_entry
, entry
)
169 xmlFreeNode( orphan
->node
);
170 HeapFree( GetProcessHeap(), 0, orphan
);
172 HeapFree(GetProcessHeap(), 0, doc
->_private
);
180 HRESULT
xmldoc_add_orphan(xmlDocPtr doc
, xmlNodePtr node
)
182 xmldoc_priv
*priv
= priv_from_xmlDocPtr(doc
);
185 entry
= HeapAlloc( GetProcessHeap(), 0, sizeof (*entry
) );
187 return E_OUTOFMEMORY
;
190 list_add_head( &priv
->orphans
, &entry
->entry
);
194 HRESULT
xmldoc_remove_orphan(xmlDocPtr doc
, xmlNodePtr node
)
196 xmldoc_priv
*priv
= priv_from_xmlDocPtr(doc
);
197 orphan_entry
*entry
, *entry2
;
199 LIST_FOR_EACH_ENTRY_SAFE( entry
, entry2
, &priv
->orphans
, orphan_entry
, entry
)
201 if( entry
->node
== node
)
203 list_remove( &entry
->entry
);
204 HeapFree( GetProcessHeap(), 0, entry
);
212 static inline domdoc
*impl_from_IXMLDOMDocument2( IXMLDOMDocument2
*iface
)
214 return (domdoc
*)((char*)iface
- FIELD_OFFSET(domdoc
, lpVtbl
));
217 static inline xmlDocPtr
get_doc( domdoc
*This
)
219 return (xmlDocPtr
) xmlNodePtr_from_domnode( This
->node
, XML_DOCUMENT_NODE
);
222 static inline domdoc
*impl_from_IPersistStream(IPersistStream
*iface
)
224 return (domdoc
*)((char*)iface
- FIELD_OFFSET(domdoc
, lpvtblIPersistStream
));
227 static inline domdoc
*impl_from_IObjectWithSite(IObjectWithSite
*iface
)
229 return (domdoc
*)((char*)iface
- FIELD_OFFSET(domdoc
, lpvtblIObjectWithSite
));
232 static inline domdoc
*impl_from_IObjectSafety(IObjectSafety
*iface
)
234 return (domdoc
*)((char*)iface
- FIELD_OFFSET(domdoc
, lpvtblIObjectSafety
));
238 /************************************************************************
239 * xmldoc implementation of IPersistStream.
241 static HRESULT WINAPI
xmldoc_IPersistStream_QueryInterface(
242 IPersistStream
*iface
, REFIID riid
, LPVOID
*ppvObj
)
244 domdoc
*this = impl_from_IPersistStream(iface
);
245 return IXMLDocument_QueryInterface((IXMLDocument
*)this, riid
, ppvObj
);
248 static ULONG WINAPI
xmldoc_IPersistStream_AddRef(
249 IPersistStream
*iface
)
251 domdoc
*this = impl_from_IPersistStream(iface
);
252 return IXMLDocument_AddRef((IXMLDocument
*)this);
255 static ULONG WINAPI
xmldoc_IPersistStream_Release(
256 IPersistStream
*iface
)
258 domdoc
*this = impl_from_IPersistStream(iface
);
259 return IXMLDocument_Release((IXMLDocument
*)this);
262 static HRESULT WINAPI
xmldoc_IPersistStream_GetClassID(
263 IPersistStream
*iface
, CLSID
*classid
)
265 TRACE("(%p,%p): stub!\n", iface
, classid
);
270 *classid
= CLSID_DOMDocument2
;
275 static HRESULT WINAPI
xmldoc_IPersistStream_IsDirty(
276 IPersistStream
*iface
)
278 domdoc
*This
= impl_from_IPersistStream(iface
);
280 FIXME("(%p->%p): stub!\n", iface
, This
);
285 static HRESULT WINAPI
xmldoc_IPersistStream_Load(
286 IPersistStream
*iface
, LPSTREAM pStm
)
288 domdoc
*This
= impl_from_IPersistStream(iface
);
291 DWORD read
, written
, len
;
294 xmlDocPtr xmldoc
= NULL
;
296 TRACE("(%p, %p)\n", iface
, pStm
);
301 hr
= CreateStreamOnHGlobal(NULL
, TRUE
, &This
->stream
);
307 IStream_Read(pStm
, buf
, sizeof(buf
), &read
);
308 hr
= IStream_Write(This
->stream
, buf
, read
, &written
);
309 } while(SUCCEEDED(hr
) && written
!= 0 && read
!= 0);
313 ERR("Failed to copy stream\n");
317 hr
= GetHGlobalFromStream(This
->stream
, &hglobal
);
321 len
= GlobalSize(hglobal
);
322 ptr
= GlobalLock(hglobal
);
324 xmldoc
= parse_xml(ptr
, len
);
325 GlobalUnlock(hglobal
);
329 ERR("Failed to parse xml\n");
333 attach_xmlnode( This
->node
, (xmlNodePtr
)xmldoc
);
338 static HRESULT WINAPI
xmldoc_IPersistStream_Save(
339 IPersistStream
*iface
, LPSTREAM pStm
, BOOL fClearDirty
)
341 FIXME("(%p, %p, %d): stub!\n", iface
, pStm
, fClearDirty
);
345 static HRESULT WINAPI
xmldoc_IPersistStream_GetSizeMax(
346 IPersistStream
*iface
, ULARGE_INTEGER
*pcbSize
)
348 TRACE("(%p, %p): stub!\n", iface
, pcbSize
);
352 static const IPersistStreamVtbl xmldoc_IPersistStream_VTable
=
354 xmldoc_IPersistStream_QueryInterface
,
355 xmldoc_IPersistStream_AddRef
,
356 xmldoc_IPersistStream_Release
,
357 xmldoc_IPersistStream_GetClassID
,
358 xmldoc_IPersistStream_IsDirty
,
359 xmldoc_IPersistStream_Load
,
360 xmldoc_IPersistStream_Save
,
361 xmldoc_IPersistStream_GetSizeMax
,
364 static HRESULT WINAPI
domdoc_QueryInterface( IXMLDOMDocument2
*iface
, REFIID riid
, void** ppvObject
)
366 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
368 TRACE("%p %s %p\n", This
, debugstr_guid( riid
), ppvObject
);
372 if ( IsEqualGUID( riid
, &IID_IUnknown
) ||
373 IsEqualGUID( riid
, &IID_IDispatch
) ||
374 IsEqualGUID( riid
, &IID_IXMLDOMDocument
) ||
375 IsEqualGUID( riid
, &IID_IXMLDOMDocument2
) )
379 else if ( IsEqualGUID( riid
, &IID_IXMLDOMNode
) )
381 return IUnknown_QueryInterface(This
->node_unk
, riid
, ppvObject
);
383 else if (IsEqualGUID(&IID_IPersistStream
, riid
))
385 *ppvObject
= (IPersistStream
*)&(This
->lpvtblIPersistStream
);
387 else if (IsEqualGUID(&IID_IObjectWithSite
, riid
))
389 *ppvObject
= (IObjectWithSite
*)&(This
->lpvtblIObjectWithSite
);
391 else if(dispex_query_interface(&This
->dispex
, riid
, ppvObject
))
393 return *ppvObject
? S_OK
: E_NOINTERFACE
;
395 else if(IsEqualGUID(&IID_IRunnableObject
, riid
))
397 TRACE("IID_IRunnableObject not supported returning NULL\n");
398 return E_NOINTERFACE
;
402 FIXME("interface %s not implemented\n", debugstr_guid(riid
));
403 return E_NOINTERFACE
;
406 IXMLDOMDocument_AddRef( iface
);
412 static ULONG WINAPI
domdoc_AddRef(
413 IXMLDOMDocument2
*iface
)
415 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
416 TRACE("%p\n", This
);
417 return InterlockedIncrement( &This
->ref
);
421 static ULONG WINAPI
domdoc_Release(
422 IXMLDOMDocument2
*iface
)
424 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
427 TRACE("%p\n", This
);
429 ref
= InterlockedDecrement( &This
->ref
);
433 detach_bsc(This
->bsc
);
436 IUnknown_Release( This
->site
);
437 IUnknown_Release( This
->node_unk
);
438 if(This
->schema
) IXMLDOMSchemaCollection_Release( This
->schema
);
439 if (This
->stream
) IStream_Release(This
->stream
);
440 HeapFree( GetProcessHeap(), 0, This
);
446 static HRESULT WINAPI
domdoc_GetTypeInfoCount( IXMLDOMDocument2
*iface
, UINT
* pctinfo
)
448 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
450 TRACE("(%p)->(%p)\n", This
, pctinfo
);
457 static HRESULT WINAPI
domdoc_GetTypeInfo(
458 IXMLDOMDocument2
*iface
,
459 UINT iTInfo
, LCID lcid
, ITypeInfo
** ppTInfo
)
461 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
464 TRACE("(%p)->(%u %u %p)\n", This
, iTInfo
, lcid
, ppTInfo
);
466 hr
= get_typeinfo(IXMLDOMDocument2_tid
, ppTInfo
);
471 static HRESULT WINAPI
domdoc_GetIDsOfNames(
472 IXMLDOMDocument2
*iface
,
479 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
483 TRACE("(%p)->(%s %p %u %u %p)\n", This
, debugstr_guid(riid
), rgszNames
, cNames
,
486 if(!rgszNames
|| cNames
== 0 || !rgDispId
)
489 hr
= get_typeinfo(IXMLDOMDocument2_tid
, &typeinfo
);
492 hr
= ITypeInfo_GetIDsOfNames(typeinfo
, rgszNames
, cNames
, rgDispId
);
493 ITypeInfo_Release(typeinfo
);
500 static HRESULT WINAPI
domdoc_Invoke(
501 IXMLDOMDocument2
*iface
,
506 DISPPARAMS
* pDispParams
,
508 EXCEPINFO
* pExcepInfo
,
511 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
515 TRACE("(%p)->(%d %s %d %d %p %p %p %p)\n", This
, dispIdMember
, debugstr_guid(riid
),
516 lcid
, wFlags
, pDispParams
, pVarResult
, pExcepInfo
, puArgErr
);
518 hr
= get_typeinfo(IXMLDOMDocument2_tid
, &typeinfo
);
521 hr
= ITypeInfo_Invoke(typeinfo
, &(This
->lpVtbl
), dispIdMember
, wFlags
, pDispParams
,
522 pVarResult
, pExcepInfo
, puArgErr
);
523 ITypeInfo_Release(typeinfo
);
530 static HRESULT WINAPI
domdoc_get_nodeName(
531 IXMLDOMDocument2
*iface
,
534 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
535 return IXMLDOMNode_get_nodeName( This
->node
, name
);
539 static HRESULT WINAPI
domdoc_get_nodeValue(
540 IXMLDOMDocument2
*iface
,
543 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
544 return IXMLDOMNode_get_nodeValue( This
->node
, value
);
548 static HRESULT WINAPI
domdoc_put_nodeValue(
549 IXMLDOMDocument2
*iface
,
552 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
553 return IXMLDOMNode_put_nodeValue( This
->node
, value
);
557 static HRESULT WINAPI
domdoc_get_nodeType(
558 IXMLDOMDocument2
*iface
,
561 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
562 return IXMLDOMNode_get_nodeType( This
->node
, type
);
566 static HRESULT WINAPI
domdoc_get_parentNode(
567 IXMLDOMDocument2
*iface
,
568 IXMLDOMNode
** parent
)
570 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
571 return IXMLDOMNode_get_parentNode( This
->node
, parent
);
575 static HRESULT WINAPI
domdoc_get_childNodes(
576 IXMLDOMDocument2
*iface
,
577 IXMLDOMNodeList
** childList
)
579 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
580 return IXMLDOMNode_get_childNodes( This
->node
, childList
);
584 static HRESULT WINAPI
domdoc_get_firstChild(
585 IXMLDOMDocument2
*iface
,
586 IXMLDOMNode
** firstChild
)
588 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
589 return IXMLDOMNode_get_firstChild( This
->node
, firstChild
);
593 static HRESULT WINAPI
domdoc_get_lastChild(
594 IXMLDOMDocument2
*iface
,
595 IXMLDOMNode
** lastChild
)
597 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
598 return IXMLDOMNode_get_lastChild( This
->node
, lastChild
);
602 static HRESULT WINAPI
domdoc_get_previousSibling(
603 IXMLDOMDocument2
*iface
,
604 IXMLDOMNode
** previousSibling
)
606 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
607 return IXMLDOMNode_get_previousSibling( This
->node
, previousSibling
);
611 static HRESULT WINAPI
domdoc_get_nextSibling(
612 IXMLDOMDocument2
*iface
,
613 IXMLDOMNode
** nextSibling
)
615 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
616 return IXMLDOMNode_get_nextSibling( This
->node
, nextSibling
);
620 static HRESULT WINAPI
domdoc_get_attributes(
621 IXMLDOMDocument2
*iface
,
622 IXMLDOMNamedNodeMap
** attributeMap
)
624 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
625 return IXMLDOMNode_get_attributes( This
->node
, attributeMap
);
629 static HRESULT WINAPI
domdoc_insertBefore(
630 IXMLDOMDocument2
*iface
,
631 IXMLDOMNode
* newChild
,
633 IXMLDOMNode
** outNewChild
)
635 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
636 return IXMLDOMNode_insertBefore( This
->node
, newChild
, refChild
, outNewChild
);
640 static HRESULT WINAPI
domdoc_replaceChild(
641 IXMLDOMDocument2
*iface
,
642 IXMLDOMNode
* newChild
,
643 IXMLDOMNode
* oldChild
,
644 IXMLDOMNode
** outOldChild
)
646 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
647 return IXMLDOMNode_replaceChild( This
->node
, newChild
, oldChild
, outOldChild
);
651 static HRESULT WINAPI
domdoc_removeChild(
652 IXMLDOMDocument2
*iface
,
653 IXMLDOMNode
* childNode
,
654 IXMLDOMNode
** oldChild
)
656 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
657 return IXMLDOMNode_removeChild( This
->node
, childNode
, oldChild
);
661 static HRESULT WINAPI
domdoc_appendChild(
662 IXMLDOMDocument2
*iface
,
663 IXMLDOMNode
* newChild
,
664 IXMLDOMNode
** outNewChild
)
666 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
667 return IXMLDOMNode_appendChild( This
->node
, newChild
, outNewChild
);
671 static HRESULT WINAPI
domdoc_hasChildNodes(
672 IXMLDOMDocument2
*iface
,
673 VARIANT_BOOL
* hasChild
)
675 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
676 return IXMLDOMNode_hasChildNodes( This
->node
, hasChild
);
680 static HRESULT WINAPI
domdoc_get_ownerDocument(
681 IXMLDOMDocument2
*iface
,
682 IXMLDOMDocument
** DOMDocument
)
684 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
685 return IXMLDOMNode_get_ownerDocument( This
->node
, DOMDocument
);
689 static HRESULT WINAPI
domdoc_cloneNode(
690 IXMLDOMDocument2
*iface
,
692 IXMLDOMNode
** cloneRoot
)
694 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
695 return IXMLDOMNode_cloneNode( This
->node
, deep
, cloneRoot
);
699 static HRESULT WINAPI
domdoc_get_nodeTypeString(
700 IXMLDOMDocument2
*iface
,
703 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
704 return IXMLDOMNode_get_nodeTypeString( This
->node
, nodeType
);
708 static HRESULT WINAPI
domdoc_get_text(
709 IXMLDOMDocument2
*iface
,
712 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
713 return IXMLDOMNode_get_text( This
->node
, text
);
717 static HRESULT WINAPI
domdoc_put_text(
718 IXMLDOMDocument2
*iface
,
721 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
722 return IXMLDOMNode_put_text( This
->node
, text
);
726 static HRESULT WINAPI
domdoc_get_specified(
727 IXMLDOMDocument2
*iface
,
728 VARIANT_BOOL
* isSpecified
)
730 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
731 return IXMLDOMNode_get_specified( This
->node
, isSpecified
);
735 static HRESULT WINAPI
domdoc_get_definition(
736 IXMLDOMDocument2
*iface
,
737 IXMLDOMNode
** definitionNode
)
739 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
740 return IXMLDOMNode_get_definition( This
->node
, definitionNode
);
744 static HRESULT WINAPI
domdoc_get_nodeTypedValue(
745 IXMLDOMDocument2
*iface
,
746 VARIANT
* typedValue
)
748 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
749 return IXMLDOMNode_get_nodeTypedValue( This
->node
, typedValue
);
752 static HRESULT WINAPI
domdoc_put_nodeTypedValue(
753 IXMLDOMDocument2
*iface
,
756 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
757 return IXMLDOMNode_put_nodeTypedValue( This
->node
, typedValue
);
761 static HRESULT WINAPI
domdoc_get_dataType(
762 IXMLDOMDocument2
*iface
,
763 VARIANT
* dataTypeName
)
765 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
766 return IXMLDOMNode_get_dataType( This
->node
, dataTypeName
);
770 static HRESULT WINAPI
domdoc_put_dataType(
771 IXMLDOMDocument2
*iface
,
774 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
775 return IXMLDOMNode_put_dataType( This
->node
, dataTypeName
);
779 static HRESULT WINAPI
domdoc_get_xml(
780 IXMLDOMDocument2
*iface
,
783 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
784 return IXMLDOMNode_get_xml( This
->node
, xmlString
);
788 static HRESULT WINAPI
domdoc_transformNode(
789 IXMLDOMDocument2
*iface
,
790 IXMLDOMNode
* styleSheet
,
793 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
794 return IXMLDOMNode_transformNode( This
->node
, styleSheet
, xmlString
);
798 static HRESULT WINAPI
domdoc_selectNodes(
799 IXMLDOMDocument2
*iface
,
801 IXMLDOMNodeList
** resultList
)
803 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
804 return IXMLDOMNode_selectNodes( This
->node
, queryString
, resultList
);
808 static HRESULT WINAPI
domdoc_selectSingleNode(
809 IXMLDOMDocument2
*iface
,
811 IXMLDOMNode
** resultNode
)
813 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
814 return IXMLDOMNode_selectSingleNode( This
->node
, queryString
, resultNode
);
818 static HRESULT WINAPI
domdoc_get_parsed(
819 IXMLDOMDocument2
*iface
,
820 VARIANT_BOOL
* isParsed
)
822 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
823 return IXMLDOMNode_get_parsed( This
->node
, isParsed
);
827 static HRESULT WINAPI
domdoc_get_namespaceURI(
828 IXMLDOMDocument2
*iface
,
831 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
832 return IXMLDOMNode_get_namespaceURI( This
->node
, namespaceURI
);
836 static HRESULT WINAPI
domdoc_get_prefix(
837 IXMLDOMDocument2
*iface
,
840 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
841 return IXMLDOMNode_get_prefix( This
->node
, prefixString
);
845 static HRESULT WINAPI
domdoc_get_baseName(
846 IXMLDOMDocument2
*iface
,
849 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
850 return IXMLDOMNode_get_baseName( This
->node
, nameString
);
854 static HRESULT WINAPI
domdoc_transformNodeToObject(
855 IXMLDOMDocument2
*iface
,
856 IXMLDOMNode
* stylesheet
,
857 VARIANT outputObject
)
859 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
860 return IXMLDOMNode_transformNodeToObject( This
->node
, stylesheet
, outputObject
);
864 static HRESULT WINAPI
domdoc_get_doctype(
865 IXMLDOMDocument2
*iface
,
866 IXMLDOMDocumentType
** documentType
)
873 static HRESULT WINAPI
domdoc_get_implementation(
874 IXMLDOMDocument2
*iface
,
875 IXMLDOMImplementation
** impl
)
880 *impl
= (IXMLDOMImplementation
*)create_doc_Implementation();
885 static HRESULT WINAPI
domdoc_get_documentElement(
886 IXMLDOMDocument2
*iface
,
887 IXMLDOMElement
** DOMElement
)
889 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
890 xmlDocPtr xmldoc
= NULL
;
891 xmlNodePtr root
= NULL
;
892 IXMLDOMNode
*element_node
;
895 TRACE("%p %p\n", This
, This
->node
);
902 xmldoc
= get_doc( This
);
904 root
= xmlDocGetRootElement( xmldoc
);
908 element_node
= create_node( root
);
909 if(!element_node
) return S_FALSE
;
911 hr
= IXMLDOMNode_QueryInterface(element_node
, &IID_IXMLDOMElement
, (LPVOID
*)DOMElement
);
912 IXMLDOMNode_Release(element_node
);
918 static HRESULT WINAPI
domdoc_put_documentElement(
919 IXMLDOMDocument2
*iface
,
920 IXMLDOMElement
* DOMElement
)
922 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
923 IXMLDOMNode
*elementNode
;
927 TRACE("(%p)->(%p)\n", This
, DOMElement
);
929 hr
= IXMLDOMElement_QueryInterface( DOMElement
, &IID_IXMLDOMNode
, (void**)&elementNode
);
933 xmlNode
= impl_from_IXMLDOMNode( elementNode
);
934 xmlDocSetRootElement( get_doc(This
), xmlNode
->node
);
935 IXMLDOMNode_Release( elementNode
);
941 static HRESULT WINAPI
domdoc_createElement(
942 IXMLDOMDocument2
*iface
,
944 IXMLDOMElement
** element
)
947 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
952 TRACE("%p->(%s,%p)\n", iface
, debugstr_w(tagname
), element
);
954 xml_name
= xmlChar_from_wchar((WCHAR
*)tagname
);
955 xmlnode
= xmlNewDocNode(get_doc(This
), NULL
, xml_name
, NULL
);
956 xmldoc_add_orphan(xmlnode
->doc
, xmlnode
);
958 TRACE("created xmlptr %p\n", xmlnode
);
959 elem_unk
= create_element(xmlnode
, NULL
);
960 HeapFree(GetProcessHeap(), 0, xml_name
);
962 hr
= IUnknown_QueryInterface(elem_unk
, &IID_IXMLDOMElement
, (void **)element
);
963 IUnknown_Release(elem_unk
);
964 TRACE("returning %p\n", *element
);
969 static HRESULT WINAPI
domdoc_createDocumentFragment(
970 IXMLDOMDocument2
*iface
,
971 IXMLDOMDocumentFragment
** docFrag
)
973 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
976 TRACE("%p\n", iface
);
983 xmlnode
= xmlNewDocFragment(get_doc( This
) );
988 xmldoc_add_orphan(xmlnode
->doc
, xmlnode
);
989 *docFrag
= (IXMLDOMDocumentFragment
*)create_doc_fragment(xmlnode
);
995 static HRESULT WINAPI
domdoc_createTextNode(
996 IXMLDOMDocument2
*iface
,
1000 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
1002 xmlChar
*xml_content
;
1004 TRACE("%p->(%s %p)\n", iface
, debugstr_w(data
), text
);
1007 return E_INVALIDARG
;
1011 xml_content
= xmlChar_from_wchar((WCHAR
*)data
);
1012 xmlnode
= xmlNewText(xml_content
);
1013 HeapFree(GetProcessHeap(), 0, xml_content
);
1018 xmlnode
->doc
= get_doc( This
);
1019 xmldoc_add_orphan(xmlnode
->doc
, xmlnode
);
1021 *text
= (IXMLDOMText
*)create_text(xmlnode
);
1027 static HRESULT WINAPI
domdoc_createComment(
1028 IXMLDOMDocument2
*iface
,
1030 IXMLDOMComment
** comment
)
1032 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
1034 xmlChar
*xml_content
;
1036 TRACE("%p->(%s %p)\n", iface
, debugstr_w(data
), comment
);
1039 return E_INVALIDARG
;
1043 xml_content
= xmlChar_from_wchar((WCHAR
*)data
);
1044 xmlnode
= xmlNewComment(xml_content
);
1045 HeapFree(GetProcessHeap(), 0, xml_content
);
1050 xmlnode
->doc
= get_doc( This
);
1051 xmldoc_add_orphan(xmlnode
->doc
, xmlnode
);
1053 *comment
= (IXMLDOMComment
*)create_comment(xmlnode
);
1059 static HRESULT WINAPI
domdoc_createCDATASection(
1060 IXMLDOMDocument2
*iface
,
1062 IXMLDOMCDATASection
** cdata
)
1064 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
1066 xmlChar
*xml_content
;
1068 TRACE("%p->(%s %p)\n", iface
, debugstr_w(data
), cdata
);
1071 return E_INVALIDARG
;
1075 xml_content
= xmlChar_from_wchar((WCHAR
*)data
);
1076 xmlnode
= xmlNewCDataBlock(get_doc( This
), xml_content
, strlen( (char*)xml_content
) );
1077 HeapFree(GetProcessHeap(), 0, xml_content
);
1082 xmlnode
->doc
= get_doc( This
);
1083 xmldoc_add_orphan(xmlnode
->doc
, xmlnode
);
1085 *cdata
= (IXMLDOMCDATASection
*)create_cdata(xmlnode
);
1091 static HRESULT WINAPI
domdoc_createProcessingInstruction(
1092 IXMLDOMDocument2
*iface
,
1095 IXMLDOMProcessingInstruction
** pi
)
1097 #ifdef HAVE_XMLNEWDOCPI
1099 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
1100 xmlChar
*xml_target
, *xml_content
;
1102 TRACE("%p->(%s %s %p)\n", iface
, debugstr_w(target
), debugstr_w(data
), pi
);
1105 return E_INVALIDARG
;
1107 if(!target
|| lstrlenW(target
) == 0)
1110 xml_target
= xmlChar_from_wchar((WCHAR
*)target
);
1111 xml_content
= xmlChar_from_wchar((WCHAR
*)data
);
1113 xmlnode
= xmlNewDocPI(get_doc(This
), xml_target
, xml_content
);
1114 xmldoc_add_orphan(xmlnode
->doc
, xmlnode
);
1115 TRACE("created xmlptr %p\n", xmlnode
);
1116 *pi
= (IXMLDOMProcessingInstruction
*)create_pi(xmlnode
);
1118 HeapFree(GetProcessHeap(), 0, xml_content
);
1119 HeapFree(GetProcessHeap(), 0, xml_target
);
1123 FIXME("Libxml 2.6.15 or greater required.\n");
1129 static HRESULT WINAPI
domdoc_createAttribute(
1130 IXMLDOMDocument2
*iface
,
1132 IXMLDOMAttribute
** attribute
)
1134 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
1138 TRACE("%p->(%s %p)\n", iface
, debugstr_w(name
), attribute
);
1141 return E_INVALIDARG
;
1145 xml_name
= xmlChar_from_wchar((WCHAR
*)name
);
1146 xmlnode
= (xmlNode
*)xmlNewProp(NULL
, xml_name
, NULL
);
1147 HeapFree(GetProcessHeap(), 0, xml_name
);
1152 xmlnode
->doc
= get_doc( This
);
1153 xmldoc_add_orphan(xmlnode
->doc
, xmlnode
);
1155 *attribute
= (IXMLDOMAttribute
*)create_attribute(xmlnode
);
1161 static HRESULT WINAPI
domdoc_createEntityReference(
1162 IXMLDOMDocument2
*iface
,
1164 IXMLDOMEntityReference
** entityRef
)
1166 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
1170 TRACE("%p\n", iface
);
1173 return E_INVALIDARG
;
1177 xml_name
= xmlChar_from_wchar((WCHAR
*)name
);
1178 xmlnode
= xmlNewReference(get_doc( This
), xml_name
);
1179 HeapFree(GetProcessHeap(), 0, xml_name
);
1184 xmlnode
->doc
= get_doc( This
);
1185 xmldoc_add_orphan(xmlnode
->doc
, xmlnode
);
1187 *entityRef
= (IXMLDOMEntityReference
*)create_doc_entity_ref(xmlnode
);
1193 static HRESULT WINAPI
domdoc_getElementsByTagName(
1194 IXMLDOMDocument2
*iface
,
1196 IXMLDOMNodeList
** resultList
)
1198 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
1201 TRACE("(%p)->(%s, %p)\n", This
, debugstr_w(tagName
), resultList
);
1203 szPattern
= HeapAlloc(GetProcessHeap(), 0, sizeof(WCHAR
)*(2+lstrlenW(tagName
)+1));
1204 szPattern
[0] = szPattern
[1] = '/';
1205 lstrcpyW(szPattern
+ 2, tagName
);
1207 hr
= queryresult_create((xmlNodePtr
)get_doc(This
), szPattern
, resultList
);
1208 HeapFree(GetProcessHeap(), 0, szPattern
);
1213 static HRESULT
get_node_type(VARIANT Type
, DOMNodeType
* type
)
1219 hr
= VariantChangeType(&tmp
, &Type
, 0, VT_I4
);
1221 return E_INVALIDARG
;
1228 static HRESULT WINAPI
domdoc_createNode(
1229 IXMLDOMDocument2
*iface
,
1233 IXMLDOMNode
** node
)
1235 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
1236 DOMNodeType node_type
;
1237 xmlNodePtr xmlnode
= NULL
;
1241 TRACE("(%p)->(type,%s,%s,%p)\n", This
, debugstr_w(name
), debugstr_w(namespaceURI
), node
);
1243 hr
= get_node_type(Type
, &node_type
);
1247 TRACE("node_type %d\n", node_type
);
1249 xml_name
= xmlChar_from_wchar((WCHAR
*)name
);
1254 xmlnode
= xmlNewDocNode(get_doc(This
), NULL
, xml_name
, NULL
);
1255 *node
= create_node(xmlnode
);
1256 TRACE("created %p\n", xmlnode
);
1258 case NODE_ATTRIBUTE
:
1259 xmlnode
= (xmlNode
*)xmlNewProp(NULL
, xml_name
, NULL
);
1262 xmlnode
->doc
= get_doc( This
);
1264 *node
= (IXMLDOMNode
*)create_attribute(xmlnode
);
1267 TRACE("created %p\n", xmlnode
);
1271 FIXME("unhandled node type %d\n", node_type
);
1275 HeapFree(GetProcessHeap(), 0, xml_name
);
1277 if(xmlnode
&& *node
)
1279 xmldoc_add_orphan(xmlnode
->doc
, xmlnode
);
1286 static HRESULT WINAPI
domdoc_nodeFromID(
1287 IXMLDOMDocument2
*iface
,
1289 IXMLDOMNode
** node
)
1295 static HRESULT
domdoc_onDataAvailable(void *obj
, char *ptr
, DWORD len
)
1300 xmldoc
= doparse( ptr
, len
);
1302 xmldoc
->_private
= create_priv();
1303 attach_xmlnode(This
->node
, (xmlNodePtr
) xmldoc
);
1309 static HRESULT
doread( domdoc
*This
, LPWSTR filename
)
1314 hr
= bind_url(filename
, domdoc_onDataAvailable
, This
, &bsc
);
1319 detach_bsc(This
->bsc
);
1325 static HRESULT WINAPI
domdoc_load(
1326 IXMLDOMDocument2
*iface
,
1328 VARIANT_BOOL
* isSuccessful
)
1330 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
1331 LPWSTR filename
= NULL
;
1332 HRESULT hr
= S_FALSE
;
1333 IXMLDOMDocument2
*pNewDoc
= NULL
;
1334 IStream
*pStream
= NULL
;
1337 TRACE("type %d\n", V_VT(&xmlSource
) );
1339 *isSuccessful
= VARIANT_FALSE
;
1341 assert( This
->node
);
1343 attach_xmlnode(This
->node
, NULL
);
1345 switch( V_VT(&xmlSource
) )
1348 filename
= V_BSTR(&xmlSource
);
1351 hr
= IUnknown_QueryInterface(V_UNKNOWN(&xmlSource
), &IID_IXMLDOMDocument2
, (void**)&pNewDoc
);
1356 domdoc
*newDoc
= impl_from_IXMLDOMDocument2( pNewDoc
);
1357 xmldoc
= xmlCopyDoc(get_doc(newDoc
), 1);
1358 attach_xmlnode(This
->node
, (xmlNodePtr
) xmldoc
);
1360 *isSuccessful
= VARIANT_TRUE
;
1365 hr
= IUnknown_QueryInterface(V_UNKNOWN(&xmlSource
), &IID_IStream
, (void**)&pStream
);
1368 IPersistStream
*pDocStream
;
1369 hr
= IUnknown_QueryInterface(iface
, &IID_IPersistStream
, (void**)&pDocStream
);
1372 hr
= xmldoc_IPersistStream_Load(pDocStream
, pStream
);
1373 IStream_Release(pStream
);
1376 *isSuccessful
= VARIANT_TRUE
;
1378 TRACE("Using ID_IStream to load Document\n");
1383 ERR("xmldoc_IPersistStream_Load failed (%d)\n", hr
);
1388 ERR("QueryInterface IID_IPersistStream failed (%d)\n", hr
);
1393 /* ISequentialStream */
1394 FIXME("Unknown type not supported (%d) (%p)(%p)\n", hr
, pNewDoc
, V_UNKNOWN(&xmlSource
)->lpVtbl
);
1398 FIXME("VT type not supported (%d)\n", V_VT(&xmlSource
));
1401 TRACE("filename (%s)\n", debugstr_w(filename
));
1405 hr
= doread( This
, filename
);
1408 This
->error
= E_FAIL
;
1411 hr
= This
->error
= S_OK
;
1412 *isSuccessful
= VARIANT_TRUE
;
1416 if(!filename
|| FAILED(hr
)) {
1417 xmldoc
= xmlNewDoc(NULL
);
1418 xmldoc
->_private
= create_priv();
1419 attach_xmlnode(This
->node
, (xmlNodePtr
) xmldoc
);
1423 TRACE("ret (%d)\n", hr
);
1429 static HRESULT WINAPI
domdoc_get_readyState(
1430 IXMLDOMDocument2
*iface
,
1438 static HRESULT WINAPI
domdoc_get_parseError(
1439 IXMLDOMDocument2
*iface
,
1440 IXMLDOMParseError
** errorObj
)
1442 BSTR error_string
= NULL
;
1443 static const WCHAR err
[] = {'e','r','r','o','r',0};
1444 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
1446 FIXME("(%p)->(%p): creating a dummy parseError\n", iface
, errorObj
);
1449 error_string
= SysAllocString(err
);
1451 *errorObj
= create_parseError(This
->error
, NULL
, error_string
, NULL
, 0, 0, 0);
1452 if(!*errorObj
) return E_OUTOFMEMORY
;
1457 static HRESULT WINAPI
domdoc_get_url(
1458 IXMLDOMDocument2
*iface
,
1466 static HRESULT WINAPI
domdoc_get_async(
1467 IXMLDOMDocument2
*iface
,
1468 VARIANT_BOOL
* isAsync
)
1470 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
1472 TRACE("%p <- %d\n", isAsync
, This
->async
);
1473 *isAsync
= This
->async
;
1478 static HRESULT WINAPI
domdoc_put_async(
1479 IXMLDOMDocument2
*iface
,
1480 VARIANT_BOOL isAsync
)
1482 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
1484 TRACE("%d\n", isAsync
);
1485 This
->async
= isAsync
;
1490 static HRESULT WINAPI
domdoc_abort(
1491 IXMLDOMDocument2
*iface
)
1498 static BOOL
bstr_to_utf8( BSTR bstr
, char **pstr
, int *plen
)
1500 UINT len
, blen
= SysStringLen( bstr
);
1503 len
= WideCharToMultiByte( CP_UTF8
, 0, bstr
, blen
, NULL
, 0, NULL
, NULL
);
1504 str
= HeapAlloc( GetProcessHeap(), 0, len
);
1507 WideCharToMultiByte( CP_UTF8
, 0, bstr
, blen
, str
, len
, NULL
, NULL
);
1513 static HRESULT WINAPI
domdoc_loadXML(
1514 IXMLDOMDocument2
*iface
,
1516 VARIANT_BOOL
* isSuccessful
)
1518 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
1519 xmlDocPtr xmldoc
= NULL
;
1522 HRESULT hr
= S_FALSE
;
1524 TRACE("%p %s %p\n", This
, debugstr_w( bstrXML
), isSuccessful
);
1526 assert ( This
->node
);
1528 attach_xmlnode( This
->node
, NULL
);
1532 *isSuccessful
= VARIANT_FALSE
;
1534 if ( bstrXML
&& bstr_to_utf8( bstrXML
, &str
, &len
) )
1536 xmldoc
= doparse( str
, len
);
1537 HeapFree( GetProcessHeap(), 0, str
);
1539 This
->error
= E_FAIL
;
1542 hr
= This
->error
= S_OK
;
1543 *isSuccessful
= VARIANT_TRUE
;
1548 xmldoc
= xmlNewDoc(NULL
);
1550 xmldoc
->_private
= create_priv();
1551 attach_xmlnode( This
->node
, (xmlNodePtr
) xmldoc
);
1557 static HRESULT WINAPI
domdoc_save(
1558 IXMLDOMDocument2
*iface
,
1559 VARIANT destination
)
1561 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
1568 TRACE("(%p)->(var(vt %d, %s))\n", This
, V_VT(&destination
),
1569 V_VT(&destination
) == VT_BSTR
? debugstr_w(V_BSTR(&destination
)) : NULL
);
1571 if(V_VT(&destination
) != VT_BSTR
&& V_VT(&destination
) != VT_UNKNOWN
)
1573 FIXME("Unhandled vt %d\n", V_VT(&destination
));
1577 if(V_VT(&destination
) == VT_UNKNOWN
)
1579 IUnknown
*pUnk
= V_UNKNOWN(&destination
);
1580 IXMLDOMDocument
*pDocument
;
1582 ret
= IXMLDOMDocument_QueryInterface(pUnk
, &IID_IXMLDOMDocument2
, (void**)&pDocument
);
1586 VARIANT_BOOL bSuccessful
;
1588 ret
= IXMLDOMDocument_get_xml(iface
, &bXML
);
1591 ret
= IXMLDOMDocument_loadXML(pDocument
, bXML
, &bSuccessful
);
1593 SysFreeString(bXML
);
1596 IXMLDOMDocument_Release(pDocument
);
1599 TRACE("ret %d\n", ret
);
1604 handle
= CreateFileW( V_BSTR(&destination
), GENERIC_WRITE
, 0,
1605 NULL
, CREATE_ALWAYS
, FILE_ATTRIBUTE_NORMAL
, NULL
);
1606 if( handle
== INVALID_HANDLE_VALUE
)
1608 WARN("failed to create file\n");
1612 xmlDocDumpMemory(get_doc(This
), &mem
, &size
);
1615 * libxml2 always adds XML declaration on top of the file and one for each processing instruction node in DOM tree.
1616 * MSXML adds XML declaration only for processing instruction nodes.
1617 * We skip the first XML declaration generated by libxml2 to get exactly what we need.
1620 if(size
> 2 && p
[0] == '<' && p
[1] == '?') {
1621 while(p
< mem
+size
&& (p
[0] != '?' || p
[1] != '>'))
1624 while(p
< mem
+size
&& isspace(*p
))
1629 if(!WriteFile(handle
, p
, (DWORD
)size
, &written
, NULL
) || written
!= (DWORD
)size
)
1631 WARN("write error\n");
1636 CloseHandle(handle
);
1640 static HRESULT WINAPI
domdoc_get_validateOnParse(
1641 IXMLDOMDocument2
*iface
,
1642 VARIANT_BOOL
* isValidating
)
1644 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
1646 TRACE("%p <- %d\n", isValidating
, This
->validating
);
1647 *isValidating
= This
->validating
;
1652 static HRESULT WINAPI
domdoc_put_validateOnParse(
1653 IXMLDOMDocument2
*iface
,
1654 VARIANT_BOOL isValidating
)
1656 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
1658 TRACE("%d\n", isValidating
);
1659 This
->validating
= isValidating
;
1664 static HRESULT WINAPI
domdoc_get_resolveExternals(
1665 IXMLDOMDocument2
*iface
,
1666 VARIANT_BOOL
* isResolving
)
1668 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
1670 TRACE("%p <- %d\n", isResolving
, This
->resolving
);
1671 *isResolving
= This
->resolving
;
1676 static HRESULT WINAPI
domdoc_put_resolveExternals(
1677 IXMLDOMDocument2
*iface
,
1678 VARIANT_BOOL isResolving
)
1680 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
1682 TRACE("%d\n", isResolving
);
1683 This
->resolving
= isResolving
;
1688 static HRESULT WINAPI
domdoc_get_preserveWhiteSpace(
1689 IXMLDOMDocument2
*iface
,
1690 VARIANT_BOOL
* isPreserving
)
1692 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
1694 TRACE("%p <- %d\n", isPreserving
, This
->preserving
);
1695 *isPreserving
= This
->preserving
;
1700 static HRESULT WINAPI
domdoc_put_preserveWhiteSpace(
1701 IXMLDOMDocument2
*iface
,
1702 VARIANT_BOOL isPreserving
)
1704 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
1706 TRACE("%d\n", isPreserving
);
1707 This
->preserving
= isPreserving
;
1712 static HRESULT WINAPI
domdoc_put_onReadyStateChange(
1713 IXMLDOMDocument2
*iface
,
1714 VARIANT readyStateChangeSink
)
1721 static HRESULT WINAPI
domdoc_put_onDataAvailable(
1722 IXMLDOMDocument2
*iface
,
1723 VARIANT onDataAvailableSink
)
1729 static HRESULT WINAPI
domdoc_put_onTransformNode(
1730 IXMLDOMDocument2
*iface
,
1731 VARIANT onTransformNodeSink
)
1737 static HRESULT WINAPI
domdoc_get_namespaces(
1738 IXMLDOMDocument2
* iface
,
1739 IXMLDOMSchemaCollection
** schemaCollection
)
1745 static HRESULT WINAPI
domdoc_get_schemas(
1746 IXMLDOMDocument2
* iface
,
1749 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
1750 HRESULT hr
= S_FALSE
;
1751 IXMLDOMSchemaCollection
*cur_schema
= This
->schema
;
1753 TRACE("(%p)->(%p)\n", This
, var1
);
1755 VariantInit(var1
); /* Test shows we don't call VariantClear here */
1756 V_VT(var1
) = VT_NULL
;
1760 hr
= IXMLDOMSchemaCollection_QueryInterface(cur_schema
, &IID_IDispatch
, (void**)&V_DISPATCH(var1
));
1762 V_VT(var1
) = VT_DISPATCH
;
1767 static HRESULT WINAPI
domdoc_putref_schemas(
1768 IXMLDOMDocument2
* iface
,
1771 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
1772 HRESULT hr
= E_FAIL
;
1773 IXMLDOMSchemaCollection
*new_schema
= NULL
;
1775 FIXME("(%p): semi-stub\n", This
);
1779 hr
= IUnknown_QueryInterface(V_UNKNOWN(&var1
), &IID_IXMLDOMSchemaCollection
, (void**)&new_schema
);
1783 hr
= IDispatch_QueryInterface(V_DISPATCH(&var1
), &IID_IXMLDOMSchemaCollection
, (void**)&new_schema
);
1792 WARN("Can't get schema from vt %x\n", V_VT(&var1
));
1797 IXMLDOMSchemaCollection
*old_schema
= InterlockedExchangePointer((void**)&This
->schema
, new_schema
);
1798 if(old_schema
) IXMLDOMSchemaCollection_Release(old_schema
);
1804 static HRESULT WINAPI
domdoc_validate(
1805 IXMLDOMDocument2
* iface
,
1806 IXMLDOMParseError
** err
)
1812 static HRESULT WINAPI
domdoc_setProperty(
1813 IXMLDOMDocument2
* iface
,
1817 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
1819 if (lstrcmpiW(p
, SZ_PROPERTY_SELECTION_LANGUAGE
) == 0)
1825 V_VT(&varStr
) = VT_EMPTY
;
1826 if (V_VT(&var
) != VT_BSTR
)
1828 if (FAILED(hr
= VariantChangeType(&varStr
, &var
, 0, VT_BSTR
)))
1830 bstr
= V_BSTR(&varStr
);
1833 bstr
= V_BSTR(&var
);
1836 if (lstrcmpiW(bstr
, SZ_VALUE_XPATH
) == 0)
1837 This
->bUseXPath
= TRUE
;
1838 else if (lstrcmpiW(bstr
, SZ_VALUE_XSLPATTERN
) == 0)
1839 This
->bUseXPath
= FALSE
;
1843 VariantClear(&varStr
);
1847 FIXME("Unknown property %s\n", wine_dbgstr_w(p
));
1851 static HRESULT WINAPI
domdoc_getProperty(
1852 IXMLDOMDocument2
* iface
,
1856 domdoc
*This
= impl_from_IXMLDOMDocument2( iface
);
1859 return E_INVALIDARG
;
1860 if (lstrcmpiW(p
, SZ_PROPERTY_SELECTION_LANGUAGE
) == 0)
1862 V_VT(var
) = VT_BSTR
;
1863 if (This
->bUseXPath
)
1864 V_BSTR(var
) = SysAllocString(SZ_VALUE_XPATH
);
1866 V_BSTR(var
) = SysAllocString(SZ_VALUE_XSLPATTERN
);
1870 FIXME("Unknown property %s\n", wine_dbgstr_w(p
));
1874 static const struct IXMLDOMDocument2Vtbl domdoc_vtbl
=
1876 domdoc_QueryInterface
,
1879 domdoc_GetTypeInfoCount
,
1881 domdoc_GetIDsOfNames
,
1883 domdoc_get_nodeName
,
1884 domdoc_get_nodeValue
,
1885 domdoc_put_nodeValue
,
1886 domdoc_get_nodeType
,
1887 domdoc_get_parentNode
,
1888 domdoc_get_childNodes
,
1889 domdoc_get_firstChild
,
1890 domdoc_get_lastChild
,
1891 domdoc_get_previousSibling
,
1892 domdoc_get_nextSibling
,
1893 domdoc_get_attributes
,
1894 domdoc_insertBefore
,
1895 domdoc_replaceChild
,
1898 domdoc_hasChildNodes
,
1899 domdoc_get_ownerDocument
,
1901 domdoc_get_nodeTypeString
,
1904 domdoc_get_specified
,
1905 domdoc_get_definition
,
1906 domdoc_get_nodeTypedValue
,
1907 domdoc_put_nodeTypedValue
,
1908 domdoc_get_dataType
,
1909 domdoc_put_dataType
,
1911 domdoc_transformNode
,
1913 domdoc_selectSingleNode
,
1915 domdoc_get_namespaceURI
,
1917 domdoc_get_baseName
,
1918 domdoc_transformNodeToObject
,
1920 domdoc_get_implementation
,
1921 domdoc_get_documentElement
,
1922 domdoc_put_documentElement
,
1923 domdoc_createElement
,
1924 domdoc_createDocumentFragment
,
1925 domdoc_createTextNode
,
1926 domdoc_createComment
,
1927 domdoc_createCDATASection
,
1928 domdoc_createProcessingInstruction
,
1929 domdoc_createAttribute
,
1930 domdoc_createEntityReference
,
1931 domdoc_getElementsByTagName
,
1935 domdoc_get_readyState
,
1936 domdoc_get_parseError
,
1943 domdoc_get_validateOnParse
,
1944 domdoc_put_validateOnParse
,
1945 domdoc_get_resolveExternals
,
1946 domdoc_put_resolveExternals
,
1947 domdoc_get_preserveWhiteSpace
,
1948 domdoc_put_preserveWhiteSpace
,
1949 domdoc_put_onReadyStateChange
,
1950 domdoc_put_onDataAvailable
,
1951 domdoc_put_onTransformNode
,
1952 domdoc_get_namespaces
,
1954 domdoc_putref_schemas
,
1960 /* xmldoc implementation of IObjectWithSite */
1961 static HRESULT WINAPI
1962 xmldoc_ObjectWithSite_QueryInterface( IObjectWithSite
* iface
, REFIID riid
, void** ppvObject
)
1964 domdoc
*This
= impl_from_IObjectWithSite(iface
);
1965 return IXMLDocument_QueryInterface( (IXMLDocument
*)This
, riid
, ppvObject
);
1969 xmldoc_ObjectWithSite_AddRef( IObjectWithSite
* iface
)
1971 domdoc
*This
= impl_from_IObjectWithSite(iface
);
1972 return IXMLDocument_AddRef((IXMLDocument
*)This
);
1976 xmldoc_ObjectWithSite_Release( IObjectWithSite
* iface
)
1978 domdoc
*This
= impl_from_IObjectWithSite(iface
);
1979 return IXMLDocument_Release((IXMLDocument
*)This
);
1982 static HRESULT WINAPI
1983 xmldoc_GetSite( IObjectWithSite
*iface
, REFIID iid
, void ** ppvSite
)
1985 domdoc
*This
= impl_from_IObjectWithSite(iface
);
1987 TRACE("%p %s %p\n", This
, debugstr_guid( iid
), ppvSite
);
1992 return IUnknown_QueryInterface( This
->site
, iid
, ppvSite
);
1995 static HRESULT WINAPI
1996 xmldoc_SetSite( IObjectWithSite
*iface
, IUnknown
*punk
)
1998 domdoc
*This
= impl_from_IObjectWithSite(iface
);
2000 TRACE("%p %p\n", iface
, punk
);
2006 IUnknown_Release( This
->site
);
2014 IUnknown_AddRef( punk
);
2017 IUnknown_Release( This
->site
);
2024 static const IObjectWithSiteVtbl domdocObjectSite
=
2026 xmldoc_ObjectWithSite_QueryInterface
,
2027 xmldoc_ObjectWithSite_AddRef
,
2028 xmldoc_ObjectWithSite_Release
,
2033 static HRESULT WINAPI
xmldoc_Safety_QueryInterface(IObjectSafety
*iface
, REFIID riid
, void **ppv
)
2035 domdoc
*This
= impl_from_IObjectSafety(iface
);
2036 return IXMLDocument_QueryInterface( (IXMLDocument
*)This
, riid
, ppv
);
2039 static ULONG WINAPI
xmldoc_Safety_AddRef(IObjectSafety
*iface
)
2041 domdoc
*This
= impl_from_IObjectSafety(iface
);
2042 return IXMLDocument_AddRef((IXMLDocument
*)This
);
2045 static ULONG WINAPI
xmldoc_Safety_Release(IObjectSafety
*iface
)
2047 domdoc
*This
= impl_from_IObjectSafety(iface
);
2048 return IXMLDocument_Release((IXMLDocument
*)This
);
2051 #define SUPPORTED_OPTIONS (INTERFACESAFE_FOR_UNTRUSTED_CALLER|INTERFACESAFE_FOR_UNTRUSTED_DATA|INTERFACE_USES_SECURITY_MANAGER)
2053 static HRESULT WINAPI
xmldoc_Safety_GetInterfaceSafetyOptions(IObjectSafety
*iface
, REFIID riid
,
2054 DWORD
*pdwSupportedOptions
, DWORD
*pdwEnabledOptions
)
2056 domdoc
*This
= impl_from_IObjectSafety(iface
);
2058 TRACE("(%p)->(%s %p %p)\n", This
, debugstr_guid(riid
), pdwSupportedOptions
, pdwEnabledOptions
);
2060 if(!pdwSupportedOptions
|| !pdwEnabledOptions
)
2063 *pdwSupportedOptions
= SUPPORTED_OPTIONS
;
2064 *pdwEnabledOptions
= This
->safeopt
;
2069 static HRESULT WINAPI
xmldoc_Safety_SetInterfaceSafetyOptions(IObjectSafety
*iface
, REFIID riid
,
2070 DWORD dwOptionSetMask
, DWORD dwEnabledOptions
)
2072 domdoc
*This
= impl_from_IObjectSafety(iface
);
2074 TRACE("(%p)->(%s %x %x)\n", This
, debugstr_guid(riid
), dwOptionSetMask
, dwEnabledOptions
);
2076 if(dwOptionSetMask
& ~SUPPORTED_OPTIONS
)
2079 This
->safeopt
= dwEnabledOptions
& dwEnabledOptions
;
2083 static const IObjectSafetyVtbl domdocObjectSafetyVtbl
= {
2084 xmldoc_Safety_QueryInterface
,
2085 xmldoc_Safety_AddRef
,
2086 xmldoc_Safety_Release
,
2087 xmldoc_Safety_GetInterfaceSafetyOptions
,
2088 xmldoc_Safety_SetInterfaceSafetyOptions
2092 static const tid_t domdoc_iface_tids
[] = {
2094 IXMLDOMDocument_tid
,
2095 IXMLDOMDocument2_tid
,
2098 static dispex_static_data_t domdoc_dispex
= {
2100 IXMLDOMDocument2_tid
,
2105 HRESULT
DOMDocument_create_from_xmldoc(xmlDocPtr xmldoc
, IXMLDOMDocument2
**document
)
2110 doc
= HeapAlloc( GetProcessHeap(), 0, sizeof (*doc
) );
2112 return E_OUTOFMEMORY
;
2114 doc
->lpVtbl
= &domdoc_vtbl
;
2115 doc
->lpvtblIPersistStream
= &xmldoc_IPersistStream_VTable
;
2116 doc
->lpvtblIObjectWithSite
= &domdocObjectSite
;
2117 doc
->lpvtblIObjectSafety
= &domdocObjectSafetyVtbl
;
2120 doc
->validating
= 0;
2122 doc
->preserving
= 0;
2123 doc
->bUseXPath
= FALSE
;
2131 doc
->node_unk
= create_basic_node( (xmlNodePtr
)xmldoc
, (IUnknown
*)&doc
->lpVtbl
);
2134 HeapFree(GetProcessHeap(), 0, doc
);
2138 hr
= IUnknown_QueryInterface(doc
->node_unk
, &IID_IXMLDOMNode
, (LPVOID
*)&doc
->node
);
2141 IUnknown_Release(doc
->node_unk
);
2142 HeapFree( GetProcessHeap(), 0, doc
);
2146 init_dispex(&doc
->dispex
, (IUnknown
*)&doc
->lpVtbl
, &domdoc_dispex
);
2148 /* The ref on doc->node is actually looped back into this object, so release it */
2149 IXMLDOMNode_Release(doc
->node
);
2151 *document
= (IXMLDOMDocument2
*)&doc
->lpVtbl
;
2153 TRACE("returning iface %p\n", *document
);
2157 HRESULT
DOMDocument_create(IUnknown
*pUnkOuter
, LPVOID
*ppObj
)
2162 TRACE("(%p,%p)\n", pUnkOuter
, ppObj
);
2164 xmldoc
= xmlNewDoc(NULL
);
2166 return E_OUTOFMEMORY
;
2168 xmldoc
->_private
= create_priv();
2170 hr
= DOMDocument_create_from_xmldoc(xmldoc
, (IXMLDOMDocument2
**)ppObj
);
2177 IUnknown
* create_domdoc( xmlNodePtr document
)
2182 TRACE("(%p)\n", document
);
2184 hr
= DOMDocument_create_from_xmldoc((xmlDocPtr
)document
, (IXMLDOMDocument2
**)&pObj
);
2188 return (IUnknown
*)pObj
;
2193 HRESULT
DOMDocument_create(IUnknown
*pUnkOuter
, LPVOID
*ppObj
)
2195 MESSAGE("This program tried to use a DOMDocument object, but\n"
2196 "libxml2 support was not present at compile time.\n");