2 * SAX Reader implementation
4 * Copyright 2008 Alistair Leslie-Hughes
5 * Copyright 2008 Piotr Caban
7 * This library is free software; you can redistribute it and/or
8 * modify it under the terms of the GNU Lesser General Public
9 * License as published by the Free Software Foundation; either
10 * version 2.1 of the License, or (at your option) any later version.
12 * This library is distributed in the hope that it will be useful,
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
15 * Lesser General Public License for more details.
17 * You should have received a copy of the GNU Lesser General Public
18 * License along with this library; if not, write to the Free Software
19 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
27 # include <libxml/parser.h>
28 # include <libxml/xmlerror.h>
29 # include <libxml/SAX2.h>
30 # include <libxml/parserInternals.h>
44 #include "wine/debug.h"
45 #include "wine/list.h"
47 #include "msxml_private.h"
49 WINE_DEFAULT_DEBUG_CHANNEL(msxml);
56 ExhaustiveErrors = 1 << 1,
57 ExternalGeneralEntities = 1 << 2,
58 ExternalParameterEntities = 1 << 3,
59 ForcedResync = 1 << 4,
60 NamespacePrefixes = 1 << 5,
62 ParameterEntities = 1 << 7,
63 PreserveSystemIndentifiers = 1 << 8,
65 SchemaValidation = 1 << 10,
66 ServerHttpRequest = 1 << 11,
67 SuppressValidationfatalError = 1 << 12,
68 UseInlineSchema = 1 << 13,
69 UseSchemaLocation = 1 << 14,
70 LexicalHandlerParEntities = 1 << 15
74 static const WCHAR FeatureExternalGeneralEntitiesW[] = {
75 'h','t','t','p',':','/','/','x','m','l','.','o','r','g','/','s','a','x','/',
76 'f','e','a','t','u','r','e','s','/','e','x','t','e','r','n','a','l','-','g','e','n','e','r','a','l',
77 '-','e','n','t','i','t','i','e','s',0
80 static const WCHAR FeatureExternalParameterEntitiesW[] = {
81 'h','t','t','p',':','/','/','x','m','l','.','o','r','g','/','s','a','x','/','f','e','a','t','u','r','e','s',
82 '/','e','x','t','e','r','n','a','l','-','p','a','r','a','m','e','t','e','r','-','e','n','t','i','t','i','e','s',0
85 static const WCHAR FeatureLexicalHandlerParEntitiesW[] = {
86 'h','t','t','p',':','/','/','x','m','l','.','o','r','g','/','s','a','x','/','f','e','a','t','u','r','e','s',
87 '/','l','e','x','i','c','a','l','-','h','a','n','d','l','e','r','/','p','a','r','a','m','e','t','e','r','-','e','n','t','i','t','i','e','s',0
90 static const WCHAR FeatureProhibitDTDW[] = {
91 'p','r','o','h','i','b','i','t','-','d','t','d',0
94 static const WCHAR FeatureNamespacesW[] = {
95 'h','t','t','p',':','/','/','x','m','l','.','o','r','g','/','s','a','x','/','f','e','a','t','u','r','e','s',
96 '/','n','a','m','e','s','p','a','c','e','s',0
99 static const WCHAR FeatureNamespacePrefixesW[] = {
100 'h','t','t','p',':','/','/','x','m','l','.','o','r','g','/','s','a','x','/','f','e','a','t','u','r','e','s',
101 '/','n','a','m','e','s','p','a','c','e','-','p','r','e','f','i','x','e','s',0
104 struct saxreader_feature_pair
106 saxreader_feature feature;
110 static const struct saxreader_feature_pair saxreader_feature_map[] = {
111 { ExternalGeneralEntities, FeatureExternalGeneralEntitiesW },
112 { ExternalParameterEntities, FeatureExternalParameterEntitiesW },
113 { LexicalHandlerParEntities, FeatureLexicalHandlerParEntitiesW },
114 { NamespacePrefixes, FeatureNamespacePrefixesW },
115 { Namespaces, FeatureNamespacesW },
116 { ProhibitDTD, FeatureProhibitDTDW }
119 static saxreader_feature get_saxreader_feature(const WCHAR *name)
124 max = sizeof(saxreader_feature_map)/sizeof(struct saxreader_feature_pair) - 1;
130 c = strcmpW(saxreader_feature_map[n].name, name);
132 return saxreader_feature_map[n].feature;
140 return FeatureUnknown;
162 ns *ns; /* namespaces defined in this particular element */
169 IVBSAXXMLReader IVBSAXXMLReader_iface;
170 ISAXXMLReader ISAXXMLReader_iface;
172 ISAXContentHandler *contentHandler;
173 IVBSAXContentHandler *vbcontentHandler;
174 ISAXErrorHandler *errorHandler;
175 IVBSAXErrorHandler *vberrorHandler;
176 ISAXLexicalHandler *lexicalHandler;
177 IVBSAXLexicalHandler *vblexicalHandler;
178 ISAXDeclHandler *declHandler;
179 IVBSAXDeclHandler *vbdeclHandler;
182 struct bstrpool pool;
183 saxreader_feature features;
184 MSXML_VERSION version;
189 IVBSAXLocator IVBSAXLocator_iface;
190 ISAXLocator ISAXLocator_iface;
191 IVBSAXAttributes IVBSAXAttributes_iface;
192 ISAXAttributes ISAXAttributes_iface;
194 saxreader *saxreader;
196 xmlParserCtxtPtr pParserCtxt;
202 struct list elements;
206 IMXAttributes *attributes;
207 ISAXAttributes *saxattr;
208 IVBSAXAttributes *vbsaxattr;
211 static inline saxreader *impl_from_IVBSAXXMLReader( IVBSAXXMLReader *iface )
213 return CONTAINING_RECORD(iface, saxreader, IVBSAXXMLReader_iface);
216 static inline saxreader *impl_from_ISAXXMLReader( ISAXXMLReader *iface )
218 return CONTAINING_RECORD(iface, saxreader, ISAXXMLReader_iface);
221 static inline saxlocator *impl_from_IVBSAXLocator( IVBSAXLocator *iface )
223 return CONTAINING_RECORD(iface, saxlocator, IVBSAXLocator_iface);
226 static inline saxlocator *impl_from_ISAXLocator( ISAXLocator *iface )
228 return CONTAINING_RECORD(iface, saxlocator, ISAXLocator_iface);
231 static inline saxlocator *impl_from_IVBSAXAttributes( IVBSAXAttributes *iface )
233 return CONTAINING_RECORD(iface, saxlocator, IVBSAXAttributes_iface);
236 static inline saxlocator *impl_from_ISAXAttributes( ISAXAttributes *iface )
238 return CONTAINING_RECORD(iface, saxlocator, ISAXAttributes_iface);
242 static const WCHAR PropertyCharsetW[] = {
243 'c','h','a','r','s','e','t',0
245 static const WCHAR PropertyDeclHandlerW[] = {
246 'h','t','t','p',':','/','/','x','m','l','.','o','r','g','/',
247 's','a','x','/','p','r','o','p','e','r','t','i','e','s','/',
248 'd','e','c','l','a','r','a','t','i','o','n',
249 '-','h','a','n','d','l','e','r',0
251 static const WCHAR PropertyDomNodeW[] = {
252 'h','t','t','p',':','/','/','x','m','l','.','o','r','g','/',
253 's','a','x','/','p','r','o','p','e','r','t','i','e','s','/',
254 'd','o','m','-','n','o','d','e',0
256 static const WCHAR PropertyInputSourceW[] = {
257 'i','n','p','u','t','-','s','o','u','r','c','e',0
259 static const WCHAR PropertyLexicalHandlerW[] = {
260 'h','t','t','p',':','/','/','x','m','l','.','o','r','g','/',
261 's','a','x','/','p','r','o','p','e','r','t','i','e','s','/',
262 'l','e','x','i','c','a','l','-','h','a','n','d','l','e','r',0
264 static const WCHAR PropertyMaxElementDepthW[] = {
265 'm','a','x','-','e','l','e','m','e','n','t','-','d','e','p','t','h',0
267 static const WCHAR PropertyMaxXMLSizeW[] = {
268 'm','a','x','-','x','m','l','-','s','i','z','e',0
270 static const WCHAR PropertySchemaDeclHandlerW[] = {
271 's','c','h','e','m','a','-','d','e','c','l','a','r','a','t','i','o','n','-',
272 'h','a','n','d','l','e','r',0
274 static const WCHAR PropertyXMLDeclEncodingW[] = {
275 'x','m','l','d','e','c','l','-','e','n','c','o','d','i','n','g',0
277 static const WCHAR PropertyXMLDeclStandaloneW[] = {
278 'x','m','l','d','e','c','l','-','s','t','a','n','d','a','l','o','n','e',0
280 static const WCHAR PropertyXMLDeclVersionW[] = {
281 'x','m','l','d','e','c','l','-','v','e','r','s','i','o','n',0
284 static inline HRESULT set_feature_value(saxreader *reader, saxreader_feature feature, VARIANT_BOOL value)
286 /* handling of non-VARIANT_* values is version dependent */
287 if ((reader->version < MSXML4) && (value != VARIANT_TRUE))
288 value = VARIANT_FALSE;
289 if ((reader->version >= MSXML4) && (value != VARIANT_FALSE))
290 value = VARIANT_TRUE;
292 if (value == VARIANT_TRUE)
293 reader->features |= feature;
295 reader->features &= ~feature;
300 static inline HRESULT get_feature_value(const saxreader *reader, saxreader_feature feature, VARIANT_BOOL *value)
302 *value = reader->features & feature ? VARIANT_TRUE : VARIANT_FALSE;
306 static BOOL is_namespaces_enabled(const saxreader *reader)
308 return (reader->version < MSXML4) || (reader->features & Namespaces);
311 static inline int has_content_handler(const saxlocator *locator)
313 return (locator->vbInterface && locator->saxreader->vbcontentHandler) ||
314 (!locator->vbInterface && locator->saxreader->contentHandler);
317 static inline int has_lexical_handler(const saxlocator *locator)
319 return (locator->vbInterface && locator->saxreader->vblexicalHandler) ||
320 (!locator->vbInterface && locator->saxreader->lexicalHandler);
323 static inline int has_error_handler(const saxlocator *locator)
325 return (locator->vbInterface && locator->saxreader->vberrorHandler) ||
326 (!locator->vbInterface && locator->saxreader->errorHandler);
329 static BSTR build_qname(BSTR prefix, BSTR local)
331 if (prefix && *prefix)
333 BSTR qname = SysAllocStringLen(NULL, SysStringLen(prefix) + SysStringLen(local) + 1);
337 strcpyW(ptr, prefix);
338 ptr += SysStringLen(prefix);
344 return SysAllocString(local);
347 static element_entry* alloc_element_entry(const xmlChar *local, const xmlChar *prefix, int nb_ns,
348 const xmlChar **namespaces)
353 ret = heap_alloc(sizeof(*ret));
354 if (!ret) return ret;
356 ret->local = bstr_from_xmlChar(local);
357 ret->prefix = bstr_from_xmlChar(prefix);
358 ret->qname = build_qname(ret->prefix, ret->local);
359 ret->ns = nb_ns ? heap_alloc(nb_ns*sizeof(ns)) : NULL;
360 ret->ns_count = nb_ns;
362 for (i=0; i < nb_ns; i++)
364 ret->ns[i].prefix = bstr_from_xmlChar(namespaces[2*i]);
365 ret->ns[i].uri = bstr_from_xmlChar(namespaces[2*i+1]);
371 static void free_element_entry(element_entry *element)
375 for (i=0; i<element->ns_count;i++)
377 SysFreeString(element->ns[i].prefix);
378 SysFreeString(element->ns[i].uri);
381 SysFreeString(element->prefix);
382 SysFreeString(element->local);
384 heap_free(element->ns);
388 static void push_element_ns(saxlocator *locator, element_entry *element)
390 list_add_head(&locator->elements, &element->entry);
393 static element_entry * pop_element_ns(saxlocator *locator)
395 element_entry *element = LIST_ENTRY(list_head(&locator->elements), element_entry, entry);
398 list_remove(&element->entry);
403 static BSTR find_element_uri(saxlocator *locator, const xmlChar *uri)
405 element_entry *element;
409 if (!uri) return NULL;
411 uriW = bstr_from_xmlChar(uri);
413 LIST_FOR_EACH_ENTRY(element, &locator->elements, element_entry, entry)
415 for (i=0; i < element->ns_count; i++)
416 if (!strcmpW(uriW, element->ns[i].uri))
419 return element->ns[i].uri;
424 ERR("namespace uri not found, %s\n", debugstr_a((char*)uri));
428 /* used to localize version dependent error check behaviour */
429 static inline BOOL sax_callback_failed(saxlocator *This, HRESULT hr)
431 return This->saxreader->version >= MSXML4 ? FAILED(hr) : hr != S_OK;
434 /* index value -1 means it tries to loop for a first time */
435 static inline BOOL iterate_endprefix_index(saxlocator *This, const element_entry *element, int *i)
437 if (This->saxreader->version >= MSXML4)
439 if (*i == -1) *i = 0; else ++*i;
440 return *i < element->ns_count;
444 if (*i == -1) *i = element->ns_count-1; else --*i;
449 static BOOL bstr_pool_insert(struct bstrpool *pool, BSTR pool_entry)
453 pool->pool = HeapAlloc(GetProcessHeap(), 0, 16 * sizeof(*pool->pool));
460 else if (pool->index == pool->len)
462 BSTR *realloc = HeapReAlloc(GetProcessHeap(), 0, pool->pool, pool->len * 2 * sizeof(*realloc));
467 pool->pool = realloc;
471 pool->pool[pool->index++] = pool_entry;
475 static void free_bstr_pool(struct bstrpool *pool)
479 for (i = 0; i < pool->index; i++)
480 SysFreeString(pool->pool[i]);
482 HeapFree(GetProcessHeap(), 0, pool->pool);
485 pool->index = pool->len = 0;
488 static BSTR bstr_from_xmlCharN(const xmlChar *buf, int len)
496 dLen = MultiByteToWideChar(CP_UTF8, 0, (LPCSTR)buf, len, NULL, 0);
497 if(len != -1) dLen++;
498 bstr = SysAllocStringLen(NULL, dLen-1);
501 MultiByteToWideChar(CP_UTF8, 0, (LPCSTR)buf, len, bstr, dLen);
502 if(len != -1) bstr[dLen-1] = '\0';
507 static BSTR QName_from_xmlChar(const xmlChar *prefix, const xmlChar *name)
512 if(!name) return NULL;
514 if(!prefix || !*prefix)
515 return bstr_from_xmlChar(name);
517 qname = xmlBuildQName(name, prefix, NULL, 0);
518 bstr = bstr_from_xmlChar(qname);
524 static BSTR pooled_bstr_from_xmlChar(struct bstrpool *pool, const xmlChar *buf)
526 BSTR pool_entry = bstr_from_xmlChar(buf);
528 if (pool_entry && !bstr_pool_insert(pool, pool_entry))
530 SysFreeString(pool_entry);
537 static BSTR pooled_bstr_from_xmlCharN(struct bstrpool *pool, const xmlChar *buf, int len)
539 BSTR pool_entry = bstr_from_xmlCharN(buf, len);
541 if (pool_entry && !bstr_pool_insert(pool, pool_entry))
543 SysFreeString(pool_entry);
550 static void format_error_message_from_id(saxlocator *This, HRESULT hr)
552 xmlStopParser(This->pParserCtxt);
555 if(has_error_handler(This))
558 if(!FormatMessageW(FORMAT_MESSAGE_FROM_SYSTEM,
559 NULL, hr, 0, msg, sizeof(msg), NULL))
561 FIXME("MSXML errors not yet supported.\n");
565 if(This->vbInterface)
567 BSTR bstrMsg = SysAllocString(msg);
568 IVBSAXErrorHandler_fatalError(This->saxreader->vberrorHandler,
569 &This->IVBSAXLocator_iface, &bstrMsg, hr);
570 SysFreeString(bstrMsg);
573 ISAXErrorHandler_fatalError(This->saxreader->errorHandler,
574 &This->ISAXLocator_iface, msg, hr);
578 static void update_position(saxlocator *This, BOOL fix_column)
580 const xmlChar *p = This->pParserCtxt->input->cur-1;
582 This->line = xmlSAX2GetLineNumber(This->pParserCtxt);
586 for(; *p!='\n' && *p!='\r' && p>=This->pParserCtxt->input->base; p--)
591 This->column = xmlSAX2GetColumnNumber(This->pParserCtxt);
595 /*** IVBSAXAttributes interface ***/
596 /*** IUnknown methods ***/
597 static HRESULT WINAPI ivbsaxattributes_QueryInterface(
598 IVBSAXAttributes* iface,
602 saxlocator *This = impl_from_IVBSAXAttributes(iface);
603 TRACE("(%p)->(%s %p)\n", This, debugstr_guid(riid), ppvObject);
604 return IVBSAXLocator_QueryInterface(&This->IVBSAXLocator_iface, riid, ppvObject);
607 static ULONG WINAPI ivbsaxattributes_AddRef(IVBSAXAttributes* iface)
609 saxlocator *This = impl_from_IVBSAXAttributes(iface);
610 return ISAXLocator_AddRef(&This->ISAXLocator_iface);
613 static ULONG WINAPI ivbsaxattributes_Release(IVBSAXAttributes* iface)
615 saxlocator *This = impl_from_IVBSAXAttributes(iface);
616 return ISAXLocator_Release(&This->ISAXLocator_iface);
619 /*** IDispatch methods ***/
620 static HRESULT WINAPI ivbsaxattributes_GetTypeInfoCount( IVBSAXAttributes *iface, UINT* pctinfo )
622 saxlocator *This = impl_from_IVBSAXAttributes( iface );
623 return IVBSAXAttributes_GetTypeInfoCount(This->vbsaxattr, pctinfo);
626 static HRESULT WINAPI ivbsaxattributes_GetTypeInfo(IVBSAXAttributes *iface,
627 UINT iTInfo, LCID lcid, ITypeInfo** ppTInfo )
629 saxlocator *This = impl_from_IVBSAXAttributes( iface );
630 return IVBSAXAttributes_GetTypeInfo(This->vbsaxattr, iTInfo, lcid, ppTInfo);
633 static HRESULT WINAPI ivbsaxattributes_GetIDsOfNames(
634 IVBSAXAttributes *iface,
641 saxlocator *This = impl_from_IVBSAXAttributes( iface );
642 return IVBSAXAttributes_GetIDsOfNames(This->vbsaxattr, riid, rgszNames, cNames, lcid, rgDispId);
645 static HRESULT WINAPI ivbsaxattributes_Invoke(
646 IVBSAXAttributes *iface,
651 DISPPARAMS* pDispParams,
653 EXCEPINFO* pExcepInfo,
656 saxlocator *This = impl_from_IVBSAXAttributes( iface );
657 return IVBSAXAttributes_Invoke(This->vbsaxattr, dispIdMember, riid, lcid, flags, pDispParams,
658 pVarResult, pExcepInfo, puArgErr);
661 /*** IVBSAXAttributes methods ***/
662 static HRESULT WINAPI ivbsaxattributes_get_length(
663 IVBSAXAttributes* iface,
666 saxlocator *This = impl_from_IVBSAXAttributes( iface );
667 return ISAXAttributes_getLength(&This->ISAXAttributes_iface, nLength);
670 static HRESULT WINAPI ivbsaxattributes_getURI(
671 IVBSAXAttributes* iface,
676 saxlocator *This = impl_from_IVBSAXAttributes( iface );
677 return ISAXAttributes_getURI(&This->ISAXAttributes_iface, nIndex, (const WCHAR**)uri, &len);
680 static HRESULT WINAPI ivbsaxattributes_getLocalName(IVBSAXAttributes* iface, int index, BSTR *name)
682 saxlocator *This = impl_from_IVBSAXAttributes( iface );
683 return IVBSAXAttributes_getLocalName(This->vbsaxattr, index, name);
686 static HRESULT WINAPI ivbsaxattributes_getQName(IVBSAXAttributes* iface, int index, BSTR *qname)
688 saxlocator *This = impl_from_IVBSAXAttributes( iface );
689 return IVBSAXAttributes_getQName(This->vbsaxattr, index, qname);
692 static HRESULT WINAPI ivbsaxattributes_getIndexFromName(IVBSAXAttributes* iface, BSTR uri, BSTR name,
695 saxlocator *This = impl_from_IVBSAXAttributes( iface );
696 return IVBSAXAttributes_getIndexFromName(This->vbsaxattr, uri, name, index);
699 static HRESULT WINAPI ivbsaxattributes_getIndexFromQName(IVBSAXAttributes* iface,
700 BSTR qname, int *index)
702 saxlocator *This = impl_from_IVBSAXAttributes( iface );
703 return IVBSAXAttributes_getIndexFromQName(This->vbsaxattr, qname, index);
706 static HRESULT WINAPI ivbsaxattributes_getType(IVBSAXAttributes* iface, int index, BSTR *type)
708 saxlocator *This = impl_from_IVBSAXAttributes( iface );
709 return IVBSAXAttributes_getType(This->vbsaxattr, index, type);
712 static HRESULT WINAPI ivbsaxattributes_getTypeFromName(IVBSAXAttributes* iface, BSTR uri,
713 BSTR name, BSTR *type)
715 saxlocator *This = impl_from_IVBSAXAttributes( iface );
716 return IVBSAXAttributes_getTypeFromName(This->vbsaxattr, uri, name, type);
719 static HRESULT WINAPI ivbsaxattributes_getTypeFromQName(IVBSAXAttributes* iface,
720 BSTR qname, BSTR *type)
722 saxlocator *This = impl_from_IVBSAXAttributes( iface );
723 return IVBSAXAttributes_getTypeFromQName(This->vbsaxattr, qname, type);
726 static HRESULT WINAPI ivbsaxattributes_getValue(IVBSAXAttributes* iface, int index,
729 saxlocator *This = impl_from_IVBSAXAttributes( iface );
730 return IVBSAXAttributes_getValue(This->vbsaxattr, index, value);
733 static HRESULT WINAPI ivbsaxattributes_getValueFromName(IVBSAXAttributes* iface, BSTR uri,
734 BSTR name, BSTR *value)
736 saxlocator *This = impl_from_IVBSAXAttributes( iface );
737 return IVBSAXAttributes_getValueFromName(This->vbsaxattr, uri, name, value);
740 static HRESULT WINAPI ivbsaxattributes_getValueFromQName(IVBSAXAttributes* iface, BSTR qname,
743 saxlocator *This = impl_from_IVBSAXAttributes( iface );
744 return IVBSAXAttributes_getValueFromQName(This->vbsaxattr, qname, value);
747 static const struct IVBSAXAttributesVtbl ivbsaxattributes_vtbl =
749 ivbsaxattributes_QueryInterface,
750 ivbsaxattributes_AddRef,
751 ivbsaxattributes_Release,
752 ivbsaxattributes_GetTypeInfoCount,
753 ivbsaxattributes_GetTypeInfo,
754 ivbsaxattributes_GetIDsOfNames,
755 ivbsaxattributes_Invoke,
756 ivbsaxattributes_get_length,
757 ivbsaxattributes_getURI,
758 ivbsaxattributes_getLocalName,
759 ivbsaxattributes_getQName,
760 ivbsaxattributes_getIndexFromName,
761 ivbsaxattributes_getIndexFromQName,
762 ivbsaxattributes_getType,
763 ivbsaxattributes_getTypeFromName,
764 ivbsaxattributes_getTypeFromQName,
765 ivbsaxattributes_getValue,
766 ivbsaxattributes_getValueFromName,
767 ivbsaxattributes_getValueFromQName
770 /*** ISAXAttributes interface ***/
771 /*** IUnknown methods ***/
772 static HRESULT WINAPI isaxattributes_QueryInterface(
773 ISAXAttributes* iface,
777 saxlocator *This = impl_from_ISAXAttributes(iface);
778 TRACE("(%p)->(%s %p)\n", This, debugstr_guid(riid), ppvObject);
779 return ISAXLocator_QueryInterface(&This->ISAXLocator_iface, riid, ppvObject);
782 static ULONG WINAPI isaxattributes_AddRef(ISAXAttributes* iface)
784 saxlocator *This = impl_from_ISAXAttributes(iface);
786 return ISAXLocator_AddRef(&This->ISAXLocator_iface);
789 static ULONG WINAPI isaxattributes_Release(ISAXAttributes* iface)
791 saxlocator *This = impl_from_ISAXAttributes(iface);
793 return ISAXLocator_Release(&This->ISAXLocator_iface);
796 /*** ISAXAttributes methods ***/
797 static HRESULT WINAPI isaxattributes_getLength(ISAXAttributes* iface, int *len)
799 saxlocator *This = impl_from_ISAXAttributes( iface );
800 return ISAXAttributes_getLength(This->saxattr, len);
803 static HRESULT WINAPI isaxattributes_getURI(ISAXAttributes* iface, int index,
804 const WCHAR **uri, int *len)
806 saxlocator *This = impl_from_ISAXAttributes( iface );
807 return ISAXAttributes_getURI(This->saxattr, index, uri, len);
810 static HRESULT WINAPI isaxattributes_getLocalName(ISAXAttributes* iface, int index,
811 const WCHAR **name, int *len)
813 saxlocator *This = impl_from_ISAXAttributes( iface );
814 return ISAXAttributes_getLocalName(This->saxattr, index, name, len);
817 static HRESULT WINAPI isaxattributes_getQName(ISAXAttributes* iface, int index,
818 const WCHAR **qname, int *len)
820 saxlocator *This = impl_from_ISAXAttributes( iface );
821 return ISAXAttributes_getLocalName(This->saxattr, index, qname, len);
824 static HRESULT WINAPI isaxattributes_getName(ISAXAttributes* iface, int index,
825 const WCHAR **uri, int *uri_len, const WCHAR **local, int *local_len,
826 const WCHAR **qname, int *qname_len)
828 saxlocator *This = impl_from_ISAXAttributes( iface );
829 return ISAXAttributes_getName(This->saxattr, index, uri, uri_len, local, local_len,
833 static HRESULT WINAPI isaxattributes_getIndexFromName(ISAXAttributes* iface, const WCHAR *uri,
834 int uri_len, const WCHAR *name, int len, int *index)
836 saxlocator *This = impl_from_ISAXAttributes( iface );
837 return ISAXAttributes_getIndexFromName(This->saxattr, uri, uri_len, name, len, index);
840 static HRESULT WINAPI isaxattributes_getIndexFromQName(ISAXAttributes* iface, const WCHAR *qname,
841 int qname_len, int *index)
843 saxlocator *This = impl_from_ISAXAttributes( iface );
844 return ISAXAttributes_getIndexFromQName(This->saxattr, qname, qname_len, index);
847 static HRESULT WINAPI isaxattributes_getType(ISAXAttributes* iface, int index,
848 const WCHAR **type, int *len)
850 saxlocator *This = impl_from_ISAXAttributes( iface );
851 return ISAXAttributes_getType(This->saxattr, index, type, len);
854 static HRESULT WINAPI isaxattributes_getTypeFromName(ISAXAttributes* iface,
855 const WCHAR *uri, int uri_len, const WCHAR *name, int name_len,
856 const WCHAR **type, int *type_len)
858 saxlocator *This = impl_from_ISAXAttributes( iface );
859 return ISAXAttributes_getTypeFromName(This->saxattr, uri, uri_len, name, name_len,
863 static HRESULT WINAPI isaxattributes_getTypeFromQName(ISAXAttributes* iface,
864 const WCHAR *qname, int qname_len, const WCHAR **type, int *type_len)
866 saxlocator *This = impl_from_ISAXAttributes( iface );
867 return ISAXAttributes_getTypeFromQName(This->saxattr, qname, qname_len, type, type_len);
870 static HRESULT WINAPI isaxattributes_getValue(ISAXAttributes* iface, int index,
871 const WCHAR **value, int *len)
873 saxlocator *This = impl_from_ISAXAttributes( iface );
874 return ISAXAttributes_getValue(This->saxattr, index, value, len);
877 static HRESULT WINAPI isaxattributes_getValueFromName(ISAXAttributes* iface,
878 const WCHAR *uri, int uri_len, const WCHAR *name, int name_len,
879 const WCHAR **value, int *len)
881 saxlocator *This = impl_from_ISAXAttributes( iface );
882 return ISAXAttributes_getValueFromName(This->saxattr, uri, uri_len, name, name_len,
886 static HRESULT WINAPI isaxattributes_getValueFromQName(ISAXAttributes* iface,
887 const WCHAR *qname, int qname_len, const WCHAR **value, int *value_len)
889 saxlocator *This = impl_from_ISAXAttributes( iface );
890 return ISAXAttributes_getValueFromQName(This->saxattr, qname, qname_len, value, value_len);
893 static const struct ISAXAttributesVtbl isaxattributes_vtbl =
895 isaxattributes_QueryInterface,
896 isaxattributes_AddRef,
897 isaxattributes_Release,
898 isaxattributes_getLength,
899 isaxattributes_getURI,
900 isaxattributes_getLocalName,
901 isaxattributes_getQName,
902 isaxattributes_getName,
903 isaxattributes_getIndexFromName,
904 isaxattributes_getIndexFromQName,
905 isaxattributes_getType,
906 isaxattributes_getTypeFromName,
907 isaxattributes_getTypeFromQName,
908 isaxattributes_getValue,
909 isaxattributes_getValueFromName,
910 isaxattributes_getValueFromQName
913 static HRESULT SAXAttributes_populate(saxlocator *locator,
914 int nb_namespaces, const xmlChar **xmlNamespaces,
915 int nb_attributes, const xmlChar **xmlAttributes)
917 static const xmlChar xmlns[] = "xmlns";
918 BSTR empty, qname, value;
921 /* skip namespace definitions */
922 if ((locator->saxreader->features & NamespacePrefixes) == 0)
925 IMXAttributes_clear(locator->attributes);
927 empty = SysAllocStringLen(NULL, 0);
929 for (i = 0; i < nb_attributes; i++)
931 static const xmlChar xmlA[] = "xml";
934 if (xmlStrEqual(xmlAttributes[i*5+1], xmlA))
935 uri = bstr_from_xmlChar(xmlAttributes[i*5+2]);
937 uri = find_element_uri(locator, xmlAttributes[i*5+2]);
939 local = bstr_from_xmlChar(xmlAttributes[i*5]);
940 value = bstr_from_xmlCharN(xmlAttributes[i*5+3], xmlAttributes[i*5+4]-xmlAttributes[i*5+3]);
941 qname = QName_from_xmlChar(xmlAttributes[i*5+1], xmlAttributes[i*5]);
943 IMXAttributes_addAttribute(locator->attributes, uri ? uri : empty, local, qname, empty, value);
945 if (xmlStrEqual(xmlAttributes[i*5+1], xmlA))
948 SysFreeString(local);
949 SysFreeString(qname);
950 SysFreeString(value);
953 for (i = 0; i < nb_namespaces; i++)
955 static const WCHAR xmlnsW[] = { 'x','m','l','n','s',0 };
957 if (!xmlNamespaces[2*i])
958 qname = SysAllocString(xmlnsW);
960 qname = QName_from_xmlChar(xmlns, xmlNamespaces[2*i]);
962 value = bstr_from_xmlChar(xmlNamespaces[2*i+1]);
964 IMXAttributes_addAttribute(locator->attributes, locator->namespaceUri,
965 empty, qname, empty, value);
967 SysFreeString(qname);
968 SysFreeString(value);
971 SysFreeString(empty);
976 /*** LibXML callbacks ***/
977 static void libxmlStartDocument(void *ctx)
979 saxlocator *This = ctx;
982 if (This->saxreader->version >= MSXML4)
984 const xmlChar *p = This->pParserCtxt->input->cur-1;
985 update_position(This, FALSE);
986 while(p>This->pParserCtxt->input->base && *p!='>')
988 if(*p=='\n' || (*p=='\r' && *(p+1)!='\n'))
993 for(; p>=This->pParserCtxt->input->base && *p!='\n' && *p!='\r'; p--)
997 if(has_content_handler(This))
999 if(This->vbInterface)
1000 hr = IVBSAXContentHandler_startDocument(This->saxreader->vbcontentHandler);
1002 hr = ISAXContentHandler_startDocument(This->saxreader->contentHandler);
1004 if (sax_callback_failed(This, hr))
1005 format_error_message_from_id(This, hr);
1009 static void libxmlEndDocument(void *ctx)
1011 saxlocator *This = ctx;
1014 if (This->saxreader->version >= MSXML4) {
1015 update_position(This, FALSE);
1016 if(This->column > 1)
1024 if(This->ret != S_OK) return;
1026 if(has_content_handler(This))
1028 if(This->vbInterface)
1029 hr = IVBSAXContentHandler_endDocument(This->saxreader->vbcontentHandler);
1031 hr = ISAXContentHandler_endDocument(This->saxreader->contentHandler);
1033 if (sax_callback_failed(This, hr))
1034 format_error_message_from_id(This, hr);
1038 static void libxmlStartElementNS(
1040 const xmlChar *localname,
1041 const xmlChar *prefix,
1044 const xmlChar **namespaces,
1047 const xmlChar **attributes)
1049 saxlocator *This = ctx;
1050 element_entry *element;
1054 update_position(This, TRUE);
1055 if(*(This->pParserCtxt->input->cur) == '/')
1057 if(This->saxreader->version < MSXML4)
1060 element = alloc_element_entry(localname, prefix, nb_namespaces, namespaces);
1061 push_element_ns(This, element);
1063 if (is_namespaces_enabled(This->saxreader))
1067 for (i = 0; i < nb_namespaces && has_content_handler(This); i++)
1069 if (This->vbInterface)
1070 hr = IVBSAXContentHandler_startPrefixMapping(
1071 This->saxreader->vbcontentHandler,
1072 &element->ns[i].prefix,
1073 &element->ns[i].uri);
1075 hr = ISAXContentHandler_startPrefixMapping(
1076 This->saxreader->contentHandler,
1077 element->ns[i].prefix,
1078 SysStringLen(element->ns[i].prefix),
1080 SysStringLen(element->ns[i].uri));
1082 if (sax_callback_failed(This, hr))
1084 format_error_message_from_id(This, hr);
1090 uri = find_element_uri(This, URI);
1091 hr = SAXAttributes_populate(This, nb_namespaces, namespaces, nb_attributes, attributes);
1092 if (hr == S_OK && has_content_handler(This))
1096 if (is_namespaces_enabled(This->saxreader))
1097 local = element->local;
1101 if (This->vbInterface)
1102 hr = IVBSAXContentHandler_startElement(This->saxreader->vbcontentHandler,
1103 &uri, &local, &element->qname, &This->IVBSAXAttributes_iface);
1105 hr = ISAXContentHandler_startElement(This->saxreader->contentHandler,
1106 uri, SysStringLen(uri),
1107 local, SysStringLen(local),
1108 element->qname, SysStringLen(element->qname),
1109 &This->ISAXAttributes_iface);
1111 if (sax_callback_failed(This, hr))
1112 format_error_message_from_id(This, hr);
1116 static void libxmlEndElementNS(
1118 const xmlChar *localname,
1119 const xmlChar *prefix,
1122 saxlocator *This = ctx;
1123 element_entry *element;
1128 update_position(This, FALSE);
1129 p = This->pParserCtxt->input->cur;
1131 if (This->saxreader->version >= MSXML4)
1134 while(p>This->pParserCtxt->input->base && *p!='>')
1136 if(*p=='\n' || (*p=='\r' && *(p+1)!='\n'))
1141 else if(*(p-1)!='>' || *(p-2)!='/')
1144 while(p-2>=This->pParserCtxt->input->base
1145 && *(p-2)!='<' && *(p-1)!='/')
1147 if(*p=='\n' || (*p=='\r' && *(p+1)!='\n'))
1153 for(; p>=This->pParserCtxt->input->base && *p!='\n' && *p!='\r'; p--)
1156 uri = find_element_uri(This, URI);
1157 element = pop_element_ns(This);
1159 if (!has_content_handler(This))
1161 IMXAttributes_clear(This->attributes);
1162 free_element_entry(element);
1166 if (is_namespaces_enabled(This->saxreader))
1167 local = element->local;
1171 if (This->vbInterface)
1172 hr = IVBSAXContentHandler_endElement(
1173 This->saxreader->vbcontentHandler,
1174 &uri, &local, &element->qname);
1176 hr = ISAXContentHandler_endElement(
1177 This->saxreader->contentHandler,
1178 uri, SysStringLen(uri),
1179 local, SysStringLen(local),
1180 element->qname, SysStringLen(element->qname));
1182 IMXAttributes_clear(This->attributes);
1184 if (sax_callback_failed(This, hr))
1186 format_error_message_from_id(This, hr);
1187 free_element_entry(element);
1191 if (is_namespaces_enabled(This->saxreader))
1194 while (iterate_endprefix_index(This, element, &i) && has_content_handler(This))
1196 if (This->vbInterface)
1197 hr = IVBSAXContentHandler_endPrefixMapping(
1198 This->saxreader->vbcontentHandler, &element->ns[i].prefix);
1200 hr = ISAXContentHandler_endPrefixMapping(
1201 This->saxreader->contentHandler,
1202 element->ns[i].prefix, SysStringLen(element->ns[i].prefix));
1204 if (sax_callback_failed(This, hr)) break;
1207 if (sax_callback_failed(This, hr))
1208 format_error_message_from_id(This, hr);
1211 free_element_entry(element);
1214 static void libxmlCharacters(
1219 saxlocator *This = ctx;
1223 BOOL lastEvent = FALSE;
1225 if(!(has_content_handler(This))) return;
1227 update_position(This, FALSE);
1228 cur = (xmlChar*)This->pParserCtxt->input->cur;
1229 while(cur>=This->pParserCtxt->input->base && *cur!='>')
1231 if(*cur=='\n' || (*cur=='\r' && *(cur+1)!='\n'))
1236 for(; cur>=This->pParserCtxt->input->base && *cur!='\n' && *cur!='\r'; cur--)
1240 if(*(ch-1)=='\r') cur--;
1245 while(end-ch<len && *end!='\r') end++;
1256 if (This->saxreader->version >= MSXML4)
1260 for(p=cur; p!=end; p++)
1277 Chars = pooled_bstr_from_xmlCharN(&This->saxreader->pool, cur, end-cur);
1278 if(This->vbInterface)
1279 hr = IVBSAXContentHandler_characters(
1280 This->saxreader->vbcontentHandler, &Chars);
1282 hr = ISAXContentHandler_characters(
1283 This->saxreader->contentHandler,
1284 Chars, SysStringLen(Chars));
1286 if (sax_callback_failed(This, hr))
1288 format_error_message_from_id(This, hr);
1292 if (This->saxreader->version < MSXML4)
1293 This->column += end-cur;
1306 if(end-ch == len) break;
1310 static void libxmlSetDocumentLocator(
1312 xmlSAXLocatorPtr loc)
1314 saxlocator *This = ctx;
1317 if(has_content_handler(This))
1319 if(This->vbInterface)
1320 hr = IVBSAXContentHandler_putref_documentLocator(This->saxreader->vbcontentHandler,
1321 &This->IVBSAXLocator_iface);
1323 hr = ISAXContentHandler_putDocumentLocator(This->saxreader->contentHandler,
1324 &This->ISAXLocator_iface);
1328 format_error_message_from_id(This, hr);
1331 static void libxmlComment(void *ctx, const xmlChar *value)
1333 saxlocator *This = ctx;
1336 const xmlChar *p = This->pParserCtxt->input->cur;
1338 update_position(This, FALSE);
1339 while(p-4>=This->pParserCtxt->input->base
1340 && memcmp(p-4, "<!--", sizeof(char[4])))
1342 if(*p=='\n' || (*p=='\r' && *(p+1)!='\n'))
1348 for(; p>=This->pParserCtxt->input->base && *p!='\n' && *p!='\r'; p--)
1351 if (!has_lexical_handler(This)) return;
1353 bValue = pooled_bstr_from_xmlChar(&This->saxreader->pool, value);
1355 if(This->vbInterface)
1356 hr = IVBSAXLexicalHandler_comment(
1357 This->saxreader->vblexicalHandler, &bValue);
1359 hr = ISAXLexicalHandler_comment(
1360 This->saxreader->lexicalHandler,
1361 bValue, SysStringLen(bValue));
1364 format_error_message_from_id(This, hr);
1367 static void libxmlFatalError(void *ctx, const char *msg, ...)
1369 saxlocator *This = ctx;
1375 if(This->ret != S_OK) {
1376 xmlStopParser(This->pParserCtxt);
1380 va_start(args, msg);
1381 vsprintf(message, msg, args);
1384 len = MultiByteToWideChar(CP_UNIXCP, 0, message, -1, NULL, 0);
1385 error = heap_alloc(sizeof(WCHAR)*len);
1388 MultiByteToWideChar(CP_UNIXCP, 0, message, -1, error, len);
1389 TRACE("fatal error for %p: %s\n", This, debugstr_w(error));
1392 if(!has_error_handler(This))
1394 xmlStopParser(This->pParserCtxt);
1400 FIXME("Error handling is not compatible.\n");
1402 if(This->vbInterface)
1404 BSTR bstrError = SysAllocString(error);
1405 IVBSAXErrorHandler_fatalError(This->saxreader->vberrorHandler, &This->IVBSAXLocator_iface,
1406 &bstrError, E_FAIL);
1407 SysFreeString(bstrError);
1410 ISAXErrorHandler_fatalError(This->saxreader->errorHandler, &This->ISAXLocator_iface,
1415 xmlStopParser(This->pParserCtxt);
1419 static void libxmlCDataBlock(void *ctx, const xmlChar *value, int len)
1421 saxlocator *This = ctx;
1423 xmlChar *beg = (xmlChar*)This->pParserCtxt->input->cur-len;
1427 BOOL lastEvent = FALSE, change;
1429 update_position(This, FALSE);
1430 while(beg-9>=This->pParserCtxt->input->base
1431 && memcmp(beg-9, "<![CDATA[", sizeof(char[9])))
1433 if(*beg=='\n' || (*beg=='\r' && *(beg+1)!='\n'))
1438 for(; beg>=This->pParserCtxt->input->base && *beg!='\n' && *beg!='\r'; beg--)
1441 if (has_lexical_handler(This))
1443 if (This->vbInterface)
1444 hr = IVBSAXLexicalHandler_startCDATA(This->saxreader->vblexicalHandler);
1446 hr = ISAXLexicalHandler_startCDATA(This->saxreader->lexicalHandler);
1451 format_error_message_from_id(This, hr);
1455 realLen = This->pParserCtxt->input->cur-beg-3;
1461 while(end-beg<realLen && *end!='\r') end++;
1462 if(end-beg==realLen)
1467 else if(end-beg==realLen-1 && *end=='\r' && *(end+1)=='\n')
1470 if(*end == '\r') change = TRUE;
1471 else change = FALSE;
1473 if(change) *end = '\n';
1475 if(has_content_handler(This))
1477 Chars = pooled_bstr_from_xmlCharN(&This->saxreader->pool, cur, end-cur+1);
1478 if(This->vbInterface)
1479 hr = IVBSAXContentHandler_characters(
1480 This->saxreader->vbcontentHandler, &Chars);
1482 hr = ISAXContentHandler_characters(
1483 This->saxreader->contentHandler,
1484 Chars, SysStringLen(Chars));
1487 if(change) *end = '\r';
1492 This->column += end-cur+2;
1497 if (has_lexical_handler(This))
1499 if (This->vbInterface)
1500 hr = IVBSAXLexicalHandler_endCDATA(This->saxreader->vblexicalHandler);
1502 hr = ISAXLexicalHandler_endCDATA(This->saxreader->lexicalHandler);
1506 format_error_message_from_id(This, hr);
1508 This->column += 4+end-cur;
1511 /*** IVBSAXLocator interface ***/
1512 /*** IUnknown methods ***/
1513 static HRESULT WINAPI ivbsaxlocator_QueryInterface(IVBSAXLocator* iface, REFIID riid, void **ppvObject)
1515 saxlocator *This = impl_from_IVBSAXLocator( iface );
1517 TRACE("%p %s %p\n", This, debugstr_guid( riid ), ppvObject);
1521 if ( IsEqualGUID( riid, &IID_IUnknown ) ||
1522 IsEqualGUID( riid, &IID_IDispatch) ||
1523 IsEqualGUID( riid, &IID_IVBSAXLocator ))
1527 else if ( IsEqualGUID( riid, &IID_IVBSAXAttributes ))
1529 *ppvObject = &This->IVBSAXAttributes_iface;
1533 FIXME("interface %s not implemented\n", debugstr_guid(riid));
1534 return E_NOINTERFACE;
1537 IVBSAXLocator_AddRef( iface );
1542 static ULONG WINAPI ivbsaxlocator_AddRef(IVBSAXLocator* iface)
1544 saxlocator *This = impl_from_IVBSAXLocator( iface );
1545 TRACE("%p\n", This );
1546 return InterlockedIncrement( &This->ref );
1549 static ULONG WINAPI ivbsaxlocator_Release(
1550 IVBSAXLocator* iface)
1552 saxlocator *This = impl_from_IVBSAXLocator( iface );
1553 return ISAXLocator_Release((ISAXLocator*)&This->IVBSAXLocator_iface);
1556 /*** IDispatch methods ***/
1557 static HRESULT WINAPI ivbsaxlocator_GetTypeInfoCount( IVBSAXLocator *iface, UINT* pctinfo )
1559 saxlocator *This = impl_from_IVBSAXLocator( iface );
1561 TRACE("(%p)->(%p)\n", This, pctinfo);
1568 static HRESULT WINAPI ivbsaxlocator_GetTypeInfo(
1569 IVBSAXLocator *iface,
1570 UINT iTInfo, LCID lcid, ITypeInfo** ppTInfo )
1572 saxlocator *This = impl_from_IVBSAXLocator( iface );
1575 TRACE("(%p)->(%u %u %p)\n", This, iTInfo, lcid, ppTInfo);
1577 hr = get_typeinfo(IVBSAXLocator_tid, ppTInfo);
1582 static HRESULT WINAPI ivbsaxlocator_GetIDsOfNames(
1583 IVBSAXLocator *iface,
1585 LPOLESTR* rgszNames,
1590 saxlocator *This = impl_from_IVBSAXLocator( iface );
1591 ITypeInfo *typeinfo;
1594 TRACE("(%p)->(%s %p %u %u %p)\n", This, debugstr_guid(riid), rgszNames, cNames,
1597 if(!rgszNames || cNames == 0 || !rgDispId)
1598 return E_INVALIDARG;
1600 hr = get_typeinfo(IVBSAXLocator_tid, &typeinfo);
1603 hr = ITypeInfo_GetIDsOfNames(typeinfo, rgszNames, cNames, rgDispId);
1604 ITypeInfo_Release(typeinfo);
1610 static HRESULT WINAPI ivbsaxlocator_Invoke(
1611 IVBSAXLocator *iface,
1612 DISPID dispIdMember,
1616 DISPPARAMS* pDispParams,
1617 VARIANT* pVarResult,
1618 EXCEPINFO* pExcepInfo,
1621 saxlocator *This = impl_from_IVBSAXLocator( iface );
1622 ITypeInfo *typeinfo;
1625 TRACE("(%p)->(%d %s %d %d %p %p %p %p)\n", This, dispIdMember, debugstr_guid(riid),
1626 lcid, wFlags, pDispParams, pVarResult, pExcepInfo, puArgErr);
1628 hr = get_typeinfo(IVBSAXLocator_tid, &typeinfo);
1631 hr = ITypeInfo_Invoke(typeinfo, &This->IVBSAXLocator_iface, dispIdMember, wFlags,
1632 pDispParams, pVarResult, pExcepInfo, puArgErr);
1633 ITypeInfo_Release(typeinfo);
1639 /*** IVBSAXLocator methods ***/
1640 static HRESULT WINAPI ivbsaxlocator_get_columnNumber(
1641 IVBSAXLocator* iface,
1644 saxlocator *This = impl_from_IVBSAXLocator( iface );
1645 return ISAXLocator_getColumnNumber((ISAXLocator*)&This->IVBSAXLocator_iface, pnColumn);
1648 static HRESULT WINAPI ivbsaxlocator_get_lineNumber(
1649 IVBSAXLocator* iface,
1652 saxlocator *This = impl_from_IVBSAXLocator( iface );
1653 return ISAXLocator_getLineNumber((ISAXLocator*)&This->IVBSAXLocator_iface, pnLine);
1656 static HRESULT WINAPI ivbsaxlocator_get_publicId(
1657 IVBSAXLocator* iface,
1660 saxlocator *This = impl_from_IVBSAXLocator( iface );
1661 return ISAXLocator_getPublicId((ISAXLocator*)&This->IVBSAXLocator_iface,
1662 (const WCHAR**)publicId);
1665 static HRESULT WINAPI ivbsaxlocator_get_systemId(
1666 IVBSAXLocator* iface,
1669 saxlocator *This = impl_from_IVBSAXLocator( iface );
1670 return ISAXLocator_getSystemId((ISAXLocator*)&This->IVBSAXLocator_iface,
1671 (const WCHAR**)systemId);
1674 static const struct IVBSAXLocatorVtbl VBSAXLocatorVtbl =
1676 ivbsaxlocator_QueryInterface,
1677 ivbsaxlocator_AddRef,
1678 ivbsaxlocator_Release,
1679 ivbsaxlocator_GetTypeInfoCount,
1680 ivbsaxlocator_GetTypeInfo,
1681 ivbsaxlocator_GetIDsOfNames,
1682 ivbsaxlocator_Invoke,
1683 ivbsaxlocator_get_columnNumber,
1684 ivbsaxlocator_get_lineNumber,
1685 ivbsaxlocator_get_publicId,
1686 ivbsaxlocator_get_systemId
1689 /*** ISAXLocator interface ***/
1690 /*** IUnknown methods ***/
1691 static HRESULT WINAPI isaxlocator_QueryInterface(ISAXLocator* iface, REFIID riid, void **ppvObject)
1693 saxlocator *This = impl_from_ISAXLocator( iface );
1695 TRACE("(%p)->(%s %p)\n", This, debugstr_guid( riid ), ppvObject );
1699 if ( IsEqualGUID( riid, &IID_IUnknown ) ||
1700 IsEqualGUID( riid, &IID_ISAXLocator ))
1704 else if ( IsEqualGUID( riid, &IID_ISAXAttributes ))
1706 *ppvObject = &This->ISAXAttributes_iface;
1710 WARN("interface %s not implemented\n", debugstr_guid(riid));
1711 return E_NOINTERFACE;
1714 ISAXLocator_AddRef( iface );
1719 static ULONG WINAPI isaxlocator_AddRef(ISAXLocator* iface)
1721 saxlocator *This = impl_from_ISAXLocator( iface );
1722 ULONG ref = InterlockedIncrement( &This->ref );
1723 TRACE("(%p)->(%d)\n", This, ref);
1727 static ULONG WINAPI isaxlocator_Release(
1730 saxlocator *This = impl_from_ISAXLocator( iface );
1731 LONG ref = InterlockedDecrement( &This->ref );
1733 TRACE("(%p)->(%d)\n", This, ref );
1737 element_entry *element, *element2;
1739 SysFreeString(This->publicId);
1740 SysFreeString(This->systemId);
1741 SysFreeString(This->namespaceUri);
1743 ISAXAttributes_Release(This->saxattr);
1744 IVBSAXAttributes_Release(This->vbsaxattr);
1745 IMXAttributes_Release(This->attributes);
1748 LIST_FOR_EACH_ENTRY_SAFE(element, element2, &This->elements, element_entry, entry)
1750 list_remove(&element->entry);
1751 free_element_entry(element);
1754 ISAXXMLReader_Release(&This->saxreader->ISAXXMLReader_iface);
1761 /*** ISAXLocator methods ***/
1762 static HRESULT WINAPI isaxlocator_getColumnNumber(
1766 saxlocator *This = impl_from_ISAXLocator( iface );
1768 *pnColumn = This->column;
1772 static HRESULT WINAPI isaxlocator_getLineNumber(
1776 saxlocator *This = impl_from_ISAXLocator( iface );
1778 *pnLine = This->line;
1782 static HRESULT WINAPI isaxlocator_getPublicId(
1784 const WCHAR ** ppwchPublicId)
1787 saxlocator *This = impl_from_ISAXLocator( iface );
1789 SysFreeString(This->publicId);
1791 publicId = bstr_from_xmlChar(xmlSAX2GetPublicId(This->pParserCtxt));
1792 if(SysStringLen(publicId))
1793 This->publicId = (WCHAR*)&publicId;
1796 SysFreeString(publicId);
1797 This->publicId = NULL;
1800 *ppwchPublicId = This->publicId;
1804 static HRESULT WINAPI isaxlocator_getSystemId(
1806 const WCHAR ** ppwchSystemId)
1809 saxlocator *This = impl_from_ISAXLocator( iface );
1811 SysFreeString(This->systemId);
1813 systemId = bstr_from_xmlChar(xmlSAX2GetSystemId(This->pParserCtxt));
1814 if(SysStringLen(systemId))
1815 This->systemId = (WCHAR*)&systemId;
1818 SysFreeString(systemId);
1819 This->systemId = NULL;
1822 *ppwchSystemId = This->systemId;
1826 static const struct ISAXLocatorVtbl SAXLocatorVtbl =
1828 isaxlocator_QueryInterface,
1830 isaxlocator_Release,
1831 isaxlocator_getColumnNumber,
1832 isaxlocator_getLineNumber,
1833 isaxlocator_getPublicId,
1834 isaxlocator_getSystemId
1837 static HRESULT SAXLocator_create(saxreader *reader, saxlocator **ppsaxlocator, BOOL vbInterface)
1839 static const WCHAR w3xmlns[] = { 'h','t','t','p',':','/','/', 'w','w','w','.','w','3','.',
1840 'o','r','g','/','2','0','0','0','/','x','m','l','n','s','/',0 };
1842 saxlocator *locator;
1845 locator = heap_alloc( sizeof (*locator) );
1847 return E_OUTOFMEMORY;
1849 locator->IVBSAXLocator_iface.lpVtbl = &VBSAXLocatorVtbl;
1850 locator->ISAXLocator_iface.lpVtbl = &SAXLocatorVtbl;
1851 locator->IVBSAXAttributes_iface.lpVtbl = &ivbsaxattributes_vtbl;
1852 locator->ISAXAttributes_iface.lpVtbl = &isaxattributes_vtbl;
1854 locator->vbInterface = vbInterface;
1856 locator->saxreader = reader;
1857 ISAXXMLReader_AddRef(&reader->ISAXXMLReader_iface);
1859 hr = SAXAttributes_create(locator->saxreader->version, NULL, (void**)&locator->attributes);
1866 IMXAttributes_QueryInterface(locator->attributes, &IID_ISAXAttributes, (void**)&locator->saxattr);
1867 IMXAttributes_QueryInterface(locator->attributes, &IID_IVBSAXAttributes, (void**)&locator->vbsaxattr);
1869 locator->pParserCtxt = NULL;
1870 locator->publicId = NULL;
1871 locator->systemId = NULL;
1872 locator->line = reader->version < MSXML4 ? 0 : 1;
1873 locator->column = 0;
1874 locator->ret = S_OK;
1875 if (locator->saxreader->version >= MSXML6)
1876 locator->namespaceUri = SysAllocString(w3xmlns);
1878 locator->namespaceUri = SysAllocStringLen(NULL, 0);
1880 if(!locator->namespaceUri)
1882 ISAXXMLReader_Release(&reader->ISAXXMLReader_iface);
1883 IMXAttributes_Release(locator->attributes);
1885 return E_OUTOFMEMORY;
1888 list_init(&locator->elements);
1890 *ppsaxlocator = locator;
1892 TRACE("returning %p\n", *ppsaxlocator);
1897 /*** SAXXMLReader internal functions ***/
1898 static HRESULT internal_parseBuffer(saxreader *This, const char *buffer, int size, BOOL vbInterface)
1900 xmlCharEncoding encoding = XML_CHAR_ENCODING_NONE;
1901 xmlChar *enc_name = NULL;
1902 saxlocator *locator;
1905 hr = SAXLocator_create(This, &locator, vbInterface);
1911 const unsigned char *buff = (unsigned char*)buffer;
1913 encoding = xmlDetectCharEncoding((xmlChar*)buffer, 4);
1914 enc_name = (xmlChar*)xmlGetCharEncodingName(encoding);
1915 TRACE("detected encoding: %s\n", enc_name);
1916 /* skip BOM, parser won't switch encodings and so won't skip it on its own */
1917 if ((encoding == XML_CHAR_ENCODING_UTF8) &&
1918 buff[0] == 0xEF && buff[1] == 0xBB && buff[2] == 0xBF)
1925 /* if libxml2 detection failed try to guess */
1926 if (encoding == XML_CHAR_ENCODING_NONE)
1928 const WCHAR *ptr = (WCHAR*)buffer;
1929 /* xml declaration with possibly specfied encoding will be still handled by parser */
1930 if ((size >= 2) && *ptr == '<' && ptr[1] != '?')
1932 enc_name = (xmlChar*)xmlGetCharEncodingName(XML_CHAR_ENCODING_UTF16LE);
1933 encoding = XML_CHAR_ENCODING_UTF16LE;
1936 else if (encoding == XML_CHAR_ENCODING_UTF8)
1937 enc_name = (xmlChar*)xmlGetCharEncodingName(encoding);
1941 locator->pParserCtxt = xmlCreateMemoryParserCtxt(buffer, size);
1942 if (!locator->pParserCtxt)
1944 ISAXLocator_Release(&locator->ISAXLocator_iface);
1950 locator->pParserCtxt->encoding = xmlStrdup(enc_name);
1951 if (encoding == XML_CHAR_ENCODING_UTF16LE) {
1952 TRACE("switching to %s\n", enc_name);
1953 xmlSwitchEncoding(locator->pParserCtxt, encoding);
1957 xmlFree(locator->pParserCtxt->sax);
1958 locator->pParserCtxt->sax = &locator->saxreader->sax;
1959 locator->pParserCtxt->userData = locator;
1961 This->isParsing = TRUE;
1962 if(xmlParseDocument(locator->pParserCtxt) == -1 && locator->ret == S_OK)
1966 This->isParsing = FALSE;
1968 if(locator->pParserCtxt)
1970 locator->pParserCtxt->sax = NULL;
1971 xmlFreeParserCtxt(locator->pParserCtxt);
1972 locator->pParserCtxt = NULL;
1975 ISAXLocator_Release(&locator->ISAXLocator_iface);
1979 static HRESULT internal_parseStream(saxreader *This, IStream *stream, BOOL vbInterface)
1981 saxlocator *locator;
1988 hr = IStream_Read(stream, data, sizeof(data), &dataRead);
1989 if(FAILED(hr)) return hr;
1991 hr = SAXLocator_create(This, &locator, vbInterface);
1992 if(FAILED(hr)) return hr;
1994 locator->pParserCtxt = xmlCreatePushParserCtxt(
1995 &locator->saxreader->sax, locator,
1996 data, dataRead, NULL);
1997 if(!locator->pParserCtxt)
1999 ISAXLocator_Release(&locator->ISAXLocator_iface);
2003 This->isParsing = TRUE;
2005 if(dataRead != sizeof(data))
2007 ret = xmlParseChunk(locator->pParserCtxt, data, 0, 1);
2008 hr = ret!=XML_ERR_OK && locator->ret==S_OK ? E_FAIL : locator->ret;
2015 hr = IStream_Read(stream, data, sizeof(data), &dataRead);
2016 if (FAILED(hr)) break;
2018 ret = xmlParseChunk(locator->pParserCtxt, data, dataRead, 0);
2019 hr = ret!=XML_ERR_OK && locator->ret==S_OK ? E_FAIL : locator->ret;
2021 if (hr != S_OK) break;
2023 if (dataRead != sizeof(data))
2025 ret = xmlParseChunk(locator->pParserCtxt, data, 0, 1);
2026 hr = ret!=XML_ERR_OK && locator->ret==S_OK ? E_FAIL : locator->ret;
2032 This->isParsing = FALSE;
2034 xmlFreeParserCtxt(locator->pParserCtxt);
2035 locator->pParserCtxt = NULL;
2036 ISAXLocator_Release(&locator->ISAXLocator_iface);
2040 static HRESULT internal_getEntityResolver(
2042 void *pEntityResolver,
2045 FIXME("(%p)->(%p) stub\n", This, pEntityResolver);
2049 static HRESULT internal_putEntityResolver(
2051 void *pEntityResolver,
2054 FIXME("(%p)->(%p) stub\n", This, pEntityResolver);
2058 static HRESULT internal_getContentHandler(
2060 void *pContentHandler,
2063 TRACE("(%p)->(%p)\n", This, pContentHandler);
2064 if(pContentHandler == NULL)
2066 if((vbInterface && This->vbcontentHandler)
2067 || (!vbInterface && This->contentHandler))
2070 IVBSAXContentHandler_AddRef(This->vbcontentHandler);
2072 ISAXContentHandler_AddRef(This->contentHandler);
2074 if(vbInterface) *(IVBSAXContentHandler**)pContentHandler =
2075 This->vbcontentHandler;
2076 else *(ISAXContentHandler**)pContentHandler = This->contentHandler;
2081 static HRESULT internal_putContentHandler(
2083 void *contentHandler,
2086 TRACE("(%p)->(%p)\n", This, contentHandler);
2090 IVBSAXContentHandler_AddRef((IVBSAXContentHandler*)contentHandler);
2092 ISAXContentHandler_AddRef((ISAXContentHandler*)contentHandler);
2094 if((vbInterface && This->vbcontentHandler)
2095 || (!vbInterface && This->contentHandler))
2098 IVBSAXContentHandler_Release(This->vbcontentHandler);
2100 ISAXContentHandler_Release(This->contentHandler);
2103 This->vbcontentHandler = contentHandler;
2105 This->contentHandler = contentHandler;
2110 static HRESULT internal_getDTDHandler(
2115 FIXME("(%p)->(%p) stub\n", This, pDTDHandler);
2119 static HRESULT internal_putDTDHandler(
2124 FIXME("(%p)->(%p) stub\n", This, pDTDHandler);
2128 static HRESULT internal_getErrorHandler(
2130 void *pErrorHandler,
2133 TRACE("(%p)->(%p)\n", This, pErrorHandler);
2134 if(pErrorHandler == NULL)
2137 if(vbInterface && This->vberrorHandler)
2138 IVBSAXErrorHandler_AddRef(This->vberrorHandler);
2139 else if(!vbInterface && This->errorHandler)
2140 ISAXErrorHandler_AddRef(This->errorHandler);
2143 *(IVBSAXErrorHandler**)pErrorHandler = This->vberrorHandler;
2145 *(ISAXErrorHandler**)pErrorHandler = This->errorHandler;
2151 static HRESULT internal_putErrorHandler(
2156 TRACE("(%p)->(%p)\n", This, errorHandler);
2160 IVBSAXErrorHandler_AddRef((IVBSAXErrorHandler*)errorHandler);
2162 ISAXErrorHandler_AddRef((ISAXErrorHandler*)errorHandler);
2165 if(vbInterface && This->vberrorHandler)
2166 IVBSAXErrorHandler_Release(This->vberrorHandler);
2167 else if(!vbInterface && This->errorHandler)
2168 ISAXErrorHandler_Release(This->errorHandler);
2171 This->vberrorHandler = errorHandler;
2173 This->errorHandler = errorHandler;
2179 static HRESULT internal_parse(
2186 TRACE("(%p)->(%s)\n", This, debugstr_variant(&varInput));
2188 /* Dispose of the BSTRs in the pool from a prior run, if any. */
2189 free_bstr_pool(&This->pool);
2191 switch(V_VT(&varInput))
2194 hr = internal_parseBuffer(This, (const char*)V_BSTR(&varInput),
2195 SysStringByteLen(V_BSTR(&varInput)), vbInterface);
2197 case VT_ARRAY|VT_UI1: {
2199 LONG lBound, uBound;
2202 hr = SafeArrayGetLBound(V_ARRAY(&varInput), 1, &lBound);
2203 if(hr != S_OK) break;
2204 hr = SafeArrayGetUBound(V_ARRAY(&varInput), 1, &uBound);
2205 if(hr != S_OK) break;
2206 dataRead = (uBound-lBound)*SafeArrayGetElemsize(V_ARRAY(&varInput));
2207 hr = SafeArrayAccessData(V_ARRAY(&varInput), &pSAData);
2208 if(hr != S_OK) break;
2209 hr = internal_parseBuffer(This, pSAData, dataRead, vbInterface);
2210 SafeArrayUnaccessData(V_ARRAY(&varInput));
2215 IPersistStream *persistStream;
2216 IStream *stream = NULL;
2217 IXMLDOMDocument *xmlDoc;
2219 if(IUnknown_QueryInterface(V_UNKNOWN(&varInput),
2220 &IID_IXMLDOMDocument, (void**)&xmlDoc) == S_OK)
2224 IXMLDOMDocument_get_xml(xmlDoc, &bstrData);
2225 hr = internal_parseBuffer(This, (const char*)bstrData,
2226 SysStringByteLen(bstrData), vbInterface);
2227 IXMLDOMDocument_Release(xmlDoc);
2228 SysFreeString(bstrData);
2232 if(IUnknown_QueryInterface(V_UNKNOWN(&varInput),
2233 &IID_IPersistStream, (void**)&persistStream) == S_OK)
2235 hr = CreateStreamOnHGlobal(NULL, TRUE, &stream);
2238 IPersistStream_Release(persistStream);
2242 hr = IPersistStream_Save(persistStream, stream, TRUE);
2243 IPersistStream_Release(persistStream);
2246 IStream_Release(stream);
2251 if(stream || IUnknown_QueryInterface(V_UNKNOWN(&varInput),
2252 &IID_IStream, (void**)&stream) == S_OK)
2254 hr = internal_parseStream(This, stream, vbInterface);
2255 IStream_Release(stream);
2260 WARN("vt %d not implemented\n", V_VT(&varInput));
2267 static HRESULT internal_vbonDataAvailable(void *obj, char *ptr, DWORD len)
2269 saxreader *This = obj;
2271 return internal_parseBuffer(This, ptr, len, TRUE);
2274 static HRESULT internal_onDataAvailable(void *obj, char *ptr, DWORD len)
2276 saxreader *This = obj;
2278 return internal_parseBuffer(This, ptr, len, FALSE);
2281 static HRESULT internal_parseURL(
2290 TRACE("(%p)->(%s)\n", This, debugstr_w(url));
2292 hr = create_moniker_from_url(url, &mon);
2296 if(vbInterface) hr = bind_url(mon, internal_vbonDataAvailable, This, &bsc);
2297 else hr = bind_url(mon, internal_onDataAvailable, This, &bsc);
2298 IMoniker_Release(mon);
2303 return detach_bsc(bsc);
2306 static HRESULT internal_putProperty(
2312 TRACE("(%p)->(%s %s)\n", This, debugstr_w(prop), debugstr_variant(&value));
2314 if(!memcmp(prop, PropertyDeclHandlerW, sizeof(PropertyDeclHandlerW)))
2316 if(This->isParsing) return E_FAIL;
2318 switch (V_VT(&value))
2323 if (This->vbdeclHandler)
2325 IVBSAXDeclHandler_Release(This->vbdeclHandler);
2326 This->vbdeclHandler = NULL;
2330 if (This->declHandler)
2332 ISAXDeclHandler_Release(This->declHandler);
2333 This->declHandler = NULL;
2337 if ((vbInterface && This->vbdeclHandler) ||
2338 (!vbInterface && This->declHandler))
2341 IVBSAXDeclHandler_Release(This->vbdeclHandler);
2343 ISAXDeclHandler_Release(This->declHandler);
2346 if (V_UNKNOWN(&value))
2348 return vbInterface ?
2349 IVBSAXDeclHandler_QueryInterface(V_UNKNOWN(&value), &IID_IVBSAXDeclHandler, (void**)&This->vbdeclHandler) :
2350 ISAXDeclHandler_QueryInterface(V_UNKNOWN(&value), &IID_ISAXDeclHandler, (void**)&This->declHandler);
2354 This->vbdeclHandler = NULL;
2355 This->declHandler = NULL;
2359 return E_INVALIDARG;
2365 if(!memcmp(prop, PropertyLexicalHandlerW, sizeof(PropertyLexicalHandlerW)))
2367 if(This->isParsing) return E_FAIL;
2369 switch (V_VT(&value))
2374 if (This->vblexicalHandler)
2376 IVBSAXLexicalHandler_Release(This->vblexicalHandler);
2377 This->vblexicalHandler = NULL;
2381 if (This->lexicalHandler)
2383 ISAXLexicalHandler_Release(This->lexicalHandler);
2384 This->lexicalHandler = NULL;
2388 if ((vbInterface && This->vblexicalHandler) ||
2389 (!vbInterface && This->lexicalHandler))
2392 IVBSAXLexicalHandler_Release(This->vblexicalHandler);
2394 ISAXLexicalHandler_Release(This->lexicalHandler);
2397 if (V_UNKNOWN(&value))
2399 return vbInterface ?
2400 IVBSAXLexicalHandler_QueryInterface(V_UNKNOWN(&value), &IID_IVBSAXLexicalHandler, (void**)&This->vblexicalHandler) :
2401 ISAXLexicalHandler_QueryInterface(V_UNKNOWN(&value), &IID_ISAXLexicalHandler, (void**)&This->lexicalHandler);
2405 This->vblexicalHandler = NULL;
2406 This->lexicalHandler = NULL;
2411 return E_INVALIDARG;
2417 if(!memcmp(prop, PropertyMaxXMLSizeW, sizeof(PropertyMaxXMLSizeW)))
2419 if (V_VT(&value) == VT_I4 && V_I4(&value) == 0) return S_OK;
2420 FIXME("(%p)->(%s): max-xml-size unsupported\n", This, debugstr_variant(&value));
2424 if(!memcmp(prop, PropertyMaxElementDepthW, sizeof(PropertyMaxElementDepthW)))
2426 if (V_VT(&value) == VT_I4 && V_I4(&value) == 0) return S_OK;
2427 FIXME("(%p)->(%s): max-element-depth unsupported\n", This, debugstr_variant(&value));
2431 FIXME("(%p)->(%s:%s): unsupported property\n", This, debugstr_w(prop), debugstr_variant(&value));
2433 if(!memcmp(prop, PropertyCharsetW, sizeof(PropertyCharsetW)))
2436 if(!memcmp(prop, PropertyDomNodeW, sizeof(PropertyDomNodeW)))
2439 if(!memcmp(prop, PropertyInputSourceW, sizeof(PropertyInputSourceW)))
2442 if(!memcmp(prop, PropertySchemaDeclHandlerW, sizeof(PropertySchemaDeclHandlerW)))
2445 if(!memcmp(prop, PropertyXMLDeclEncodingW, sizeof(PropertyXMLDeclEncodingW)))
2448 if(!memcmp(prop, PropertyXMLDeclStandaloneW, sizeof(PropertyXMLDeclStandaloneW)))
2451 if(!memcmp(prop, PropertyXMLDeclVersionW, sizeof(PropertyXMLDeclVersionW)))
2454 return E_INVALIDARG;
2457 static HRESULT internal_getProperty(const saxreader* This, const WCHAR *prop, VARIANT *value, BOOL vb)
2459 TRACE("(%p)->(%s)\n", This, debugstr_w(prop));
2461 if (!value) return E_POINTER;
2463 if (!memcmp(PropertyLexicalHandlerW, prop, sizeof(PropertyLexicalHandlerW)))
2465 V_VT(value) = VT_UNKNOWN;
2466 V_UNKNOWN(value) = vb ? (IUnknown*)This->vblexicalHandler : (IUnknown*)This->lexicalHandler;
2467 if (V_UNKNOWN(value)) IUnknown_AddRef(V_UNKNOWN(value));
2471 if (!memcmp(PropertyDeclHandlerW, prop, sizeof(PropertyDeclHandlerW)))
2473 V_VT(value) = VT_UNKNOWN;
2474 V_UNKNOWN(value) = vb ? (IUnknown*)This->vbdeclHandler : (IUnknown*)This->declHandler;
2475 if (V_UNKNOWN(value)) IUnknown_AddRef(V_UNKNOWN(value));
2479 FIXME("(%p)->(%s) unsupported property\n", This, debugstr_w(prop));
2484 /*** IVBSAXXMLReader interface ***/
2485 /*** IUnknown methods ***/
2486 static HRESULT WINAPI saxxmlreader_QueryInterface(IVBSAXXMLReader* iface, REFIID riid, void **ppvObject)
2488 saxreader *This = impl_from_IVBSAXXMLReader( iface );
2490 TRACE("(%p)->(%s %p)\n", This, debugstr_guid( riid ), ppvObject );
2494 if ( IsEqualGUID( riid, &IID_IUnknown ) ||
2495 IsEqualGUID( riid, &IID_IDispatch ) ||
2496 IsEqualGUID( riid, &IID_IVBSAXXMLReader ))
2500 else if( IsEqualGUID( riid, &IID_ISAXXMLReader ))
2502 *ppvObject = &This->ISAXXMLReader_iface;
2504 else if (dispex_query_interface(&This->dispex, riid, ppvObject))
2506 return *ppvObject ? S_OK : E_NOINTERFACE;
2510 FIXME("interface %s not implemented\n", debugstr_guid(riid));
2511 return E_NOINTERFACE;
2514 IVBSAXXMLReader_AddRef( iface );
2519 static ULONG WINAPI saxxmlreader_AddRef(IVBSAXXMLReader* iface)
2521 saxreader *This = impl_from_IVBSAXXMLReader( iface );
2522 TRACE("%p\n", This );
2523 return InterlockedIncrement( &This->ref );
2526 static ULONG WINAPI saxxmlreader_Release(
2527 IVBSAXXMLReader* iface)
2529 saxreader *This = impl_from_IVBSAXXMLReader( iface );
2532 TRACE("%p\n", This );
2534 ref = InterlockedDecrement( &This->ref );
2537 if(This->contentHandler)
2538 ISAXContentHandler_Release(This->contentHandler);
2540 if(This->vbcontentHandler)
2541 IVBSAXContentHandler_Release(This->vbcontentHandler);
2543 if(This->errorHandler)
2544 ISAXErrorHandler_Release(This->errorHandler);
2546 if(This->vberrorHandler)
2547 IVBSAXErrorHandler_Release(This->vberrorHandler);
2549 if(This->lexicalHandler)
2550 ISAXLexicalHandler_Release(This->lexicalHandler);
2552 if(This->vblexicalHandler)
2553 IVBSAXLexicalHandler_Release(This->vblexicalHandler);
2555 if(This->declHandler)
2556 ISAXDeclHandler_Release(This->declHandler);
2558 if(This->vbdeclHandler)
2559 IVBSAXDeclHandler_Release(This->vbdeclHandler);
2561 free_bstr_pool(&This->pool);
2563 release_dispex(&This->dispex);
2570 static HRESULT WINAPI saxxmlreader_GetTypeInfoCount( IVBSAXXMLReader *iface, UINT* pctinfo )
2572 saxreader *This = impl_from_IVBSAXXMLReader( iface );
2573 return IDispatchEx_GetTypeInfoCount(&This->dispex.IDispatchEx_iface, pctinfo);
2576 static HRESULT WINAPI saxxmlreader_GetTypeInfo(
2577 IVBSAXXMLReader *iface,
2578 UINT iTInfo, LCID lcid, ITypeInfo** ppTInfo )
2580 saxreader *This = impl_from_IVBSAXXMLReader( iface );
2581 return IDispatchEx_GetTypeInfo(&This->dispex.IDispatchEx_iface,
2582 iTInfo, lcid, ppTInfo);
2585 static HRESULT WINAPI saxxmlreader_GetIDsOfNames(
2586 IVBSAXXMLReader *iface,
2588 LPOLESTR* rgszNames,
2593 saxreader *This = impl_from_IVBSAXXMLReader( iface );
2594 return IDispatchEx_GetIDsOfNames(&This->dispex.IDispatchEx_iface,
2595 riid, rgszNames, cNames, lcid, rgDispId);
2598 static HRESULT WINAPI saxxmlreader_Invoke(
2599 IVBSAXXMLReader *iface,
2600 DISPID dispIdMember,
2604 DISPPARAMS* pDispParams,
2605 VARIANT* pVarResult,
2606 EXCEPINFO* pExcepInfo,
2609 saxreader *This = impl_from_IVBSAXXMLReader( iface );
2610 return IDispatchEx_Invoke(&This->dispex.IDispatchEx_iface,
2611 dispIdMember, riid, lcid, wFlags, pDispParams, pVarResult, pExcepInfo, puArgErr);
2614 /*** IVBSAXXMLReader methods ***/
2615 static HRESULT WINAPI saxxmlreader_getFeature(
2616 IVBSAXXMLReader* iface,
2617 const WCHAR *feature_name,
2618 VARIANT_BOOL *value)
2620 saxreader *This = impl_from_IVBSAXXMLReader( iface );
2621 saxreader_feature feature;
2623 TRACE("(%p)->(%s %p)\n", This, debugstr_w(feature_name), value);
2625 feature = get_saxreader_feature(feature_name);
2626 if (feature == Namespaces || feature == NamespacePrefixes)
2627 return get_feature_value(This, feature, value);
2629 FIXME("(%p)->(%s %p) stub\n", This, debugstr_w(feature_name), value);
2633 static HRESULT WINAPI saxxmlreader_putFeature(
2634 IVBSAXXMLReader* iface,
2635 const WCHAR *feature_name,
2638 saxreader *This = impl_from_IVBSAXXMLReader( iface );
2639 saxreader_feature feature;
2641 TRACE("(%p)->(%s %x)\n", This, debugstr_w(feature_name), value);
2643 feature = get_saxreader_feature(feature_name);
2645 /* accepted cases */
2646 if ((feature == ExternalGeneralEntities && value == VARIANT_FALSE) ||
2647 (feature == ExternalParameterEntities && value == VARIANT_FALSE) ||
2648 feature == Namespaces ||
2649 feature == NamespacePrefixes)
2651 return set_feature_value(This, feature, value);
2654 if (feature == LexicalHandlerParEntities || feature == ProhibitDTD)
2656 FIXME("(%p)->(%s %x) stub\n", This, debugstr_w(feature_name), value);
2657 return set_feature_value(This, feature, value);
2660 FIXME("(%p)->(%s %x) stub\n", This, debugstr_w(feature_name), value);
2664 static HRESULT WINAPI saxxmlreader_getProperty(
2665 IVBSAXXMLReader* iface,
2669 saxreader *This = impl_from_IVBSAXXMLReader( iface );
2670 return internal_getProperty(This, prop, value, TRUE);
2673 static HRESULT WINAPI saxxmlreader_putProperty(
2674 IVBSAXXMLReader* iface,
2678 saxreader *This = impl_from_IVBSAXXMLReader( iface );
2679 return internal_putProperty(This, pProp, value, TRUE);
2682 static HRESULT WINAPI saxxmlreader_get_entityResolver(
2683 IVBSAXXMLReader* iface,
2684 IVBSAXEntityResolver **pEntityResolver)
2686 saxreader *This = impl_from_IVBSAXXMLReader( iface );
2687 return internal_getEntityResolver(This, pEntityResolver, TRUE);
2690 static HRESULT WINAPI saxxmlreader_put_entityResolver(
2691 IVBSAXXMLReader* iface,
2692 IVBSAXEntityResolver *pEntityResolver)
2694 saxreader *This = impl_from_IVBSAXXMLReader( iface );
2695 return internal_putEntityResolver(This, pEntityResolver, TRUE);
2698 static HRESULT WINAPI saxxmlreader_get_contentHandler(
2699 IVBSAXXMLReader* iface,
2700 IVBSAXContentHandler **ppContentHandler)
2702 saxreader *This = impl_from_IVBSAXXMLReader( iface );
2703 return internal_getContentHandler(This, ppContentHandler, TRUE);
2706 static HRESULT WINAPI saxxmlreader_put_contentHandler(
2707 IVBSAXXMLReader* iface,
2708 IVBSAXContentHandler *contentHandler)
2710 saxreader *This = impl_from_IVBSAXXMLReader( iface );
2711 return internal_putContentHandler(This, contentHandler, TRUE);
2714 static HRESULT WINAPI saxxmlreader_get_dtdHandler(
2715 IVBSAXXMLReader* iface,
2716 IVBSAXDTDHandler **pDTDHandler)
2718 saxreader *This = impl_from_IVBSAXXMLReader( iface );
2719 return internal_getDTDHandler(This, pDTDHandler, TRUE);
2722 static HRESULT WINAPI saxxmlreader_put_dtdHandler(
2723 IVBSAXXMLReader* iface,
2724 IVBSAXDTDHandler *pDTDHandler)
2726 saxreader *This = impl_from_IVBSAXXMLReader( iface );
2727 return internal_putDTDHandler(This, pDTDHandler, TRUE);
2730 static HRESULT WINAPI saxxmlreader_get_errorHandler(
2731 IVBSAXXMLReader* iface,
2732 IVBSAXErrorHandler **pErrorHandler)
2734 saxreader *This = impl_from_IVBSAXXMLReader( iface );
2735 return internal_getErrorHandler(This, pErrorHandler, TRUE);
2738 static HRESULT WINAPI saxxmlreader_put_errorHandler(
2739 IVBSAXXMLReader* iface,
2740 IVBSAXErrorHandler *errorHandler)
2742 saxreader *This = impl_from_IVBSAXXMLReader( iface );
2743 return internal_putErrorHandler(This, errorHandler, TRUE);
2746 static HRESULT WINAPI saxxmlreader_get_baseURL(
2747 IVBSAXXMLReader* iface,
2748 const WCHAR **pBaseUrl)
2750 saxreader *This = impl_from_IVBSAXXMLReader( iface );
2752 FIXME("(%p)->(%p) stub\n", This, pBaseUrl);
2756 static HRESULT WINAPI saxxmlreader_put_baseURL(
2757 IVBSAXXMLReader* iface,
2758 const WCHAR *pBaseUrl)
2760 saxreader *This = impl_from_IVBSAXXMLReader( iface );
2762 FIXME("(%p)->(%s) stub\n", This, debugstr_w(pBaseUrl));
2766 static HRESULT WINAPI saxxmlreader_get_secureBaseURL(
2767 IVBSAXXMLReader* iface,
2768 const WCHAR **pSecureBaseUrl)
2770 saxreader *This = impl_from_IVBSAXXMLReader( iface );
2772 FIXME("(%p)->(%p) stub\n", This, pSecureBaseUrl);
2777 static HRESULT WINAPI saxxmlreader_put_secureBaseURL(
2778 IVBSAXXMLReader* iface,
2779 const WCHAR *secureBaseUrl)
2781 saxreader *This = impl_from_IVBSAXXMLReader( iface );
2783 FIXME("(%p)->(%s) stub\n", This, debugstr_w(secureBaseUrl));
2787 static HRESULT WINAPI saxxmlreader_parse(
2788 IVBSAXXMLReader* iface,
2791 saxreader *This = impl_from_IVBSAXXMLReader( iface );
2792 return internal_parse(This, varInput, TRUE);
2795 static HRESULT WINAPI saxxmlreader_parseURL(
2796 IVBSAXXMLReader* iface,
2799 saxreader *This = impl_from_IVBSAXXMLReader( iface );
2800 return internal_parseURL(This, url, TRUE);
2803 static const struct IVBSAXXMLReaderVtbl VBSAXXMLReaderVtbl =
2805 saxxmlreader_QueryInterface,
2806 saxxmlreader_AddRef,
2807 saxxmlreader_Release,
2808 saxxmlreader_GetTypeInfoCount,
2809 saxxmlreader_GetTypeInfo,
2810 saxxmlreader_GetIDsOfNames,
2811 saxxmlreader_Invoke,
2812 saxxmlreader_getFeature,
2813 saxxmlreader_putFeature,
2814 saxxmlreader_getProperty,
2815 saxxmlreader_putProperty,
2816 saxxmlreader_get_entityResolver,
2817 saxxmlreader_put_entityResolver,
2818 saxxmlreader_get_contentHandler,
2819 saxxmlreader_put_contentHandler,
2820 saxxmlreader_get_dtdHandler,
2821 saxxmlreader_put_dtdHandler,
2822 saxxmlreader_get_errorHandler,
2823 saxxmlreader_put_errorHandler,
2824 saxxmlreader_get_baseURL,
2825 saxxmlreader_put_baseURL,
2826 saxxmlreader_get_secureBaseURL,
2827 saxxmlreader_put_secureBaseURL,
2829 saxxmlreader_parseURL
2832 /*** ISAXXMLReader interface ***/
2833 /*** IUnknown methods ***/
2834 static HRESULT WINAPI isaxxmlreader_QueryInterface(ISAXXMLReader* iface, REFIID riid, void **ppvObject)
2836 saxreader *This = impl_from_ISAXXMLReader( iface );
2837 return saxxmlreader_QueryInterface(&This->IVBSAXXMLReader_iface, riid, ppvObject);
2840 static ULONG WINAPI isaxxmlreader_AddRef(ISAXXMLReader* iface)
2842 saxreader *This = impl_from_ISAXXMLReader( iface );
2843 return saxxmlreader_AddRef(&This->IVBSAXXMLReader_iface);
2846 static ULONG WINAPI isaxxmlreader_Release(ISAXXMLReader* iface)
2848 saxreader *This = impl_from_ISAXXMLReader( iface );
2849 return saxxmlreader_Release(&This->IVBSAXXMLReader_iface);
2852 /*** ISAXXMLReader methods ***/
2853 static HRESULT WINAPI isaxxmlreader_getFeature(
2854 ISAXXMLReader* iface,
2855 const WCHAR *pFeature,
2856 VARIANT_BOOL *pValue)
2858 saxreader *This = impl_from_ISAXXMLReader( iface );
2859 return IVBSAXXMLReader_getFeature(&This->IVBSAXXMLReader_iface, pFeature, pValue);
2862 static HRESULT WINAPI isaxxmlreader_putFeature(
2863 ISAXXMLReader* iface,
2864 const WCHAR *pFeature,
2865 VARIANT_BOOL vfValue)
2867 saxreader *This = impl_from_ISAXXMLReader( iface );
2868 return IVBSAXXMLReader_putFeature(&This->IVBSAXXMLReader_iface, pFeature, vfValue);
2871 static HRESULT WINAPI isaxxmlreader_getProperty(
2872 ISAXXMLReader* iface,
2876 saxreader *This = impl_from_ISAXXMLReader( iface );
2877 return internal_getProperty(This, prop, value, FALSE);
2880 static HRESULT WINAPI isaxxmlreader_putProperty(
2881 ISAXXMLReader* iface,
2885 saxreader *This = impl_from_ISAXXMLReader( iface );
2886 return internal_putProperty(This, pProp, value, FALSE);
2889 static HRESULT WINAPI isaxxmlreader_getEntityResolver(
2890 ISAXXMLReader* iface,
2891 ISAXEntityResolver **ppEntityResolver)
2893 saxreader *This = impl_from_ISAXXMLReader( iface );
2894 return internal_getEntityResolver(This, ppEntityResolver, FALSE);
2897 static HRESULT WINAPI isaxxmlreader_putEntityResolver(
2898 ISAXXMLReader* iface,
2899 ISAXEntityResolver *pEntityResolver)
2901 saxreader *This = impl_from_ISAXXMLReader( iface );
2902 return internal_putEntityResolver(This, pEntityResolver, FALSE);
2905 static HRESULT WINAPI isaxxmlreader_getContentHandler(
2906 ISAXXMLReader* iface,
2907 ISAXContentHandler **pContentHandler)
2909 saxreader *This = impl_from_ISAXXMLReader( iface );
2910 return internal_getContentHandler(This, pContentHandler, FALSE);
2913 static HRESULT WINAPI isaxxmlreader_putContentHandler(
2914 ISAXXMLReader* iface,
2915 ISAXContentHandler *contentHandler)
2917 saxreader *This = impl_from_ISAXXMLReader( iface );
2918 return internal_putContentHandler(This, contentHandler, FALSE);
2921 static HRESULT WINAPI isaxxmlreader_getDTDHandler(
2922 ISAXXMLReader* iface,
2923 ISAXDTDHandler **pDTDHandler)
2925 saxreader *This = impl_from_ISAXXMLReader( iface );
2926 return internal_getDTDHandler(This, pDTDHandler, FALSE);
2929 static HRESULT WINAPI isaxxmlreader_putDTDHandler(
2930 ISAXXMLReader* iface,
2931 ISAXDTDHandler *pDTDHandler)
2933 saxreader *This = impl_from_ISAXXMLReader( iface );
2934 return internal_putDTDHandler(This, pDTDHandler, FALSE);
2937 static HRESULT WINAPI isaxxmlreader_getErrorHandler(
2938 ISAXXMLReader* iface,
2939 ISAXErrorHandler **pErrorHandler)
2941 saxreader *This = impl_from_ISAXXMLReader( iface );
2942 return internal_getErrorHandler(This, pErrorHandler, FALSE);
2945 static HRESULT WINAPI isaxxmlreader_putErrorHandler(
2946 ISAXXMLReader* iface,
2947 ISAXErrorHandler *errorHandler)
2949 saxreader *This = impl_from_ISAXXMLReader( iface );
2950 return internal_putErrorHandler(This, errorHandler, FALSE);
2953 static HRESULT WINAPI isaxxmlreader_getBaseURL(
2954 ISAXXMLReader* iface,
2955 const WCHAR **pBaseUrl)
2957 saxreader *This = impl_from_ISAXXMLReader( iface );
2958 return IVBSAXXMLReader_get_baseURL(&This->IVBSAXXMLReader_iface, pBaseUrl);
2961 static HRESULT WINAPI isaxxmlreader_putBaseURL(
2962 ISAXXMLReader* iface,
2963 const WCHAR *pBaseUrl)
2965 saxreader *This = impl_from_ISAXXMLReader( iface );
2966 return IVBSAXXMLReader_put_baseURL(&This->IVBSAXXMLReader_iface, pBaseUrl);
2969 static HRESULT WINAPI isaxxmlreader_getSecureBaseURL(
2970 ISAXXMLReader* iface,
2971 const WCHAR **pSecureBaseUrl)
2973 saxreader *This = impl_from_ISAXXMLReader( iface );
2974 return IVBSAXXMLReader_get_secureBaseURL(&This->IVBSAXXMLReader_iface, pSecureBaseUrl);
2977 static HRESULT WINAPI isaxxmlreader_putSecureBaseURL(
2978 ISAXXMLReader* iface,
2979 const WCHAR *secureBaseUrl)
2981 saxreader *This = impl_from_ISAXXMLReader( iface );
2982 return IVBSAXXMLReader_put_secureBaseURL(&This->IVBSAXXMLReader_iface, secureBaseUrl);
2985 static HRESULT WINAPI isaxxmlreader_parse(
2986 ISAXXMLReader* iface,
2989 saxreader *This = impl_from_ISAXXMLReader( iface );
2990 return internal_parse(This, varInput, FALSE);
2993 static HRESULT WINAPI isaxxmlreader_parseURL(
2994 ISAXXMLReader* iface,
2997 saxreader *This = impl_from_ISAXXMLReader( iface );
2998 return internal_parseURL(This, url, FALSE);
3001 static const struct ISAXXMLReaderVtbl SAXXMLReaderVtbl =
3003 isaxxmlreader_QueryInterface,
3004 isaxxmlreader_AddRef,
3005 isaxxmlreader_Release,
3006 isaxxmlreader_getFeature,
3007 isaxxmlreader_putFeature,
3008 isaxxmlreader_getProperty,
3009 isaxxmlreader_putProperty,
3010 isaxxmlreader_getEntityResolver,
3011 isaxxmlreader_putEntityResolver,
3012 isaxxmlreader_getContentHandler,
3013 isaxxmlreader_putContentHandler,
3014 isaxxmlreader_getDTDHandler,
3015 isaxxmlreader_putDTDHandler,
3016 isaxxmlreader_getErrorHandler,
3017 isaxxmlreader_putErrorHandler,
3018 isaxxmlreader_getBaseURL,
3019 isaxxmlreader_putBaseURL,
3020 isaxxmlreader_getSecureBaseURL,
3021 isaxxmlreader_putSecureBaseURL,
3022 isaxxmlreader_parse,
3023 isaxxmlreader_parseURL
3026 static const tid_t saxreader_iface_tids[] = {
3027 IVBSAXXMLReader_tid,
3030 static dispex_static_data_t saxreader_dispex = {
3032 IVBSAXXMLReader_tid,
3034 saxreader_iface_tids
3037 HRESULT SAXXMLReader_create(MSXML_VERSION version, IUnknown *outer, LPVOID *ppObj)
3041 TRACE("(%p, %p)\n", outer, ppObj);
3043 reader = heap_alloc( sizeof (*reader) );
3045 return E_OUTOFMEMORY;
3047 reader->IVBSAXXMLReader_iface.lpVtbl = &VBSAXXMLReaderVtbl;
3048 reader->ISAXXMLReader_iface.lpVtbl = &SAXXMLReaderVtbl;
3050 reader->contentHandler = NULL;
3051 reader->vbcontentHandler = NULL;
3052 reader->errorHandler = NULL;
3053 reader->vberrorHandler = NULL;
3054 reader->lexicalHandler = NULL;
3055 reader->vblexicalHandler = NULL;
3056 reader->declHandler = NULL;
3057 reader->vbdeclHandler = NULL;
3058 reader->isParsing = FALSE;
3059 reader->pool.pool = NULL;
3060 reader->pool.index = 0;
3061 reader->pool.len = 0;
3062 reader->features = Namespaces | NamespacePrefixes;
3063 reader->version = version;
3065 init_dispex(&reader->dispex, (IUnknown*)&reader->IVBSAXXMLReader_iface, &saxreader_dispex);
3067 memset(&reader->sax, 0, sizeof(xmlSAXHandler));
3068 reader->sax.initialized = XML_SAX2_MAGIC;
3069 reader->sax.startDocument = libxmlStartDocument;
3070 reader->sax.endDocument = libxmlEndDocument;
3071 reader->sax.startElementNs = libxmlStartElementNS;
3072 reader->sax.endElementNs = libxmlEndElementNS;
3073 reader->sax.characters = libxmlCharacters;
3074 reader->sax.setDocumentLocator = libxmlSetDocumentLocator;
3075 reader->sax.comment = libxmlComment;
3076 reader->sax.error = libxmlFatalError;
3077 reader->sax.fatalError = libxmlFatalError;
3078 reader->sax.cdataBlock = libxmlCDataBlock;
3080 *ppObj = &reader->IVBSAXXMLReader_iface;
3082 TRACE("returning iface %p\n", *ppObj);
3089 HRESULT SAXXMLReader_create(MSXML_VERSION version, IUnknown *pUnkOuter, LPVOID *ppObj)
3091 MESSAGE("This program tried to use a SAX XML Reader object, but\n"
3092 "libxml2 support was not present at compile time.\n");