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 */
168 SAXContentHandler
= 0,
177 struct saxanyhandler_iface
183 struct saxcontenthandler_iface
185 ISAXContentHandler
*handler
;
186 IVBSAXContentHandler
*vbhandler
;
189 struct saxerrorhandler_iface
191 ISAXErrorHandler
*handler
;
192 IVBSAXErrorHandler
*vbhandler
;
195 struct saxlexicalhandler_iface
197 ISAXLexicalHandler
*handler
;
198 IVBSAXLexicalHandler
*vbhandler
;
201 struct saxentityresolver_iface
203 ISAXEntityResolver
*handler
;
204 IVBSAXEntityResolver
*vbhandler
;
207 struct saxhandler_iface
210 struct saxcontenthandler_iface content
;
211 struct saxentityresolver_iface entityresolver
;
212 struct saxerrorhandler_iface error
;
213 struct saxlexicalhandler_iface lexical
;
214 struct saxanyhandler_iface anyhandler
;
221 IVBSAXXMLReader IVBSAXXMLReader_iface
;
222 ISAXXMLReader ISAXXMLReader_iface
;
225 struct saxhandler_iface saxhandlers
[SAXHandler_Last
];
228 struct bstrpool pool
;
229 saxreader_feature features
;
230 BSTR xmldecl_version
;
231 MSXML_VERSION version
;
234 static HRESULT
saxreader_put_handler(saxreader
*reader
, enum saxhandler_type type
, void *ptr
, BOOL vb
)
236 struct saxanyhandler_iface
*iface
= &reader
->saxhandlers
[type
].u
.anyhandler
;
237 IUnknown
*unk
= (IUnknown
*)ptr
;
240 IUnknown_AddRef(unk
);
242 if ((vb
&& iface
->vbhandler
) || (!vb
&& iface
->handler
))
243 IUnknown_Release(vb
? iface
->vbhandler
: iface
->handler
);
246 iface
->vbhandler
= unk
;
248 iface
->handler
= unk
;
253 static HRESULT
saxreader_get_handler(const saxreader
*reader
, enum saxhandler_type type
, BOOL vb
, void **ret
)
255 const struct saxanyhandler_iface
*iface
= &reader
->saxhandlers
[type
].u
.anyhandler
;
257 if (!ret
) return E_POINTER
;
259 if ((vb
&& iface
->vbhandler
) || (!vb
&& iface
->handler
))
262 IUnknown_AddRef(iface
->vbhandler
);
264 IUnknown_AddRef(iface
->handler
);
267 *ret
= vb
? iface
->vbhandler
: iface
->handler
;
272 static struct saxcontenthandler_iface
*saxreader_get_contenthandler(saxreader
*reader
)
274 return &reader
->saxhandlers
[SAXContentHandler
].u
.content
;
277 static struct saxerrorhandler_iface
*saxreader_get_errorhandler(saxreader
*reader
)
279 return &reader
->saxhandlers
[SAXErrorHandler
].u
.error
;
282 static struct saxlexicalhandler_iface
*saxreader_get_lexicalhandler(saxreader
*reader
)
284 return &reader
->saxhandlers
[SAXLexicalHandler
].u
.lexical
;
289 IVBSAXLocator IVBSAXLocator_iface
;
290 ISAXLocator ISAXLocator_iface
;
291 IVBSAXAttributes IVBSAXAttributes_iface
;
292 ISAXAttributes ISAXAttributes_iface
;
294 saxreader
*saxreader
;
296 xmlParserCtxtPtr pParserCtxt
;
302 struct list elements
;
316 static inline saxreader
*impl_from_IVBSAXXMLReader( IVBSAXXMLReader
*iface
)
318 return CONTAINING_RECORD(iface
, saxreader
, IVBSAXXMLReader_iface
);
321 static inline saxreader
*impl_from_ISAXXMLReader( ISAXXMLReader
*iface
)
323 return CONTAINING_RECORD(iface
, saxreader
, ISAXXMLReader_iface
);
326 static inline saxlocator
*impl_from_IVBSAXLocator( IVBSAXLocator
*iface
)
328 return CONTAINING_RECORD(iface
, saxlocator
, IVBSAXLocator_iface
);
331 static inline saxlocator
*impl_from_ISAXLocator( ISAXLocator
*iface
)
333 return CONTAINING_RECORD(iface
, saxlocator
, ISAXLocator_iface
);
336 static inline saxlocator
*impl_from_IVBSAXAttributes( IVBSAXAttributes
*iface
)
338 return CONTAINING_RECORD(iface
, saxlocator
, IVBSAXAttributes_iface
);
341 static inline saxlocator
*impl_from_ISAXAttributes( ISAXAttributes
*iface
)
343 return CONTAINING_RECORD(iface
, saxlocator
, ISAXAttributes_iface
);
346 static inline BOOL
saxreader_has_handler(const saxlocator
*locator
, enum saxhandler_type type
)
348 struct saxanyhandler_iface
*iface
= &locator
->saxreader
->saxhandlers
[type
].u
.anyhandler
;
349 return (locator
->vbInterface
&& iface
->vbhandler
) || (!locator
->vbInterface
&& iface
->handler
);
352 static HRESULT
saxreader_saxcharacters(saxlocator
*locator
, BSTR chars
)
354 struct saxcontenthandler_iface
*content
= saxreader_get_contenthandler(locator
->saxreader
);
357 if (!saxreader_has_handler(locator
, SAXContentHandler
)) return S_OK
;
359 if (locator
->vbInterface
)
360 hr
= IVBSAXContentHandler_characters(content
->vbhandler
, &chars
);
362 hr
= ISAXContentHandler_characters(content
->handler
, chars
, SysStringLen(chars
));
368 static const WCHAR PropertyCharsetW
[] = {
369 'c','h','a','r','s','e','t',0
371 static const WCHAR PropertyXmlDeclVersionW
[] = {
372 'x','m','l','d','e','c','l','-','v','e','r','s','i','o','n',0
374 static const WCHAR PropertyDeclHandlerW
[] = {
375 'h','t','t','p',':','/','/','x','m','l','.','o','r','g','/',
376 's','a','x','/','p','r','o','p','e','r','t','i','e','s','/',
377 'd','e','c','l','a','r','a','t','i','o','n',
378 '-','h','a','n','d','l','e','r',0
380 static const WCHAR PropertyDomNodeW
[] = {
381 'h','t','t','p',':','/','/','x','m','l','.','o','r','g','/',
382 's','a','x','/','p','r','o','p','e','r','t','i','e','s','/',
383 'd','o','m','-','n','o','d','e',0
385 static const WCHAR PropertyInputSourceW
[] = {
386 'i','n','p','u','t','-','s','o','u','r','c','e',0
388 static const WCHAR PropertyLexicalHandlerW
[] = {
389 'h','t','t','p',':','/','/','x','m','l','.','o','r','g','/',
390 's','a','x','/','p','r','o','p','e','r','t','i','e','s','/',
391 'l','e','x','i','c','a','l','-','h','a','n','d','l','e','r',0
393 static const WCHAR PropertyMaxElementDepthW
[] = {
394 'm','a','x','-','e','l','e','m','e','n','t','-','d','e','p','t','h',0
396 static const WCHAR PropertyMaxXMLSizeW
[] = {
397 'm','a','x','-','x','m','l','-','s','i','z','e',0
399 static const WCHAR PropertySchemaDeclHandlerW
[] = {
400 's','c','h','e','m','a','-','d','e','c','l','a','r','a','t','i','o','n','-',
401 'h','a','n','d','l','e','r',0
403 static const WCHAR PropertyXMLDeclEncodingW
[] = {
404 'x','m','l','d','e','c','l','-','e','n','c','o','d','i','n','g',0
406 static const WCHAR PropertyXMLDeclStandaloneW
[] = {
407 'x','m','l','d','e','c','l','-','s','t','a','n','d','a','l','o','n','e',0
409 static const WCHAR PropertyXMLDeclVersionW
[] = {
410 'x','m','l','d','e','c','l','-','v','e','r','s','i','o','n',0
413 static inline HRESULT
set_feature_value(saxreader
*reader
, saxreader_feature feature
, VARIANT_BOOL value
)
415 /* handling of non-VARIANT_* values is version dependent */
416 if ((reader
->version
< MSXML4
) && (value
!= VARIANT_TRUE
))
417 value
= VARIANT_FALSE
;
418 if ((reader
->version
>= MSXML4
) && (value
!= VARIANT_FALSE
))
419 value
= VARIANT_TRUE
;
421 if (value
== VARIANT_TRUE
)
422 reader
->features
|= feature
;
424 reader
->features
&= ~feature
;
429 static inline HRESULT
get_feature_value(const saxreader
*reader
, saxreader_feature feature
, VARIANT_BOOL
*value
)
431 *value
= reader
->features
& feature
? VARIANT_TRUE
: VARIANT_FALSE
;
435 static BOOL
is_namespaces_enabled(const saxreader
*reader
)
437 return (reader
->version
< MSXML4
) || (reader
->features
& Namespaces
);
440 static BSTR
build_qname(BSTR prefix
, BSTR local
)
442 if (prefix
&& *prefix
)
444 BSTR qname
= SysAllocStringLen(NULL
, SysStringLen(prefix
) + SysStringLen(local
) + 1);
448 strcpyW(ptr
, prefix
);
449 ptr
+= SysStringLen(prefix
);
455 return SysAllocString(local
);
458 static element_entry
* alloc_element_entry(const xmlChar
*local
, const xmlChar
*prefix
, int nb_ns
,
459 const xmlChar
**namespaces
)
464 ret
= heap_alloc(sizeof(*ret
));
465 if (!ret
) return ret
;
467 ret
->local
= bstr_from_xmlChar(local
);
468 ret
->prefix
= bstr_from_xmlChar(prefix
);
469 ret
->qname
= build_qname(ret
->prefix
, ret
->local
);
470 ret
->ns
= nb_ns
? heap_alloc(nb_ns
*sizeof(ns
)) : NULL
;
471 ret
->ns_count
= nb_ns
;
473 for (i
=0; i
< nb_ns
; i
++)
475 ret
->ns
[i
].prefix
= bstr_from_xmlChar(namespaces
[2*i
]);
476 ret
->ns
[i
].uri
= bstr_from_xmlChar(namespaces
[2*i
+1]);
482 static void free_element_entry(element_entry
*element
)
486 for (i
=0; i
<element
->ns_count
;i
++)
488 SysFreeString(element
->ns
[i
].prefix
);
489 SysFreeString(element
->ns
[i
].uri
);
492 SysFreeString(element
->prefix
);
493 SysFreeString(element
->local
);
495 heap_free(element
->ns
);
499 static void push_element_ns(saxlocator
*locator
, element_entry
*element
)
501 list_add_head(&locator
->elements
, &element
->entry
);
504 static element_entry
* pop_element_ns(saxlocator
*locator
)
506 element_entry
*element
= LIST_ENTRY(list_head(&locator
->elements
), element_entry
, entry
);
509 list_remove(&element
->entry
);
514 static BSTR
find_element_uri(saxlocator
*locator
, const xmlChar
*uri
)
516 element_entry
*element
;
520 if (!uri
) return NULL
;
522 uriW
= bstr_from_xmlChar(uri
);
524 LIST_FOR_EACH_ENTRY(element
, &locator
->elements
, element_entry
, entry
)
526 for (i
=0; i
< element
->ns_count
; i
++)
527 if (!strcmpW(uriW
, element
->ns
[i
].uri
))
530 return element
->ns
[i
].uri
;
535 ERR("namespace uri not found, %s\n", debugstr_a((char*)uri
));
539 /* used to localize version dependent error check behaviour */
540 static inline BOOL
sax_callback_failed(saxlocator
*This
, HRESULT hr
)
542 return This
->saxreader
->version
>= MSXML4
? FAILED(hr
) : hr
!= S_OK
;
545 /* index value -1 means it tries to loop for a first time */
546 static inline BOOL
iterate_endprefix_index(saxlocator
*This
, const element_entry
*element
, int *i
)
548 if (This
->saxreader
->version
>= MSXML4
)
550 if (*i
== -1) *i
= 0; else ++*i
;
551 return *i
< element
->ns_count
;
555 if (*i
== -1) *i
= element
->ns_count
-1; else --*i
;
560 static BOOL
bstr_pool_insert(struct bstrpool
*pool
, BSTR pool_entry
)
564 pool
->pool
= HeapAlloc(GetProcessHeap(), 0, 16 * sizeof(*pool
->pool
));
571 else if (pool
->index
== pool
->len
)
573 BSTR
*realloc
= HeapReAlloc(GetProcessHeap(), 0, pool
->pool
, pool
->len
* 2 * sizeof(*realloc
));
578 pool
->pool
= realloc
;
582 pool
->pool
[pool
->index
++] = pool_entry
;
586 static void free_bstr_pool(struct bstrpool
*pool
)
590 for (i
= 0; i
< pool
->index
; i
++)
591 SysFreeString(pool
->pool
[i
]);
593 HeapFree(GetProcessHeap(), 0, pool
->pool
);
596 pool
->index
= pool
->len
= 0;
599 static BSTR
bstr_from_xmlCharN(const xmlChar
*buf
, int len
)
607 dLen
= MultiByteToWideChar(CP_UTF8
, 0, (LPCSTR
)buf
, len
, NULL
, 0);
608 if(len
!= -1) dLen
++;
609 bstr
= SysAllocStringLen(NULL
, dLen
-1);
612 MultiByteToWideChar(CP_UTF8
, 0, (LPCSTR
)buf
, len
, bstr
, dLen
);
613 if(len
!= -1) bstr
[dLen
-1] = '\0';
618 static BSTR
QName_from_xmlChar(const xmlChar
*prefix
, const xmlChar
*name
)
623 if(!name
) return NULL
;
625 if(!prefix
|| !*prefix
)
626 return bstr_from_xmlChar(name
);
628 qname
= xmlBuildQName(name
, prefix
, NULL
, 0);
629 bstr
= bstr_from_xmlChar(qname
);
635 static BSTR
pooled_bstr_from_xmlChar(struct bstrpool
*pool
, const xmlChar
*buf
)
637 BSTR pool_entry
= bstr_from_xmlChar(buf
);
639 if (pool_entry
&& !bstr_pool_insert(pool
, pool_entry
))
641 SysFreeString(pool_entry
);
648 static BSTR
pooled_bstr_from_xmlCharN(struct bstrpool
*pool
, const xmlChar
*buf
, int len
)
650 BSTR pool_entry
= bstr_from_xmlCharN(buf
, len
);
652 if (pool_entry
&& !bstr_pool_insert(pool
, pool_entry
))
654 SysFreeString(pool_entry
);
661 static void format_error_message_from_id(saxlocator
*This
, HRESULT hr
)
663 struct saxerrorhandler_iface
*handler
= saxreader_get_errorhandler(This
->saxreader
);
664 xmlStopParser(This
->pParserCtxt
);
667 if (saxreader_has_handler(This
, SAXErrorHandler
))
670 if(!FormatMessageW(FORMAT_MESSAGE_FROM_SYSTEM
,
671 NULL
, hr
, 0, msg
, sizeof(msg
), NULL
))
673 FIXME("MSXML errors not yet supported.\n");
677 if(This
->vbInterface
)
679 BSTR bstrMsg
= SysAllocString(msg
);
680 IVBSAXErrorHandler_fatalError(handler
->vbhandler
,
681 &This
->IVBSAXLocator_iface
, &bstrMsg
, hr
);
682 SysFreeString(bstrMsg
);
685 ISAXErrorHandler_fatalError(handler
->handler
,
686 &This
->ISAXLocator_iface
, msg
, hr
);
690 static void update_position(saxlocator
*This
, BOOL fix_column
)
692 const xmlChar
*p
= This
->pParserCtxt
->input
->cur
-1;
694 This
->line
= xmlSAX2GetLineNumber(This
->pParserCtxt
);
698 for(; *p
!='\n' && *p
!='\r' && p
>=This
->pParserCtxt
->input
->base
; p
--)
703 This
->column
= xmlSAX2GetColumnNumber(This
->pParserCtxt
);
707 /*** IVBSAXAttributes interface ***/
708 /*** IUnknown methods ***/
709 static HRESULT WINAPI
ivbsaxattributes_QueryInterface(
710 IVBSAXAttributes
* iface
,
714 saxlocator
*This
= impl_from_IVBSAXAttributes(iface
);
715 TRACE("%p %s %p\n", This
, debugstr_guid(riid
), ppvObject
);
716 return IVBSAXLocator_QueryInterface(&This
->IVBSAXLocator_iface
, riid
, ppvObject
);
719 static ULONG WINAPI
ivbsaxattributes_AddRef(IVBSAXAttributes
* iface
)
721 saxlocator
*This
= impl_from_IVBSAXAttributes(iface
);
722 return ISAXLocator_AddRef(&This
->ISAXLocator_iface
);
725 static ULONG WINAPI
ivbsaxattributes_Release(IVBSAXAttributes
* iface
)
727 saxlocator
*This
= impl_from_IVBSAXAttributes(iface
);
728 return ISAXLocator_Release(&This
->ISAXLocator_iface
);
731 /*** IDispatch methods ***/
732 static HRESULT WINAPI
ivbsaxattributes_GetTypeInfoCount( IVBSAXAttributes
*iface
, UINT
* pctinfo
)
734 saxlocator
*This
= impl_from_IVBSAXAttributes( iface
);
736 TRACE("(%p)->(%p)\n", This
, pctinfo
);
743 static HRESULT WINAPI
ivbsaxattributes_GetTypeInfo(
744 IVBSAXAttributes
*iface
,
745 UINT iTInfo
, LCID lcid
, ITypeInfo
** ppTInfo
)
747 saxlocator
*This
= impl_from_IVBSAXAttributes( iface
);
750 TRACE("(%p)->(%u %u %p)\n", This
, iTInfo
, lcid
, ppTInfo
);
752 hr
= get_typeinfo(IVBSAXAttributes_tid
, ppTInfo
);
757 static HRESULT WINAPI
ivbsaxattributes_GetIDsOfNames(
758 IVBSAXAttributes
*iface
,
765 saxlocator
*This
= impl_from_IVBSAXAttributes( iface
);
769 TRACE("(%p)->(%s %p %u %u %p)\n", This
, debugstr_guid(riid
), rgszNames
, cNames
,
772 if(!rgszNames
|| cNames
== 0 || !rgDispId
)
775 hr
= get_typeinfo(IVBSAXAttributes_tid
, &typeinfo
);
778 hr
= ITypeInfo_GetIDsOfNames(typeinfo
, rgszNames
, cNames
, rgDispId
);
779 ITypeInfo_Release(typeinfo
);
785 static HRESULT WINAPI
ivbsaxattributes_Invoke(
786 IVBSAXAttributes
*iface
,
791 DISPPARAMS
* pDispParams
,
793 EXCEPINFO
* pExcepInfo
,
796 saxlocator
*This
= impl_from_IVBSAXAttributes( iface
);
800 TRACE("(%p)->(%d %s %d %d %p %p %p %p)\n", This
, dispIdMember
, debugstr_guid(riid
),
801 lcid
, wFlags
, pDispParams
, pVarResult
, pExcepInfo
, puArgErr
);
803 hr
= get_typeinfo(IVBSAXAttributes_tid
, &typeinfo
);
806 hr
= ITypeInfo_Invoke(typeinfo
, &This
->IVBSAXAttributes_iface
, dispIdMember
, wFlags
,
807 pDispParams
, pVarResult
, pExcepInfo
, puArgErr
);
808 ITypeInfo_Release(typeinfo
);
814 /*** IVBSAXAttributes methods ***/
815 static HRESULT WINAPI
ivbsaxattributes_get_length(
816 IVBSAXAttributes
* iface
,
819 saxlocator
*This
= impl_from_IVBSAXAttributes( iface
);
820 return ISAXAttributes_getLength(&This
->ISAXAttributes_iface
, nLength
);
823 static HRESULT WINAPI
ivbsaxattributes_getURI(
824 IVBSAXAttributes
* iface
,
829 saxlocator
*This
= impl_from_IVBSAXAttributes( iface
);
830 return ISAXAttributes_getURI(&This
->ISAXAttributes_iface
, nIndex
, (const WCHAR
**)uri
, &len
);
833 static HRESULT WINAPI
ivbsaxattributes_getLocalName(
834 IVBSAXAttributes
* iface
,
839 saxlocator
*This
= impl_from_IVBSAXAttributes( iface
);
840 return ISAXAttributes_getLocalName(&This
->ISAXAttributes_iface
, nIndex
,
841 (const WCHAR
**)localName
, &len
);
844 static HRESULT WINAPI
ivbsaxattributes_getQName(
845 IVBSAXAttributes
* iface
,
850 saxlocator
*This
= impl_from_IVBSAXAttributes( iface
);
851 return ISAXAttributes_getQName(&This
->ISAXAttributes_iface
, nIndex
, (const WCHAR
**)QName
, &len
);
854 static HRESULT WINAPI
ivbsaxattributes_getIndexFromName(
855 IVBSAXAttributes
* iface
,
860 saxlocator
*This
= impl_from_IVBSAXAttributes( iface
);
861 return ISAXAttributes_getIndexFromName(&This
->ISAXAttributes_iface
, uri
, SysStringLen(uri
),
862 localName
, SysStringLen(localName
), index
);
865 static HRESULT WINAPI
ivbsaxattributes_getIndexFromQName(
866 IVBSAXAttributes
* iface
,
870 saxlocator
*This
= impl_from_IVBSAXAttributes( iface
);
871 return ISAXAttributes_getIndexFromQName(&This
->ISAXAttributes_iface
, QName
,
872 SysStringLen(QName
), index
);
875 static HRESULT WINAPI
ivbsaxattributes_getType(
876 IVBSAXAttributes
* iface
,
881 saxlocator
*This
= impl_from_IVBSAXAttributes( iface
);
882 return ISAXAttributes_getType(&This
->ISAXAttributes_iface
, nIndex
, (const WCHAR
**)type
, &len
);
885 static HRESULT WINAPI
ivbsaxattributes_getTypeFromName(
886 IVBSAXAttributes
* iface
,
892 saxlocator
*This
= impl_from_IVBSAXAttributes( iface
);
893 return ISAXAttributes_getTypeFromName(&This
->ISAXAttributes_iface
, uri
, SysStringLen(uri
),
894 localName
, SysStringLen(localName
), (const WCHAR
**)type
, &len
);
897 static HRESULT WINAPI
ivbsaxattributes_getTypeFromQName(
898 IVBSAXAttributes
* iface
,
903 saxlocator
*This
= impl_from_IVBSAXAttributes( iface
);
904 return ISAXAttributes_getTypeFromQName(&This
->ISAXAttributes_iface
, QName
, SysStringLen(QName
),
905 (const WCHAR
**)type
, &len
);
908 static HRESULT WINAPI
ivbsaxattributes_getValue(
909 IVBSAXAttributes
* iface
,
914 saxlocator
*This
= impl_from_IVBSAXAttributes( iface
);
915 return ISAXAttributes_getValue(&This
->ISAXAttributes_iface
, nIndex
, (const WCHAR
**)value
, &len
);
918 static HRESULT WINAPI
ivbsaxattributes_getValueFromName(
919 IVBSAXAttributes
* iface
,
925 saxlocator
*This
= impl_from_IVBSAXAttributes( iface
);
926 return ISAXAttributes_getValueFromName(&This
->ISAXAttributes_iface
, uri
, SysStringLen(uri
),
927 localName
, SysStringLen(localName
), (const WCHAR
**)value
, &len
);
930 static HRESULT WINAPI
ivbsaxattributes_getValueFromQName(
931 IVBSAXAttributes
* iface
,
936 saxlocator
*This
= impl_from_IVBSAXAttributes( iface
);
937 return ISAXAttributes_getValueFromQName(&This
->ISAXAttributes_iface
, QName
,
938 SysStringLen(QName
), (const WCHAR
**)value
, &len
);
941 static const struct IVBSAXAttributesVtbl ivbsaxattributes_vtbl
=
943 ivbsaxattributes_QueryInterface
,
944 ivbsaxattributes_AddRef
,
945 ivbsaxattributes_Release
,
946 ivbsaxattributes_GetTypeInfoCount
,
947 ivbsaxattributes_GetTypeInfo
,
948 ivbsaxattributes_GetIDsOfNames
,
949 ivbsaxattributes_Invoke
,
950 ivbsaxattributes_get_length
,
951 ivbsaxattributes_getURI
,
952 ivbsaxattributes_getLocalName
,
953 ivbsaxattributes_getQName
,
954 ivbsaxattributes_getIndexFromName
,
955 ivbsaxattributes_getIndexFromQName
,
956 ivbsaxattributes_getType
,
957 ivbsaxattributes_getTypeFromName
,
958 ivbsaxattributes_getTypeFromQName
,
959 ivbsaxattributes_getValue
,
960 ivbsaxattributes_getValueFromName
,
961 ivbsaxattributes_getValueFromQName
964 /*** ISAXAttributes interface ***/
965 /*** IUnknown methods ***/
966 static HRESULT WINAPI
isaxattributes_QueryInterface(
967 ISAXAttributes
* iface
,
971 saxlocator
*This
= impl_from_ISAXAttributes(iface
);
972 TRACE("%p %s %p\n", This
, debugstr_guid(riid
), ppvObject
);
973 return ISAXLocator_QueryInterface(&This
->ISAXLocator_iface
, riid
, ppvObject
);
976 static ULONG WINAPI
isaxattributes_AddRef(ISAXAttributes
* iface
)
978 saxlocator
*This
= impl_from_ISAXAttributes(iface
);
980 return ISAXLocator_AddRef(&This
->ISAXLocator_iface
);
983 static ULONG WINAPI
isaxattributes_Release(ISAXAttributes
* iface
)
985 saxlocator
*This
= impl_from_ISAXAttributes(iface
);
988 return ISAXLocator_Release(&This
->ISAXLocator_iface
);
991 /*** ISAXAttributes methods ***/
992 static HRESULT WINAPI
isaxattributes_getLength(
993 ISAXAttributes
* iface
,
996 saxlocator
*This
= impl_from_ISAXAttributes( iface
);
998 *length
= This
->nb_attributes
;
999 TRACE("Length set to %d\n", *length
);
1003 static HRESULT WINAPI
isaxattributes_getURI(
1004 ISAXAttributes
* iface
,
1009 saxlocator
*This
= impl_from_ISAXAttributes( iface
);
1010 TRACE("(%p)->(%d)\n", This
, index
);
1012 if(index
>= This
->nb_attributes
|| index
< 0) return E_INVALIDARG
;
1013 if(!url
|| !size
) return E_POINTER
;
1015 *size
= SysStringLen(This
->attributes
[index
].szURI
);
1016 *url
= This
->attributes
[index
].szURI
;
1018 TRACE("(%s:%d)\n", debugstr_w(This
->attributes
[index
].szURI
), *size
);
1023 static HRESULT WINAPI
isaxattributes_getLocalName(
1024 ISAXAttributes
* iface
,
1026 const WCHAR
**pLocalName
,
1027 int *pLocalNameLength
)
1029 saxlocator
*This
= impl_from_ISAXAttributes( iface
);
1030 TRACE("(%p)->(%d)\n", This
, nIndex
);
1032 if(nIndex
>=This
->nb_attributes
|| nIndex
<0) return E_INVALIDARG
;
1033 if(!pLocalName
|| !pLocalNameLength
) return E_POINTER
;
1035 *pLocalNameLength
= SysStringLen(This
->attributes
[nIndex
].szLocalname
);
1036 *pLocalName
= This
->attributes
[nIndex
].szLocalname
;
1041 static HRESULT WINAPI
isaxattributes_getQName(
1042 ISAXAttributes
* iface
,
1044 const WCHAR
**pQName
,
1047 saxlocator
*This
= impl_from_ISAXAttributes( iface
);
1048 TRACE("(%p)->(%d)\n", This
, nIndex
);
1050 if(nIndex
>=This
->nb_attributes
|| nIndex
<0) return E_INVALIDARG
;
1051 if(!pQName
|| !pQNameLength
) return E_POINTER
;
1053 *pQNameLength
= SysStringLen(This
->attributes
[nIndex
].szQName
);
1054 *pQName
= This
->attributes
[nIndex
].szQName
;
1059 static HRESULT WINAPI
isaxattributes_getName(
1060 ISAXAttributes
* iface
,
1064 const WCHAR
**localName
,
1065 int *pLocalNameSize
,
1066 const WCHAR
**QName
,
1069 saxlocator
*This
= impl_from_ISAXAttributes( iface
);
1070 TRACE("(%p)->(%d)\n", This
, index
);
1072 if(index
>=This
->nb_attributes
|| index
<0) return E_INVALIDARG
;
1073 if(!uri
|| !pUriLength
|| !localName
|| !pLocalNameSize
1074 || !QName
|| !pQNameLength
) return E_POINTER
;
1076 *pUriLength
= SysStringLen(This
->attributes
[index
].szURI
);
1077 *uri
= This
->attributes
[index
].szURI
;
1078 *pLocalNameSize
= SysStringLen(This
->attributes
[index
].szLocalname
);
1079 *localName
= This
->attributes
[index
].szLocalname
;
1080 *pQNameLength
= SysStringLen(This
->attributes
[index
].szQName
);
1081 *QName
= This
->attributes
[index
].szQName
;
1083 TRACE("(%s, %s, %s)\n", debugstr_w(*uri
), debugstr_w(*localName
), debugstr_w(*QName
));
1088 static HRESULT WINAPI
isaxattributes_getIndexFromName(
1089 ISAXAttributes
* iface
,
1092 const WCHAR
*pLocalName
,
1093 int cocalNameLength
,
1096 saxlocator
*This
= impl_from_ISAXAttributes( iface
);
1098 TRACE("(%p)->(%s, %d, %s, %d)\n", This
, debugstr_w(pUri
), cUriLength
,
1099 debugstr_w(pLocalName
), cocalNameLength
);
1101 if(!pUri
|| !pLocalName
|| !index
) return E_POINTER
;
1103 for(i
=0; i
<This
->nb_attributes
; i
++)
1105 if(cUriLength
!=SysStringLen(This
->attributes
[i
].szURI
)
1106 || cocalNameLength
!=SysStringLen(This
->attributes
[i
].szLocalname
))
1108 if(cUriLength
&& memcmp(pUri
, This
->attributes
[i
].szURI
,
1109 sizeof(WCHAR
)*cUriLength
))
1111 if(cocalNameLength
&& memcmp(pLocalName
, This
->attributes
[i
].szLocalname
,
1112 sizeof(WCHAR
)*cocalNameLength
))
1119 return E_INVALIDARG
;
1122 static HRESULT WINAPI
isaxattributes_getIndexFromQName(
1123 ISAXAttributes
* iface
,
1124 const WCHAR
*pQName
,
1128 saxlocator
*This
= impl_from_ISAXAttributes( iface
);
1130 TRACE("(%p)->(%s, %d)\n", This
, debugstr_w(pQName
), nQNameLength
);
1132 if(!pQName
|| !index
) return E_POINTER
;
1133 if(!nQNameLength
) return E_INVALIDARG
;
1135 for(i
=0; i
<This
->nb_attributes
; i
++)
1137 if(nQNameLength
!=SysStringLen(This
->attributes
[i
].szQName
)) continue;
1138 if(memcmp(pQName
, This
->attributes
[i
].szQName
, sizeof(WCHAR
)*nQNameLength
)) continue;
1144 return E_INVALIDARG
;
1147 static HRESULT WINAPI
isaxattributes_getType(
1148 ISAXAttributes
* iface
,
1150 const WCHAR
**pType
,
1153 saxlocator
*This
= impl_from_ISAXAttributes( iface
);
1155 FIXME("(%p)->(%d) stub\n", This
, nIndex
);
1159 static HRESULT WINAPI
isaxattributes_getTypeFromName(
1160 ISAXAttributes
* iface
,
1163 const WCHAR
*pLocalName
,
1165 const WCHAR
**pType
,
1168 saxlocator
*This
= impl_from_ISAXAttributes( iface
);
1170 FIXME("(%p)->(%s, %d, %s, %d) stub\n", This
, debugstr_w(pUri
), nUri
,
1171 debugstr_w(pLocalName
), nLocalName
);
1175 static HRESULT WINAPI
isaxattributes_getTypeFromQName(
1176 ISAXAttributes
* iface
,
1177 const WCHAR
*pQName
,
1179 const WCHAR
**pType
,
1182 saxlocator
*This
= impl_from_ISAXAttributes( iface
);
1184 FIXME("(%p)->(%s, %d) stub\n", This
, debugstr_w(pQName
), nQName
);
1188 static HRESULT WINAPI
isaxattributes_getValue(
1189 ISAXAttributes
* iface
,
1191 const WCHAR
**value
,
1194 saxlocator
*This
= impl_from_ISAXAttributes( iface
);
1195 TRACE("(%p)->(%d)\n", This
, index
);
1197 if(index
>=This
->nb_attributes
|| index
<0) return E_INVALIDARG
;
1198 if(!value
|| !nValue
) return E_POINTER
;
1200 *nValue
= SysStringLen(This
->attributes
[index
].szValue
);
1201 *value
= This
->attributes
[index
].szValue
;
1203 TRACE("(%s:%d)\n", debugstr_w(*value
), *nValue
);
1208 static HRESULT WINAPI
isaxattributes_getValueFromName(
1209 ISAXAttributes
* iface
,
1212 const WCHAR
*pLocalName
,
1214 const WCHAR
**pValue
,
1219 saxlocator
*This
= impl_from_ISAXAttributes( iface
);
1220 TRACE("(%p)->(%s, %d, %s, %d)\n", This
, debugstr_w(pUri
), nUri
,
1221 debugstr_w(pLocalName
), nLocalName
);
1223 hr
= ISAXAttributes_getIndexFromName(iface
,
1224 pUri
, nUri
, pLocalName
, nLocalName
, &index
);
1225 if(hr
==S_OK
) hr
= ISAXAttributes_getValue(iface
, index
, pValue
, nValue
);
1230 static HRESULT WINAPI
isaxattributes_getValueFromQName(
1231 ISAXAttributes
* iface
,
1232 const WCHAR
*pQName
,
1234 const WCHAR
**pValue
,
1239 saxlocator
*This
= impl_from_ISAXAttributes( iface
);
1240 TRACE("(%p)->(%s, %d)\n", This
, debugstr_w(pQName
), nQName
);
1242 hr
= ISAXAttributes_getIndexFromQName(iface
, pQName
, nQName
, &index
);
1243 if(hr
==S_OK
) hr
= ISAXAttributes_getValue(iface
, index
, pValue
, nValue
);
1248 static const struct ISAXAttributesVtbl isaxattributes_vtbl
=
1250 isaxattributes_QueryInterface
,
1251 isaxattributes_AddRef
,
1252 isaxattributes_Release
,
1253 isaxattributes_getLength
,
1254 isaxattributes_getURI
,
1255 isaxattributes_getLocalName
,
1256 isaxattributes_getQName
,
1257 isaxattributes_getName
,
1258 isaxattributes_getIndexFromName
,
1259 isaxattributes_getIndexFromQName
,
1260 isaxattributes_getType
,
1261 isaxattributes_getTypeFromName
,
1262 isaxattributes_getTypeFromQName
,
1263 isaxattributes_getValue
,
1264 isaxattributes_getValueFromName
,
1265 isaxattributes_getValueFromQName
1268 /* Libxml2 escapes '&' back to char reference '&' in attribute value,
1269 so when document has escaped value with '&' it's parsed to '&' and then
1270 escaped to '&'. This function takes care of ampersands only. */
1271 static BSTR
saxreader_get_unescaped_value(const xmlChar
*buf
, int len
)
1273 static const WCHAR ampescW
[] = {'&','#','3','8',';',0};
1274 WCHAR
*dest
, *ptrW
, *str
;
1281 str_len
= MultiByteToWideChar(CP_UTF8
, 0, (LPCSTR
)buf
, len
, NULL
, 0);
1282 if (len
!= -1) str_len
++;
1284 str
= heap_alloc(str_len
*sizeof(WCHAR
));
1285 if (!str
) return NULL
;
1287 MultiByteToWideChar(CP_UTF8
, 0, (LPCSTR
)buf
, len
, str
, str_len
);
1288 if (len
!= -1) str
[str_len
-1] = 0;
1291 while ((dest
= strstrW(ptrW
, ampescW
)))
1295 /* leave first '&' from a reference as a value */
1296 src
= dest
+ (sizeof(ampescW
)/sizeof(WCHAR
) - 1);
1299 /* move together with null terminator */
1300 memmove(dest
, src
, (strlenW(src
) + 1)*sizeof(WCHAR
));
1305 bstr
= SysAllocString(str
);
1311 static HRESULT
SAXAttributes_populate(saxlocator
*locator
,
1312 int nb_namespaces
, const xmlChar
**xmlNamespaces
,
1313 int nb_attributes
, const xmlChar
**xmlAttributes
)
1315 static const xmlChar xmlns
[] = "xmlns";
1316 static const WCHAR xmlnsW
[] = { 'x','m','l','n','s',0 };
1318 struct _attributes
*attrs
;
1321 /* skip namespace definitions */
1322 if ((locator
->saxreader
->features
& NamespacePrefixes
) == 0)
1325 locator
->nb_attributes
= nb_namespaces
+ nb_attributes
;
1326 if(locator
->nb_attributes
> locator
->attributesSize
)
1328 attrs
= heap_realloc(locator
->attributes
, sizeof(struct _attributes
)*locator
->nb_attributes
*2);
1331 locator
->nb_attributes
= 0;
1332 return E_OUTOFMEMORY
;
1334 locator
->attributes
= attrs
;
1338 attrs
= locator
->attributes
;
1341 for (i
= 0; i
< nb_namespaces
; i
++)
1343 attrs
[nb_attributes
+i
].szLocalname
= SysAllocStringLen(NULL
, 0);
1344 attrs
[nb_attributes
+i
].szURI
= locator
->namespaceUri
;
1345 attrs
[nb_attributes
+i
].szValue
= bstr_from_xmlChar(xmlNamespaces
[2*i
+1]);
1346 if(!xmlNamespaces
[2*i
])
1347 attrs
[nb_attributes
+i
].szQName
= SysAllocString(xmlnsW
);
1349 attrs
[nb_attributes
+i
].szQName
= QName_from_xmlChar(xmlns
, xmlNamespaces
[2*i
]);
1352 for (i
= 0; i
< nb_attributes
; i
++)
1354 static const xmlChar xmlA
[] = "xml";
1356 if (xmlStrEqual(xmlAttributes
[i
*5+1], xmlA
))
1357 attrs
[i
].szURI
= bstr_from_xmlChar(xmlAttributes
[i
*5+2]);
1359 /* that's an important feature to keep same uri pointer for every reported attribute */
1360 attrs
[i
].szURI
= find_element_uri(locator
, xmlAttributes
[i
*5+2]);
1362 attrs
[i
].szLocalname
= bstr_from_xmlChar(xmlAttributes
[i
*5]);
1363 attrs
[i
].szValue
= saxreader_get_unescaped_value(xmlAttributes
[i
*5+3], xmlAttributes
[i
*5+4]-xmlAttributes
[i
*5+3]);
1364 attrs
[i
].szQName
= QName_from_xmlChar(xmlAttributes
[i
*5+1],
1365 xmlAttributes
[i
*5]);
1371 /*** LibXML callbacks ***/
1372 static void libxmlStartDocument(void *ctx
)
1374 saxlocator
*This
= ctx
;
1375 struct saxcontenthandler_iface
*handler
= saxreader_get_contenthandler(This
->saxreader
);
1378 if (This
->saxreader
->version
>= MSXML4
)
1380 const xmlChar
*p
= This
->pParserCtxt
->input
->cur
-1;
1381 update_position(This
, FALSE
);
1382 while(p
>This
->pParserCtxt
->input
->base
&& *p
!='>')
1384 if(*p
=='\n' || (*p
=='\r' && *(p
+1)!='\n'))
1389 for(; p
>=This
->pParserCtxt
->input
->base
&& *p
!='\n' && *p
!='\r'; p
--)
1393 /* store version value, declaration has to contain version attribute */
1394 if (This
->pParserCtxt
->standalone
!= -1)
1396 SysFreeString(This
->saxreader
->xmldecl_version
);
1397 This
->saxreader
->xmldecl_version
= bstr_from_xmlChar(This
->pParserCtxt
->version
);
1400 if (saxreader_has_handler(This
, SAXContentHandler
))
1402 if(This
->vbInterface
)
1403 hr
= IVBSAXContentHandler_startDocument(handler
->vbhandler
);
1405 hr
= ISAXContentHandler_startDocument(handler
->handler
);
1407 if (sax_callback_failed(This
, hr
))
1408 format_error_message_from_id(This
, hr
);
1412 static void libxmlEndDocument(void *ctx
)
1414 saxlocator
*This
= ctx
;
1415 struct saxcontenthandler_iface
*handler
= saxreader_get_contenthandler(This
->saxreader
);
1418 if (This
->saxreader
->version
>= MSXML4
) {
1419 update_position(This
, FALSE
);
1420 if(This
->column
> 1)
1428 if(This
->ret
!= S_OK
) return;
1430 if (saxreader_has_handler(This
, SAXContentHandler
))
1432 if(This
->vbInterface
)
1433 hr
= IVBSAXContentHandler_endDocument(handler
->vbhandler
);
1435 hr
= ISAXContentHandler_endDocument(handler
->handler
);
1437 if (sax_callback_failed(This
, hr
))
1438 format_error_message_from_id(This
, hr
);
1442 static void libxmlStartElementNS(
1444 const xmlChar
*localname
,
1445 const xmlChar
*prefix
,
1448 const xmlChar
**namespaces
,
1451 const xmlChar
**attributes
)
1453 saxlocator
*This
= ctx
;
1454 struct saxcontenthandler_iface
*handler
= saxreader_get_contenthandler(This
->saxreader
);
1455 element_entry
*element
;
1459 update_position(This
, TRUE
);
1460 if(*(This
->pParserCtxt
->input
->cur
) == '/')
1462 if(This
->saxreader
->version
< MSXML4
)
1465 element
= alloc_element_entry(localname
, prefix
, nb_namespaces
, namespaces
);
1466 push_element_ns(This
, element
);
1468 if (is_namespaces_enabled(This
->saxreader
))
1472 for (i
= 0; i
< nb_namespaces
&& saxreader_has_handler(This
, SAXContentHandler
); i
++)
1474 if (This
->vbInterface
)
1475 hr
= IVBSAXContentHandler_startPrefixMapping(
1477 &element
->ns
[i
].prefix
,
1478 &element
->ns
[i
].uri
);
1480 hr
= ISAXContentHandler_startPrefixMapping(
1482 element
->ns
[i
].prefix
,
1483 SysStringLen(element
->ns
[i
].prefix
),
1485 SysStringLen(element
->ns
[i
].uri
));
1487 if (sax_callback_failed(This
, hr
))
1489 format_error_message_from_id(This
, hr
);
1495 uri
= find_element_uri(This
, URI
);
1496 hr
= SAXAttributes_populate(This
, nb_namespaces
, namespaces
, nb_attributes
, attributes
);
1497 if (hr
== S_OK
&& saxreader_has_handler(This
, SAXContentHandler
))
1501 if (is_namespaces_enabled(This
->saxreader
))
1502 local
= element
->local
;
1506 if (This
->vbInterface
)
1507 hr
= IVBSAXContentHandler_startElement(handler
->vbhandler
,
1508 &uri
, &local
, &element
->qname
, &This
->IVBSAXAttributes_iface
);
1510 hr
= ISAXContentHandler_startElement(handler
->handler
,
1511 uri
, SysStringLen(uri
),
1512 local
, SysStringLen(local
),
1513 element
->qname
, SysStringLen(element
->qname
),
1514 &This
->ISAXAttributes_iface
);
1516 if (sax_callback_failed(This
, hr
))
1517 format_error_message_from_id(This
, hr
);
1521 static void libxmlEndElementNS(
1523 const xmlChar
*localname
,
1524 const xmlChar
*prefix
,
1527 saxlocator
*This
= ctx
;
1528 struct saxcontenthandler_iface
*handler
= saxreader_get_contenthandler(This
->saxreader
);
1529 element_entry
*element
;
1534 update_position(This
, FALSE
);
1535 p
= This
->pParserCtxt
->input
->cur
;
1537 if (This
->saxreader
->version
>= MSXML4
)
1540 while(p
>This
->pParserCtxt
->input
->base
&& *p
!='>')
1542 if(*p
=='\n' || (*p
=='\r' && *(p
+1)!='\n'))
1547 else if(*(p
-1)!='>' || *(p
-2)!='/')
1550 while(p
-2>=This
->pParserCtxt
->input
->base
1551 && *(p
-2)!='<' && *(p
-1)!='/')
1553 if(*p
=='\n' || (*p
=='\r' && *(p
+1)!='\n'))
1559 for(; p
>=This
->pParserCtxt
->input
->base
&& *p
!='\n' && *p
!='\r'; p
--)
1562 uri
= find_element_uri(This
, URI
);
1563 element
= pop_element_ns(This
);
1565 if (!saxreader_has_handler(This
, SAXContentHandler
))
1567 This
->nb_attributes
= 0;
1568 free_element_entry(element
);
1572 if (is_namespaces_enabled(This
->saxreader
))
1573 local
= element
->local
;
1577 if (This
->vbInterface
)
1578 hr
= IVBSAXContentHandler_endElement(
1580 &uri
, &local
, &element
->qname
);
1582 hr
= ISAXContentHandler_endElement(
1584 uri
, SysStringLen(uri
),
1585 local
, SysStringLen(local
),
1586 element
->qname
, SysStringLen(element
->qname
));
1588 This
->nb_attributes
= 0;
1590 if (sax_callback_failed(This
, hr
))
1592 format_error_message_from_id(This
, hr
);
1593 free_element_entry(element
);
1597 if (is_namespaces_enabled(This
->saxreader
))
1600 while (iterate_endprefix_index(This
, element
, &i
) && saxreader_has_handler(This
, SAXContentHandler
))
1602 if (This
->vbInterface
)
1603 hr
= IVBSAXContentHandler_endPrefixMapping(
1604 handler
->vbhandler
, &element
->ns
[i
].prefix
);
1606 hr
= ISAXContentHandler_endPrefixMapping(
1607 handler
->handler
, element
->ns
[i
].prefix
, SysStringLen(element
->ns
[i
].prefix
));
1609 if (sax_callback_failed(This
, hr
)) break;
1612 if (sax_callback_failed(This
, hr
))
1613 format_error_message_from_id(This
, hr
);
1616 free_element_entry(element
);
1619 static void libxmlCharacters(
1624 saxlocator
*This
= ctx
;
1628 BOOL lastEvent
= FALSE
;
1630 if (!saxreader_has_handler(This
, SAXContentHandler
)) return;
1632 update_position(This
, FALSE
);
1633 cur
= (xmlChar
*)This
->pParserCtxt
->input
->cur
;
1634 while(cur
>=This
->pParserCtxt
->input
->base
&& *cur
!='>')
1636 if(*cur
=='\n' || (*cur
=='\r' && *(cur
+1)!='\n'))
1641 for(; cur
>=This
->pParserCtxt
->input
->base
&& *cur
!='\n' && *cur
!='\r'; cur
--)
1645 if(*(ch
-1)=='\r') cur
--;
1650 while(end
-ch
<len
&& *end
!='\r') end
++;
1661 if (This
->saxreader
->version
>= MSXML4
)
1665 for(p
=cur
; p
!=end
; p
++)
1682 Chars
= pooled_bstr_from_xmlCharN(&This
->saxreader
->pool
, cur
, end
-cur
);
1683 hr
= saxreader_saxcharacters(This
, Chars
);
1685 if (sax_callback_failed(This
, hr
))
1687 format_error_message_from_id(This
, hr
);
1691 if (This
->saxreader
->version
< MSXML4
)
1692 This
->column
+= end
-cur
;
1705 if(end
-ch
== len
) break;
1709 static void libxmlSetDocumentLocator(
1711 xmlSAXLocatorPtr loc
)
1713 saxlocator
*This
= ctx
;
1714 struct saxcontenthandler_iface
*handler
= saxreader_get_contenthandler(This
->saxreader
);
1717 if (saxreader_has_handler(This
, SAXContentHandler
))
1719 if(This
->vbInterface
)
1720 hr
= IVBSAXContentHandler_putref_documentLocator(handler
->vbhandler
,
1721 &This
->IVBSAXLocator_iface
);
1723 hr
= ISAXContentHandler_putDocumentLocator(handler
->handler
, &This
->ISAXLocator_iface
);
1727 format_error_message_from_id(This
, hr
);
1730 static void libxmlComment(void *ctx
, const xmlChar
*value
)
1732 saxlocator
*This
= ctx
;
1733 struct saxlexicalhandler_iface
*handler
= saxreader_get_lexicalhandler(This
->saxreader
);
1736 const xmlChar
*p
= This
->pParserCtxt
->input
->cur
;
1738 update_position(This
, FALSE
);
1739 while(p
-4>=This
->pParserCtxt
->input
->base
1740 && memcmp(p
-4, "<!--", sizeof(char[4])))
1742 if(*p
=='\n' || (*p
=='\r' && *(p
+1)!='\n'))
1748 for(; p
>=This
->pParserCtxt
->input
->base
&& *p
!='\n' && *p
!='\r'; p
--)
1751 if (!saxreader_has_handler(This
, SAXLexicalHandler
)) return;
1753 bValue
= pooled_bstr_from_xmlChar(&This
->saxreader
->pool
, value
);
1755 if (This
->vbInterface
)
1756 hr
= IVBSAXLexicalHandler_comment(handler
->vbhandler
, &bValue
);
1758 hr
= ISAXLexicalHandler_comment(handler
->handler
, bValue
, SysStringLen(bValue
));
1761 format_error_message_from_id(This
, hr
);
1764 static void libxmlFatalError(void *ctx
, const char *msg
, ...)
1766 saxlocator
*This
= ctx
;
1767 struct saxerrorhandler_iface
*handler
= saxreader_get_errorhandler(This
->saxreader
);
1773 if(This
->ret
!= S_OK
) {
1774 xmlStopParser(This
->pParserCtxt
);
1778 va_start(args
, msg
);
1779 vsprintf(message
, msg
, args
);
1782 len
= MultiByteToWideChar(CP_UNIXCP
, 0, message
, -1, NULL
, 0);
1783 error
= heap_alloc(sizeof(WCHAR
)*len
);
1786 MultiByteToWideChar(CP_UNIXCP
, 0, message
, -1, error
, len
);
1787 TRACE("fatal error for %p: %s\n", This
, debugstr_w(error
));
1790 if (!saxreader_has_handler(This
, SAXErrorHandler
))
1792 xmlStopParser(This
->pParserCtxt
);
1798 FIXME("Error handling is not compatible.\n");
1800 if(This
->vbInterface
)
1802 BSTR bstrError
= SysAllocString(error
);
1803 IVBSAXErrorHandler_fatalError(handler
->vbhandler
, &This
->IVBSAXLocator_iface
,
1804 &bstrError
, E_FAIL
);
1805 SysFreeString(bstrError
);
1808 ISAXErrorHandler_fatalError(handler
->handler
, &This
->ISAXLocator_iface
, error
, E_FAIL
);
1812 xmlStopParser(This
->pParserCtxt
);
1816 /* The only reason this helper exists is that CDATA section are reported by chunks,
1817 newlines are used as delimiter. More than that, reader even alters input data before reporting.
1819 This helper should be called for substring with trailing newlines.
1821 static BSTR
saxreader_get_cdata_chunk(const xmlChar
*str
, int len
)
1823 BSTR bstr
= bstr_from_xmlCharN(str
, len
), ret
;
1826 ptr
= bstr
+ len
- 1;
1827 while ((*ptr
== '\r' || *ptr
== '\n') && ptr
>= bstr
)
1832 /* replace returns as:
1834 - "\r<char>" -> "\n<char>"
1840 if (*(ptr
+1) == '\r' || *(ptr
+1) == '\n')
1843 memmove(ptr
, ptr
+1, len
-- - (ptr
-bstr
));
1850 ret
= SysAllocStringLen(bstr
, len
);
1851 SysFreeString(bstr
);
1855 static void libxml_cdatablock(void *ctx
, const xmlChar
*value
, int len
)
1857 const xmlChar
*start
, *end
;
1858 saxlocator
*locator
= ctx
;
1859 struct saxlexicalhandler_iface
*lexical
= saxreader_get_lexicalhandler(locator
->saxreader
);
1864 update_position(locator
, FALSE
);
1865 if (saxreader_has_handler(locator
, SAXLexicalHandler
))
1867 if (locator
->vbInterface
)
1868 hr
= IVBSAXLexicalHandler_startCDATA(lexical
->vbhandler
);
1870 hr
= ISAXLexicalHandler_startCDATA(lexical
->handler
);
1875 format_error_message_from_id(locator
, hr
);
1885 /* scan for newlines */
1886 if (value
[i
] == '\r' || value
[i
] == '\n')
1888 /* skip newlines/linefeeds */
1891 if (value
[i
] != '\r' && value
[i
] != '\n') break;
1897 chars
= saxreader_get_cdata_chunk(start
, end
-start
);
1898 TRACE("(chunk %s)\n", debugstr_w(chars
));
1899 hr
= saxreader_saxcharacters(locator
, chars
);
1900 SysFreeString(chars
);
1909 /* no newline chars (or last chunk) report as a whole */
1910 if (!end
&& start
== value
)
1913 chars
= bstr_from_xmlCharN(start
, len
-(start
-value
));
1914 TRACE("(%s)\n", debugstr_w(chars
));
1915 hr
= saxreader_saxcharacters(locator
, chars
);
1916 SysFreeString(chars
);
1919 if (saxreader_has_handler(locator
, SAXLexicalHandler
))
1921 if (locator
->vbInterface
)
1922 hr
= IVBSAXLexicalHandler_endCDATA(lexical
->vbhandler
);
1924 hr
= ISAXLexicalHandler_endCDATA(lexical
->handler
);
1928 format_error_message_from_id(locator
, hr
);
1931 static xmlParserInputPtr
libxmlresolveentity(void *ctx
, const xmlChar
*publicid
, const xmlChar
*systemid
)
1933 FIXME("entity resolving not implemented, %s, %s\n", publicid
, systemid
);
1934 return xmlSAX2ResolveEntity(ctx
, publicid
, systemid
);
1937 /*** IVBSAXLocator interface ***/
1938 /*** IUnknown methods ***/
1939 static HRESULT WINAPI
ivbsaxlocator_QueryInterface(IVBSAXLocator
* iface
, REFIID riid
, void **ppvObject
)
1941 saxlocator
*This
= impl_from_IVBSAXLocator( iface
);
1943 TRACE("%p %s %p\n", This
, debugstr_guid( riid
), ppvObject
);
1947 if ( IsEqualGUID( riid
, &IID_IUnknown
) ||
1948 IsEqualGUID( riid
, &IID_IDispatch
) ||
1949 IsEqualGUID( riid
, &IID_IVBSAXLocator
))
1953 else if ( IsEqualGUID( riid
, &IID_IVBSAXAttributes
))
1955 *ppvObject
= &This
->IVBSAXAttributes_iface
;
1959 FIXME("interface %s not implemented\n", debugstr_guid(riid
));
1960 return E_NOINTERFACE
;
1963 IVBSAXLocator_AddRef( iface
);
1968 static ULONG WINAPI
ivbsaxlocator_AddRef(IVBSAXLocator
* iface
)
1970 saxlocator
*This
= impl_from_IVBSAXLocator( iface
);
1971 TRACE("%p\n", This
);
1972 return InterlockedIncrement( &This
->ref
);
1975 static ULONG WINAPI
ivbsaxlocator_Release(
1976 IVBSAXLocator
* iface
)
1978 saxlocator
*This
= impl_from_IVBSAXLocator( iface
);
1979 return ISAXLocator_Release((ISAXLocator
*)&This
->IVBSAXLocator_iface
);
1982 /*** IDispatch methods ***/
1983 static HRESULT WINAPI
ivbsaxlocator_GetTypeInfoCount( IVBSAXLocator
*iface
, UINT
* pctinfo
)
1985 saxlocator
*This
= impl_from_IVBSAXLocator( iface
);
1987 TRACE("(%p)->(%p)\n", This
, pctinfo
);
1994 static HRESULT WINAPI
ivbsaxlocator_GetTypeInfo(
1995 IVBSAXLocator
*iface
,
1996 UINT iTInfo
, LCID lcid
, ITypeInfo
** ppTInfo
)
1998 saxlocator
*This
= impl_from_IVBSAXLocator( iface
);
2001 TRACE("(%p)->(%u %u %p)\n", This
, iTInfo
, lcid
, ppTInfo
);
2003 hr
= get_typeinfo(IVBSAXLocator_tid
, ppTInfo
);
2008 static HRESULT WINAPI
ivbsaxlocator_GetIDsOfNames(
2009 IVBSAXLocator
*iface
,
2011 LPOLESTR
* rgszNames
,
2016 saxlocator
*This
= impl_from_IVBSAXLocator( iface
);
2017 ITypeInfo
*typeinfo
;
2020 TRACE("(%p)->(%s %p %u %u %p)\n", This
, debugstr_guid(riid
), rgszNames
, cNames
,
2023 if(!rgszNames
|| cNames
== 0 || !rgDispId
)
2024 return E_INVALIDARG
;
2026 hr
= get_typeinfo(IVBSAXLocator_tid
, &typeinfo
);
2029 hr
= ITypeInfo_GetIDsOfNames(typeinfo
, rgszNames
, cNames
, rgDispId
);
2030 ITypeInfo_Release(typeinfo
);
2036 static HRESULT WINAPI
ivbsaxlocator_Invoke(
2037 IVBSAXLocator
*iface
,
2038 DISPID dispIdMember
,
2042 DISPPARAMS
* pDispParams
,
2043 VARIANT
* pVarResult
,
2044 EXCEPINFO
* pExcepInfo
,
2047 saxlocator
*This
= impl_from_IVBSAXLocator( iface
);
2048 ITypeInfo
*typeinfo
;
2051 TRACE("(%p)->(%d %s %d %d %p %p %p %p)\n", This
, dispIdMember
, debugstr_guid(riid
),
2052 lcid
, wFlags
, pDispParams
, pVarResult
, pExcepInfo
, puArgErr
);
2054 hr
= get_typeinfo(IVBSAXLocator_tid
, &typeinfo
);
2057 hr
= ITypeInfo_Invoke(typeinfo
, &This
->IVBSAXLocator_iface
, dispIdMember
, wFlags
,
2058 pDispParams
, pVarResult
, pExcepInfo
, puArgErr
);
2059 ITypeInfo_Release(typeinfo
);
2065 /*** IVBSAXLocator methods ***/
2066 static HRESULT WINAPI
ivbsaxlocator_get_columnNumber(
2067 IVBSAXLocator
* iface
,
2070 saxlocator
*This
= impl_from_IVBSAXLocator( iface
);
2071 return ISAXLocator_getColumnNumber((ISAXLocator
*)&This
->IVBSAXLocator_iface
, pnColumn
);
2074 static HRESULT WINAPI
ivbsaxlocator_get_lineNumber(
2075 IVBSAXLocator
* iface
,
2078 saxlocator
*This
= impl_from_IVBSAXLocator( iface
);
2079 return ISAXLocator_getLineNumber((ISAXLocator
*)&This
->IVBSAXLocator_iface
, pnLine
);
2082 static HRESULT WINAPI
ivbsaxlocator_get_publicId(
2083 IVBSAXLocator
* iface
,
2086 saxlocator
*This
= impl_from_IVBSAXLocator( iface
);
2087 return ISAXLocator_getPublicId((ISAXLocator
*)&This
->IVBSAXLocator_iface
,
2088 (const WCHAR
**)publicId
);
2091 static HRESULT WINAPI
ivbsaxlocator_get_systemId(
2092 IVBSAXLocator
* iface
,
2095 saxlocator
*This
= impl_from_IVBSAXLocator( iface
);
2096 return ISAXLocator_getSystemId((ISAXLocator
*)&This
->IVBSAXLocator_iface
,
2097 (const WCHAR
**)systemId
);
2100 static const struct IVBSAXLocatorVtbl VBSAXLocatorVtbl
=
2102 ivbsaxlocator_QueryInterface
,
2103 ivbsaxlocator_AddRef
,
2104 ivbsaxlocator_Release
,
2105 ivbsaxlocator_GetTypeInfoCount
,
2106 ivbsaxlocator_GetTypeInfo
,
2107 ivbsaxlocator_GetIDsOfNames
,
2108 ivbsaxlocator_Invoke
,
2109 ivbsaxlocator_get_columnNumber
,
2110 ivbsaxlocator_get_lineNumber
,
2111 ivbsaxlocator_get_publicId
,
2112 ivbsaxlocator_get_systemId
2115 /*** ISAXLocator interface ***/
2116 /*** IUnknown methods ***/
2117 static HRESULT WINAPI
isaxlocator_QueryInterface(ISAXLocator
* iface
, REFIID riid
, void **ppvObject
)
2119 saxlocator
*This
= impl_from_ISAXLocator( iface
);
2121 TRACE("%p %s %p\n", This
, debugstr_guid( riid
), ppvObject
);
2125 if ( IsEqualGUID( riid
, &IID_IUnknown
) ||
2126 IsEqualGUID( riid
, &IID_ISAXLocator
))
2130 else if ( IsEqualGUID( riid
, &IID_ISAXAttributes
))
2132 *ppvObject
= &This
->ISAXAttributes_iface
;
2136 WARN("interface %s not implemented\n", debugstr_guid(riid
));
2137 return E_NOINTERFACE
;
2140 ISAXLocator_AddRef( iface
);
2145 static ULONG WINAPI
isaxlocator_AddRef(ISAXLocator
* iface
)
2147 saxlocator
*This
= impl_from_ISAXLocator( iface
);
2148 ULONG ref
= InterlockedIncrement( &This
->ref
);
2149 TRACE("(%p)->(%d)\n", This
, ref
);
2153 static ULONG WINAPI
isaxlocator_Release(
2156 saxlocator
*This
= impl_from_ISAXLocator( iface
);
2157 LONG ref
= InterlockedDecrement( &This
->ref
);
2159 TRACE("(%p)->(%d)\n", This
, ref
);
2163 element_entry
*element
, *element2
;
2166 SysFreeString(This
->publicId
);
2167 SysFreeString(This
->systemId
);
2168 SysFreeString(This
->namespaceUri
);
2170 for(index
=0; index
<This
->nb_attributes
; index
++)
2172 SysFreeString(This
->attributes
[index
].szLocalname
);
2173 SysFreeString(This
->attributes
[index
].szValue
);
2174 SysFreeString(This
->attributes
[index
].szQName
);
2176 heap_free(This
->attributes
);
2179 LIST_FOR_EACH_ENTRY_SAFE(element
, element2
, &This
->elements
, element_entry
, entry
)
2181 list_remove(&element
->entry
);
2182 free_element_entry(element
);
2185 ISAXXMLReader_Release(&This
->saxreader
->ISAXXMLReader_iface
);
2192 /*** ISAXLocator methods ***/
2193 static HRESULT WINAPI
isaxlocator_getColumnNumber(
2197 saxlocator
*This
= impl_from_ISAXLocator( iface
);
2199 *pnColumn
= This
->column
;
2203 static HRESULT WINAPI
isaxlocator_getLineNumber(
2207 saxlocator
*This
= impl_from_ISAXLocator( iface
);
2209 *pnLine
= This
->line
;
2213 static HRESULT WINAPI
isaxlocator_getPublicId(
2215 const WCHAR
** ppwchPublicId
)
2218 saxlocator
*This
= impl_from_ISAXLocator( iface
);
2220 SysFreeString(This
->publicId
);
2222 publicId
= bstr_from_xmlChar(xmlSAX2GetPublicId(This
->pParserCtxt
));
2223 if(SysStringLen(publicId
))
2224 This
->publicId
= publicId
;
2227 SysFreeString(publicId
);
2228 This
->publicId
= NULL
;
2231 *ppwchPublicId
= This
->publicId
;
2235 static HRESULT WINAPI
isaxlocator_getSystemId(
2237 const WCHAR
** ppwchSystemId
)
2240 saxlocator
*This
= impl_from_ISAXLocator( iface
);
2242 SysFreeString(This
->systemId
);
2244 systemId
= bstr_from_xmlChar(xmlSAX2GetSystemId(This
->pParserCtxt
));
2245 if(SysStringLen(systemId
))
2246 This
->systemId
= systemId
;
2249 SysFreeString(systemId
);
2250 This
->systemId
= NULL
;
2253 *ppwchSystemId
= This
->systemId
;
2257 static const struct ISAXLocatorVtbl SAXLocatorVtbl
=
2259 isaxlocator_QueryInterface
,
2261 isaxlocator_Release
,
2262 isaxlocator_getColumnNumber
,
2263 isaxlocator_getLineNumber
,
2264 isaxlocator_getPublicId
,
2265 isaxlocator_getSystemId
2268 static HRESULT
SAXLocator_create(saxreader
*reader
, saxlocator
**ppsaxlocator
, BOOL vbInterface
)
2270 static const WCHAR w3xmlns
[] = { 'h','t','t','p',':','/','/', 'w','w','w','.','w','3','.',
2271 'o','r','g','/','2','0','0','0','/','x','m','l','n','s','/',0 };
2273 saxlocator
*locator
;
2275 locator
= heap_alloc( sizeof (*locator
) );
2277 return E_OUTOFMEMORY
;
2279 locator
->IVBSAXLocator_iface
.lpVtbl
= &VBSAXLocatorVtbl
;
2280 locator
->ISAXLocator_iface
.lpVtbl
= &SAXLocatorVtbl
;
2281 locator
->IVBSAXAttributes_iface
.lpVtbl
= &ivbsaxattributes_vtbl
;
2282 locator
->ISAXAttributes_iface
.lpVtbl
= &isaxattributes_vtbl
;
2284 locator
->vbInterface
= vbInterface
;
2286 locator
->saxreader
= reader
;
2287 ISAXXMLReader_AddRef(&reader
->ISAXXMLReader_iface
);
2289 locator
->pParserCtxt
= NULL
;
2290 locator
->publicId
= NULL
;
2291 locator
->systemId
= NULL
;
2292 locator
->line
= reader
->version
< MSXML4
? 0 : 1;
2293 locator
->column
= 0;
2294 locator
->ret
= S_OK
;
2295 if (locator
->saxreader
->version
>= MSXML6
)
2296 locator
->namespaceUri
= SysAllocString(w3xmlns
);
2298 locator
->namespaceUri
= SysAllocStringLen(NULL
, 0);
2299 if(!locator
->namespaceUri
)
2301 ISAXXMLReader_Release(&reader
->ISAXXMLReader_iface
);
2303 return E_OUTOFMEMORY
;
2306 locator
->attributesSize
= 8;
2307 locator
->nb_attributes
= 0;
2308 locator
->attributes
= heap_alloc(sizeof(struct _attributes
)*locator
->attributesSize
);
2309 if(!locator
->attributes
)
2311 ISAXXMLReader_Release(&reader
->ISAXXMLReader_iface
);
2312 SysFreeString(locator
->namespaceUri
);
2314 return E_OUTOFMEMORY
;
2317 list_init(&locator
->elements
);
2319 *ppsaxlocator
= locator
;
2321 TRACE("returning %p\n", *ppsaxlocator
);
2326 /*** SAXXMLReader internal functions ***/
2327 static HRESULT
internal_parseBuffer(saxreader
*This
, const char *buffer
, int size
, BOOL vbInterface
)
2329 xmlCharEncoding encoding
= XML_CHAR_ENCODING_NONE
;
2330 xmlChar
*enc_name
= NULL
;
2331 saxlocator
*locator
;
2334 TRACE("(%p)->(%p %d)\n", This
, buffer
, size
);
2336 hr
= SAXLocator_create(This
, &locator
, vbInterface
);
2342 const unsigned char *buff
= (unsigned char*)buffer
;
2344 encoding
= xmlDetectCharEncoding((xmlChar
*)buffer
, 4);
2345 enc_name
= (xmlChar
*)xmlGetCharEncodingName(encoding
);
2346 TRACE("detected encoding: %s\n", enc_name
);
2347 /* skip BOM, parser won't switch encodings and so won't skip it on its own */
2348 if ((encoding
== XML_CHAR_ENCODING_UTF8
) &&
2349 buff
[0] == 0xEF && buff
[1] == 0xBB && buff
[2] == 0xBF)
2356 /* if libxml2 detection failed try to guess */
2357 if (encoding
== XML_CHAR_ENCODING_NONE
)
2359 const WCHAR
*ptr
= (WCHAR
*)buffer
;
2360 /* xml declaration with possibly specfied encoding will be still handled by parser */
2361 if ((size
>= 2) && *ptr
== '<' && ptr
[1] != '?')
2363 enc_name
= (xmlChar
*)xmlGetCharEncodingName(XML_CHAR_ENCODING_UTF16LE
);
2364 encoding
= XML_CHAR_ENCODING_UTF16LE
;
2367 else if (encoding
== XML_CHAR_ENCODING_UTF8
)
2368 enc_name
= (xmlChar
*)xmlGetCharEncodingName(encoding
);
2372 locator
->pParserCtxt
= xmlCreateMemoryParserCtxt(buffer
, size
);
2373 if (!locator
->pParserCtxt
)
2375 ISAXLocator_Release(&locator
->ISAXLocator_iface
);
2381 locator
->pParserCtxt
->encoding
= xmlStrdup(enc_name
);
2382 if (encoding
== XML_CHAR_ENCODING_UTF16LE
) {
2383 TRACE("switching to %s\n", enc_name
);
2384 xmlSwitchEncoding(locator
->pParserCtxt
, encoding
);
2388 xmlFree(locator
->pParserCtxt
->sax
);
2389 locator
->pParserCtxt
->sax
= &locator
->saxreader
->sax
;
2390 locator
->pParserCtxt
->userData
= locator
;
2392 This
->isParsing
= TRUE
;
2393 if(xmlParseDocument(locator
->pParserCtxt
) == -1 && locator
->ret
== S_OK
)
2397 This
->isParsing
= FALSE
;
2399 if(locator
->pParserCtxt
)
2401 locator
->pParserCtxt
->sax
= NULL
;
2402 xmlFreeParserCtxt(locator
->pParserCtxt
);
2403 locator
->pParserCtxt
= NULL
;
2406 ISAXLocator_Release(&locator
->ISAXLocator_iface
);
2410 static HRESULT
internal_parseStream(saxreader
*This
, ISequentialStream
*stream
, BOOL vbInterface
)
2412 saxlocator
*locator
;
2419 hr
= ISequentialStream_Read(stream
, data
, sizeof(data
), &dataRead
);
2420 if(FAILED(hr
)) return hr
;
2422 hr
= SAXLocator_create(This
, &locator
, vbInterface
);
2423 if(FAILED(hr
)) return hr
;
2425 locator
->pParserCtxt
= xmlCreatePushParserCtxt(
2426 &locator
->saxreader
->sax
, locator
,
2427 data
, dataRead
, NULL
);
2428 if(!locator
->pParserCtxt
)
2430 ISAXLocator_Release(&locator
->ISAXLocator_iface
);
2434 This
->isParsing
= TRUE
;
2436 if(dataRead
!= sizeof(data
))
2438 ret
= xmlParseChunk(locator
->pParserCtxt
, data
, 0, 1);
2439 hr
= ret
!=XML_ERR_OK
&& locator
->ret
==S_OK
? E_FAIL
: locator
->ret
;
2446 hr
= ISequentialStream_Read(stream
, data
, sizeof(data
), &dataRead
);
2447 if (FAILED(hr
)) break;
2449 ret
= xmlParseChunk(locator
->pParserCtxt
, data
, dataRead
, 0);
2450 hr
= ret
!=XML_ERR_OK
&& locator
->ret
==S_OK
? E_FAIL
: locator
->ret
;
2452 if (hr
!= S_OK
) break;
2454 if (dataRead
!= sizeof(data
))
2456 ret
= xmlParseChunk(locator
->pParserCtxt
, data
, 0, 1);
2457 hr
= ret
!=XML_ERR_OK
&& locator
->ret
==S_OK
? E_FAIL
: locator
->ret
;
2463 This
->isParsing
= FALSE
;
2465 xmlFreeParserCtxt(locator
->pParserCtxt
);
2466 locator
->pParserCtxt
= NULL
;
2467 ISAXLocator_Release(&locator
->ISAXLocator_iface
);
2471 static HRESULT
internal_parse(
2478 TRACE("(%p)->(%s)\n", This
, debugstr_variant(&varInput
));
2480 /* Dispose of the BSTRs in the pool from a prior run, if any. */
2481 free_bstr_pool(&This
->pool
);
2483 switch(V_VT(&varInput
))
2486 hr
= internal_parseBuffer(This
, (const char*)V_BSTR(&varInput
),
2487 strlenW(V_BSTR(&varInput
))*sizeof(WCHAR
), vbInterface
);
2489 case VT_ARRAY
|VT_UI1
: {
2491 LONG lBound
, uBound
;
2494 hr
= SafeArrayGetLBound(V_ARRAY(&varInput
), 1, &lBound
);
2495 if(hr
!= S_OK
) break;
2496 hr
= SafeArrayGetUBound(V_ARRAY(&varInput
), 1, &uBound
);
2497 if(hr
!= S_OK
) break;
2498 dataRead
= (uBound
-lBound
)*SafeArrayGetElemsize(V_ARRAY(&varInput
));
2499 hr
= SafeArrayAccessData(V_ARRAY(&varInput
), &pSAData
);
2500 if(hr
!= S_OK
) break;
2501 hr
= internal_parseBuffer(This
, pSAData
, dataRead
, vbInterface
);
2502 SafeArrayUnaccessData(V_ARRAY(&varInput
));
2507 IPersistStream
*persistStream
;
2508 ISequentialStream
*stream
= NULL
;
2509 IXMLDOMDocument
*xmlDoc
;
2511 if(IUnknown_QueryInterface(V_UNKNOWN(&varInput
),
2512 &IID_IXMLDOMDocument
, (void**)&xmlDoc
) == S_OK
)
2516 IXMLDOMDocument_get_xml(xmlDoc
, &bstrData
);
2517 hr
= internal_parseBuffer(This
, (const char*)bstrData
,
2518 SysStringByteLen(bstrData
), vbInterface
);
2519 IXMLDOMDocument_Release(xmlDoc
);
2520 SysFreeString(bstrData
);
2524 if(IUnknown_QueryInterface(V_UNKNOWN(&varInput
),
2525 &IID_IPersistStream
, (void**)&persistStream
) == S_OK
)
2527 IStream
*stream_copy
;
2529 hr
= CreateStreamOnHGlobal(NULL
, TRUE
, &stream_copy
);
2532 IPersistStream_Release(persistStream
);
2536 hr
= IPersistStream_Save(persistStream
, stream_copy
, TRUE
);
2537 IPersistStream_Release(persistStream
);
2539 IStream_QueryInterface(stream_copy
, &IID_ISequentialStream
, (void**)&stream
);
2541 IStream_Release(stream_copy
);
2544 /* try base interface first */
2547 IUnknown_QueryInterface(V_UNKNOWN(&varInput
), &IID_ISequentialStream
, (void**)&stream
);
2549 /* this should never happen if IStream is implemented properly, but just in case */
2550 IUnknown_QueryInterface(V_UNKNOWN(&varInput
), &IID_IStream
, (void**)&stream
);
2555 hr
= internal_parseStream(This
, stream
, vbInterface
);
2556 ISequentialStream_Release(stream
);
2560 WARN("IUnknown* input doesn't support any of expected interfaces\n");
2567 WARN("vt %d not implemented\n", V_VT(&varInput
));
2574 static HRESULT
internal_vbonDataAvailable(void *obj
, char *ptr
, DWORD len
)
2576 saxreader
*This
= obj
;
2578 return internal_parseBuffer(This
, ptr
, len
, TRUE
);
2581 static HRESULT
internal_onDataAvailable(void *obj
, char *ptr
, DWORD len
)
2583 saxreader
*This
= obj
;
2585 return internal_parseBuffer(This
, ptr
, len
, FALSE
);
2588 static HRESULT
internal_parseURL(
2597 TRACE("(%p)->(%s)\n", This
, debugstr_w(url
));
2599 hr
= create_moniker_from_url(url
, &mon
);
2603 if(vbInterface
) hr
= bind_url(mon
, internal_vbonDataAvailable
, This
, &bsc
);
2604 else hr
= bind_url(mon
, internal_onDataAvailable
, This
, &bsc
);
2605 IMoniker_Release(mon
);
2610 return detach_bsc(bsc
);
2613 static HRESULT
internal_putProperty(
2619 TRACE("(%p)->(%s %s)\n", This
, debugstr_w(prop
), debugstr_variant(&value
));
2621 if(!memcmp(prop
, PropertyDeclHandlerW
, sizeof(PropertyDeclHandlerW
)))
2623 if(This
->isParsing
) return E_FAIL
;
2625 switch (V_VT(&value
))
2628 saxreader_put_handler(This
, SAXDeclHandler
, NULL
, vbInterface
);
2632 IUnknown
*handler
= NULL
;
2634 if (V_UNKNOWN(&value
))
2639 hr
= IUnknown_QueryInterface(V_UNKNOWN(&value
), &IID_IVBSAXDeclHandler
, (void**)&handler
);
2641 hr
= IUnknown_QueryInterface(V_UNKNOWN(&value
), &IID_ISAXDeclHandler
, (void**)&handler
);
2642 if (FAILED(hr
)) return hr
;
2645 saxreader_put_handler(This
, SAXDeclHandler
, handler
, vbInterface
);
2646 if (handler
) IUnknown_Release(handler
);
2650 return E_INVALIDARG
;
2656 if(!memcmp(prop
, PropertyLexicalHandlerW
, sizeof(PropertyLexicalHandlerW
)))
2658 if(This
->isParsing
) return E_FAIL
;
2660 switch (V_VT(&value
))
2663 saxreader_put_handler(This
, SAXLexicalHandler
, NULL
, vbInterface
);
2667 IUnknown
*handler
= NULL
;
2669 if (V_UNKNOWN(&value
))
2674 hr
= IUnknown_QueryInterface(V_UNKNOWN(&value
), &IID_IVBSAXLexicalHandler
, (void**)&handler
);
2676 hr
= IUnknown_QueryInterface(V_UNKNOWN(&value
), &IID_ISAXLexicalHandler
, (void**)&handler
);
2677 if (FAILED(hr
)) return hr
;
2680 saxreader_put_handler(This
, SAXLexicalHandler
, handler
, vbInterface
);
2681 if (handler
) IUnknown_Release(handler
);
2685 return E_INVALIDARG
;
2691 if(!memcmp(prop
, PropertyMaxXMLSizeW
, sizeof(PropertyMaxXMLSizeW
)))
2693 if (V_VT(&value
) == VT_I4
&& V_I4(&value
) == 0) return S_OK
;
2694 FIXME("(%p)->(%s): max-xml-size unsupported\n", This
, debugstr_variant(&value
));
2698 if(!memcmp(prop
, PropertyMaxElementDepthW
, sizeof(PropertyMaxElementDepthW
)))
2700 if (V_VT(&value
) == VT_I4
&& V_I4(&value
) == 0) return S_OK
;
2701 FIXME("(%p)->(%s): max-element-depth unsupported\n", This
, debugstr_variant(&value
));
2705 FIXME("(%p)->(%s:%s): unsupported property\n", This
, debugstr_w(prop
), debugstr_variant(&value
));
2707 if(!memcmp(prop
, PropertyCharsetW
, sizeof(PropertyCharsetW
)))
2710 if(!memcmp(prop
, PropertyDomNodeW
, sizeof(PropertyDomNodeW
)))
2713 if(!memcmp(prop
, PropertyInputSourceW
, sizeof(PropertyInputSourceW
)))
2716 if(!memcmp(prop
, PropertySchemaDeclHandlerW
, sizeof(PropertySchemaDeclHandlerW
)))
2719 if(!memcmp(prop
, PropertyXMLDeclEncodingW
, sizeof(PropertyXMLDeclEncodingW
)))
2722 if(!memcmp(prop
, PropertyXMLDeclStandaloneW
, sizeof(PropertyXMLDeclStandaloneW
)))
2725 if(!memcmp(prop
, PropertyXMLDeclVersionW
, sizeof(PropertyXMLDeclVersionW
)))
2728 return E_INVALIDARG
;
2731 static HRESULT
internal_getProperty(const saxreader
* This
, const WCHAR
*prop
, VARIANT
*value
, BOOL vb
)
2733 TRACE("(%p)->(%s)\n", This
, debugstr_w(prop
));
2735 if (!value
) return E_POINTER
;
2737 if (!memcmp(PropertyLexicalHandlerW
, prop
, sizeof(PropertyLexicalHandlerW
)))
2739 V_VT(value
) = VT_UNKNOWN
;
2740 saxreader_get_handler(This
, SAXLexicalHandler
, vb
, (void**)&V_UNKNOWN(value
));
2744 if (!memcmp(PropertyDeclHandlerW
, prop
, sizeof(PropertyDeclHandlerW
)))
2746 V_VT(value
) = VT_UNKNOWN
;
2747 saxreader_get_handler(This
, SAXDeclHandler
, vb
, (void**)&V_UNKNOWN(value
));
2751 if (!memcmp(PropertyXmlDeclVersionW
, prop
, sizeof(PropertyXmlDeclVersionW
)))
2753 V_VT(value
) = VT_BSTR
;
2754 V_BSTR(value
) = SysAllocString(This
->xmldecl_version
);
2758 FIXME("(%p)->(%s) unsupported property\n", This
, debugstr_w(prop
));
2763 /*** IVBSAXXMLReader interface ***/
2764 /*** IUnknown methods ***/
2765 static HRESULT WINAPI
saxxmlreader_QueryInterface(IVBSAXXMLReader
* iface
, REFIID riid
, void **ppvObject
)
2767 saxreader
*This
= impl_from_IVBSAXXMLReader( iface
);
2769 TRACE("%p %s %p\n", This
, debugstr_guid( riid
), ppvObject
);
2773 if ( IsEqualGUID( riid
, &IID_IUnknown
) ||
2774 IsEqualGUID( riid
, &IID_IDispatch
) ||
2775 IsEqualGUID( riid
, &IID_IVBSAXXMLReader
))
2779 else if( IsEqualGUID( riid
, &IID_ISAXXMLReader
))
2781 *ppvObject
= &This
->ISAXXMLReader_iface
;
2783 else if (dispex_query_interface(&This
->dispex
, riid
, ppvObject
))
2785 return *ppvObject
? S_OK
: E_NOINTERFACE
;
2789 FIXME("interface %s not implemented\n", debugstr_guid(riid
));
2790 return E_NOINTERFACE
;
2793 IVBSAXXMLReader_AddRef( iface
);
2798 static ULONG WINAPI
saxxmlreader_AddRef(IVBSAXXMLReader
* iface
)
2800 saxreader
*This
= impl_from_IVBSAXXMLReader( iface
);
2801 TRACE("%p\n", This
);
2802 return InterlockedIncrement( &This
->ref
);
2805 static ULONG WINAPI
saxxmlreader_Release(
2806 IVBSAXXMLReader
* iface
)
2808 saxreader
*This
= impl_from_IVBSAXXMLReader( iface
);
2811 TRACE("%p\n", This
);
2813 ref
= InterlockedDecrement( &This
->ref
);
2818 for (i
= 0; i
< SAXHandler_Last
; i
++)
2820 struct saxanyhandler_iface
*saxiface
= &This
->saxhandlers
[i
].u
.anyhandler
;
2822 if (saxiface
->handler
)
2823 IUnknown_Release(saxiface
->handler
);
2825 if (saxiface
->vbhandler
)
2826 IUnknown_Release(saxiface
->vbhandler
);
2829 SysFreeString(This
->xmldecl_version
);
2830 free_bstr_pool(&This
->pool
);
2832 release_dispex(&This
->dispex
);
2839 static HRESULT WINAPI
saxxmlreader_GetTypeInfoCount( IVBSAXXMLReader
*iface
, UINT
* pctinfo
)
2841 saxreader
*This
= impl_from_IVBSAXXMLReader( iface
);
2842 return IDispatchEx_GetTypeInfoCount(&This
->dispex
.IDispatchEx_iface
, pctinfo
);
2845 static HRESULT WINAPI
saxxmlreader_GetTypeInfo(
2846 IVBSAXXMLReader
*iface
,
2847 UINT iTInfo
, LCID lcid
, ITypeInfo
** ppTInfo
)
2849 saxreader
*This
= impl_from_IVBSAXXMLReader( iface
);
2850 return IDispatchEx_GetTypeInfo(&This
->dispex
.IDispatchEx_iface
,
2851 iTInfo
, lcid
, ppTInfo
);
2854 static HRESULT WINAPI
saxxmlreader_GetIDsOfNames(
2855 IVBSAXXMLReader
*iface
,
2857 LPOLESTR
* rgszNames
,
2862 saxreader
*This
= impl_from_IVBSAXXMLReader( iface
);
2863 return IDispatchEx_GetIDsOfNames(&This
->dispex
.IDispatchEx_iface
,
2864 riid
, rgszNames
, cNames
, lcid
, rgDispId
);
2867 static HRESULT WINAPI
saxxmlreader_Invoke(
2868 IVBSAXXMLReader
*iface
,
2869 DISPID dispIdMember
,
2873 DISPPARAMS
* pDispParams
,
2874 VARIANT
* pVarResult
,
2875 EXCEPINFO
* pExcepInfo
,
2878 saxreader
*This
= impl_from_IVBSAXXMLReader( iface
);
2879 return IDispatchEx_Invoke(&This
->dispex
.IDispatchEx_iface
,
2880 dispIdMember
, riid
, lcid
, wFlags
, pDispParams
, pVarResult
, pExcepInfo
, puArgErr
);
2883 /*** IVBSAXXMLReader methods ***/
2884 static HRESULT WINAPI
saxxmlreader_getFeature(
2885 IVBSAXXMLReader
* iface
,
2886 const WCHAR
*feature_name
,
2887 VARIANT_BOOL
*value
)
2889 saxreader
*This
= impl_from_IVBSAXXMLReader( iface
);
2890 saxreader_feature feature
;
2892 TRACE("(%p)->(%s %p)\n", This
, debugstr_w(feature_name
), value
);
2894 feature
= get_saxreader_feature(feature_name
);
2895 if (feature
== Namespaces
|| feature
== NamespacePrefixes
)
2896 return get_feature_value(This
, feature
, value
);
2898 FIXME("(%p)->(%s %p) stub\n", This
, debugstr_w(feature_name
), value
);
2902 static HRESULT WINAPI
saxxmlreader_putFeature(
2903 IVBSAXXMLReader
* iface
,
2904 const WCHAR
*feature_name
,
2907 saxreader
*This
= impl_from_IVBSAXXMLReader( iface
);
2908 saxreader_feature feature
;
2910 TRACE("(%p)->(%s %x)\n", This
, debugstr_w(feature_name
), value
);
2912 feature
= get_saxreader_feature(feature_name
);
2914 /* accepted cases */
2915 if ((feature
== ExternalGeneralEntities
&& value
== VARIANT_FALSE
) ||
2916 (feature
== ExternalParameterEntities
&& value
== VARIANT_FALSE
) ||
2917 feature
== Namespaces
||
2918 feature
== NamespacePrefixes
)
2920 return set_feature_value(This
, feature
, value
);
2923 if (feature
== LexicalHandlerParEntities
|| feature
== ProhibitDTD
)
2925 FIXME("(%p)->(%s %x) stub\n", This
, debugstr_w(feature_name
), value
);
2926 return set_feature_value(This
, feature
, value
);
2929 FIXME("(%p)->(%s %x) stub\n", This
, debugstr_w(feature_name
), value
);
2933 static HRESULT WINAPI
saxxmlreader_getProperty(
2934 IVBSAXXMLReader
* iface
,
2938 saxreader
*This
= impl_from_IVBSAXXMLReader( iface
);
2939 return internal_getProperty(This
, prop
, value
, TRUE
);
2942 static HRESULT WINAPI
saxxmlreader_putProperty(
2943 IVBSAXXMLReader
* iface
,
2947 saxreader
*This
= impl_from_IVBSAXXMLReader( iface
);
2948 return internal_putProperty(This
, pProp
, value
, TRUE
);
2951 static HRESULT WINAPI
saxxmlreader_get_entityResolver(
2952 IVBSAXXMLReader
* iface
,
2953 IVBSAXEntityResolver
**resolver
)
2955 saxreader
*This
= impl_from_IVBSAXXMLReader( iface
);
2956 return saxreader_get_handler(This
, SAXEntityResolver
, TRUE
, (void**)resolver
);
2959 static HRESULT WINAPI
saxxmlreader_put_entityResolver(
2960 IVBSAXXMLReader
* iface
,
2961 IVBSAXEntityResolver
*resolver
)
2963 saxreader
*This
= impl_from_IVBSAXXMLReader( iface
);
2964 return saxreader_put_handler(This
, SAXEntityResolver
, resolver
, TRUE
);
2967 static HRESULT WINAPI
saxxmlreader_get_contentHandler(
2968 IVBSAXXMLReader
* iface
,
2969 IVBSAXContentHandler
**handler
)
2971 saxreader
*This
= impl_from_IVBSAXXMLReader( iface
);
2972 return saxreader_get_handler(This
, SAXContentHandler
, TRUE
, (void**)handler
);
2975 static HRESULT WINAPI
saxxmlreader_put_contentHandler(
2976 IVBSAXXMLReader
* iface
,
2977 IVBSAXContentHandler
*handler
)
2979 saxreader
*This
= impl_from_IVBSAXXMLReader( iface
);
2980 return saxreader_put_handler(This
, SAXContentHandler
, handler
, TRUE
);
2983 static HRESULT WINAPI
saxxmlreader_get_dtdHandler(
2984 IVBSAXXMLReader
* iface
,
2985 IVBSAXDTDHandler
**handler
)
2987 saxreader
*This
= impl_from_IVBSAXXMLReader( iface
);
2988 return saxreader_get_handler(This
, SAXDTDHandler
, TRUE
, (void**)handler
);
2991 static HRESULT WINAPI
saxxmlreader_put_dtdHandler(
2992 IVBSAXXMLReader
* iface
,
2993 IVBSAXDTDHandler
*handler
)
2995 saxreader
*This
= impl_from_IVBSAXXMLReader( iface
);
2996 return saxreader_put_handler(This
, SAXDTDHandler
, handler
, TRUE
);
2999 static HRESULT WINAPI
saxxmlreader_get_errorHandler(
3000 IVBSAXXMLReader
* iface
,
3001 IVBSAXErrorHandler
**handler
)
3003 saxreader
*This
= impl_from_IVBSAXXMLReader( iface
);
3004 return saxreader_get_handler(This
, SAXErrorHandler
, TRUE
, (void**)handler
);
3007 static HRESULT WINAPI
saxxmlreader_put_errorHandler(
3008 IVBSAXXMLReader
* iface
,
3009 IVBSAXErrorHandler
*handler
)
3011 saxreader
*This
= impl_from_IVBSAXXMLReader( iface
);
3012 return saxreader_put_handler(This
, SAXErrorHandler
, handler
, TRUE
);
3015 static HRESULT WINAPI
saxxmlreader_get_baseURL(
3016 IVBSAXXMLReader
* iface
,
3017 const WCHAR
**pBaseUrl
)
3019 saxreader
*This
= impl_from_IVBSAXXMLReader( iface
);
3021 FIXME("(%p)->(%p) stub\n", This
, pBaseUrl
);
3025 static HRESULT WINAPI
saxxmlreader_put_baseURL(
3026 IVBSAXXMLReader
* iface
,
3027 const WCHAR
*pBaseUrl
)
3029 saxreader
*This
= impl_from_IVBSAXXMLReader( iface
);
3031 FIXME("(%p)->(%s) stub\n", This
, debugstr_w(pBaseUrl
));
3035 static HRESULT WINAPI
saxxmlreader_get_secureBaseURL(
3036 IVBSAXXMLReader
* iface
,
3037 const WCHAR
**pSecureBaseUrl
)
3039 saxreader
*This
= impl_from_IVBSAXXMLReader( iface
);
3041 FIXME("(%p)->(%p) stub\n", This
, pSecureBaseUrl
);
3046 static HRESULT WINAPI
saxxmlreader_put_secureBaseURL(
3047 IVBSAXXMLReader
* iface
,
3048 const WCHAR
*secureBaseUrl
)
3050 saxreader
*This
= impl_from_IVBSAXXMLReader( iface
);
3052 FIXME("(%p)->(%s) stub\n", This
, debugstr_w(secureBaseUrl
));
3056 static HRESULT WINAPI
saxxmlreader_parse(
3057 IVBSAXXMLReader
* iface
,
3060 saxreader
*This
= impl_from_IVBSAXXMLReader( iface
);
3061 return internal_parse(This
, varInput
, TRUE
);
3064 static HRESULT WINAPI
saxxmlreader_parseURL(
3065 IVBSAXXMLReader
* iface
,
3068 saxreader
*This
= impl_from_IVBSAXXMLReader( iface
);
3069 return internal_parseURL(This
, url
, TRUE
);
3072 static const struct IVBSAXXMLReaderVtbl VBSAXXMLReaderVtbl
=
3074 saxxmlreader_QueryInterface
,
3075 saxxmlreader_AddRef
,
3076 saxxmlreader_Release
,
3077 saxxmlreader_GetTypeInfoCount
,
3078 saxxmlreader_GetTypeInfo
,
3079 saxxmlreader_GetIDsOfNames
,
3080 saxxmlreader_Invoke
,
3081 saxxmlreader_getFeature
,
3082 saxxmlreader_putFeature
,
3083 saxxmlreader_getProperty
,
3084 saxxmlreader_putProperty
,
3085 saxxmlreader_get_entityResolver
,
3086 saxxmlreader_put_entityResolver
,
3087 saxxmlreader_get_contentHandler
,
3088 saxxmlreader_put_contentHandler
,
3089 saxxmlreader_get_dtdHandler
,
3090 saxxmlreader_put_dtdHandler
,
3091 saxxmlreader_get_errorHandler
,
3092 saxxmlreader_put_errorHandler
,
3093 saxxmlreader_get_baseURL
,
3094 saxxmlreader_put_baseURL
,
3095 saxxmlreader_get_secureBaseURL
,
3096 saxxmlreader_put_secureBaseURL
,
3098 saxxmlreader_parseURL
3101 /*** ISAXXMLReader interface ***/
3102 /*** IUnknown methods ***/
3103 static HRESULT WINAPI
isaxxmlreader_QueryInterface(ISAXXMLReader
* iface
, REFIID riid
, void **ppvObject
)
3105 saxreader
*This
= impl_from_ISAXXMLReader( iface
);
3106 return saxxmlreader_QueryInterface(&This
->IVBSAXXMLReader_iface
, riid
, ppvObject
);
3109 static ULONG WINAPI
isaxxmlreader_AddRef(ISAXXMLReader
* iface
)
3111 saxreader
*This
= impl_from_ISAXXMLReader( iface
);
3112 return saxxmlreader_AddRef(&This
->IVBSAXXMLReader_iface
);
3115 static ULONG WINAPI
isaxxmlreader_Release(ISAXXMLReader
* iface
)
3117 saxreader
*This
= impl_from_ISAXXMLReader( iface
);
3118 return saxxmlreader_Release(&This
->IVBSAXXMLReader_iface
);
3121 /*** ISAXXMLReader methods ***/
3122 static HRESULT WINAPI
isaxxmlreader_getFeature(
3123 ISAXXMLReader
* iface
,
3124 const WCHAR
*pFeature
,
3125 VARIANT_BOOL
*pValue
)
3127 saxreader
*This
= impl_from_ISAXXMLReader( iface
);
3128 return IVBSAXXMLReader_getFeature(&This
->IVBSAXXMLReader_iface
, pFeature
, pValue
);
3131 static HRESULT WINAPI
isaxxmlreader_putFeature(
3132 ISAXXMLReader
* iface
,
3133 const WCHAR
*pFeature
,
3134 VARIANT_BOOL vfValue
)
3136 saxreader
*This
= impl_from_ISAXXMLReader( iface
);
3137 return IVBSAXXMLReader_putFeature(&This
->IVBSAXXMLReader_iface
, pFeature
, vfValue
);
3140 static HRESULT WINAPI
isaxxmlreader_getProperty(
3141 ISAXXMLReader
* iface
,
3145 saxreader
*This
= impl_from_ISAXXMLReader( iface
);
3146 return internal_getProperty(This
, prop
, value
, FALSE
);
3149 static HRESULT WINAPI
isaxxmlreader_putProperty(
3150 ISAXXMLReader
* iface
,
3154 saxreader
*This
= impl_from_ISAXXMLReader( iface
);
3155 return internal_putProperty(This
, pProp
, value
, FALSE
);
3158 static HRESULT WINAPI
isaxxmlreader_getEntityResolver(
3159 ISAXXMLReader
* iface
,
3160 ISAXEntityResolver
**resolver
)
3162 saxreader
*This
= impl_from_ISAXXMLReader( iface
);
3163 return saxreader_get_handler(This
, SAXEntityResolver
, FALSE
, (void**)resolver
);
3166 static HRESULT WINAPI
isaxxmlreader_putEntityResolver(
3167 ISAXXMLReader
* iface
,
3168 ISAXEntityResolver
*resolver
)
3170 saxreader
*This
= impl_from_ISAXXMLReader( iface
);
3171 return saxreader_put_handler(This
, SAXEntityResolver
, resolver
, FALSE
);
3174 static HRESULT WINAPI
isaxxmlreader_getContentHandler(
3175 ISAXXMLReader
* iface
,
3176 ISAXContentHandler
**handler
)
3178 saxreader
*This
= impl_from_ISAXXMLReader( iface
);
3179 return saxreader_get_handler(This
, SAXContentHandler
, FALSE
, (void**)handler
);
3182 static HRESULT WINAPI
isaxxmlreader_putContentHandler(
3183 ISAXXMLReader
* iface
,
3184 ISAXContentHandler
*handler
)
3186 saxreader
*This
= impl_from_ISAXXMLReader( iface
);
3187 return saxreader_put_handler(This
, SAXContentHandler
, handler
, FALSE
);
3190 static HRESULT WINAPI
isaxxmlreader_getDTDHandler(
3191 ISAXXMLReader
* iface
,
3192 ISAXDTDHandler
**handler
)
3194 saxreader
*This
= impl_from_ISAXXMLReader( iface
);
3195 return saxreader_get_handler(This
, SAXDTDHandler
, FALSE
, (void**)handler
);
3198 static HRESULT WINAPI
isaxxmlreader_putDTDHandler(
3199 ISAXXMLReader
* iface
,
3200 ISAXDTDHandler
*handler
)
3202 saxreader
*This
= impl_from_ISAXXMLReader( iface
);
3203 return saxreader_put_handler(This
, SAXDTDHandler
, handler
, FALSE
);
3206 static HRESULT WINAPI
isaxxmlreader_getErrorHandler(
3207 ISAXXMLReader
* iface
,
3208 ISAXErrorHandler
**handler
)
3210 saxreader
*This
= impl_from_ISAXXMLReader( iface
);
3211 return saxreader_get_handler(This
, SAXErrorHandler
, FALSE
, (void**)handler
);
3214 static HRESULT WINAPI
isaxxmlreader_putErrorHandler(ISAXXMLReader
* iface
, ISAXErrorHandler
*handler
)
3216 saxreader
*This
= impl_from_ISAXXMLReader( iface
);
3217 return saxreader_put_handler(This
, SAXErrorHandler
, handler
, FALSE
);
3220 static HRESULT WINAPI
isaxxmlreader_getBaseURL(
3221 ISAXXMLReader
* iface
,
3222 const WCHAR
**pBaseUrl
)
3224 saxreader
*This
= impl_from_ISAXXMLReader( iface
);
3225 return IVBSAXXMLReader_get_baseURL(&This
->IVBSAXXMLReader_iface
, pBaseUrl
);
3228 static HRESULT WINAPI
isaxxmlreader_putBaseURL(
3229 ISAXXMLReader
* iface
,
3230 const WCHAR
*pBaseUrl
)
3232 saxreader
*This
= impl_from_ISAXXMLReader( iface
);
3233 return IVBSAXXMLReader_put_baseURL(&This
->IVBSAXXMLReader_iface
, pBaseUrl
);
3236 static HRESULT WINAPI
isaxxmlreader_getSecureBaseURL(
3237 ISAXXMLReader
* iface
,
3238 const WCHAR
**pSecureBaseUrl
)
3240 saxreader
*This
= impl_from_ISAXXMLReader( iface
);
3241 return IVBSAXXMLReader_get_secureBaseURL(&This
->IVBSAXXMLReader_iface
, pSecureBaseUrl
);
3244 static HRESULT WINAPI
isaxxmlreader_putSecureBaseURL(
3245 ISAXXMLReader
* iface
,
3246 const WCHAR
*secureBaseUrl
)
3248 saxreader
*This
= impl_from_ISAXXMLReader( iface
);
3249 return IVBSAXXMLReader_put_secureBaseURL(&This
->IVBSAXXMLReader_iface
, secureBaseUrl
);
3252 static HRESULT WINAPI
isaxxmlreader_parse(
3253 ISAXXMLReader
* iface
,
3256 saxreader
*This
= impl_from_ISAXXMLReader( iface
);
3257 return internal_parse(This
, varInput
, FALSE
);
3260 static HRESULT WINAPI
isaxxmlreader_parseURL(
3261 ISAXXMLReader
* iface
,
3264 saxreader
*This
= impl_from_ISAXXMLReader( iface
);
3265 return internal_parseURL(This
, url
, FALSE
);
3268 static const struct ISAXXMLReaderVtbl SAXXMLReaderVtbl
=
3270 isaxxmlreader_QueryInterface
,
3271 isaxxmlreader_AddRef
,
3272 isaxxmlreader_Release
,
3273 isaxxmlreader_getFeature
,
3274 isaxxmlreader_putFeature
,
3275 isaxxmlreader_getProperty
,
3276 isaxxmlreader_putProperty
,
3277 isaxxmlreader_getEntityResolver
,
3278 isaxxmlreader_putEntityResolver
,
3279 isaxxmlreader_getContentHandler
,
3280 isaxxmlreader_putContentHandler
,
3281 isaxxmlreader_getDTDHandler
,
3282 isaxxmlreader_putDTDHandler
,
3283 isaxxmlreader_getErrorHandler
,
3284 isaxxmlreader_putErrorHandler
,
3285 isaxxmlreader_getBaseURL
,
3286 isaxxmlreader_putBaseURL
,
3287 isaxxmlreader_getSecureBaseURL
,
3288 isaxxmlreader_putSecureBaseURL
,
3289 isaxxmlreader_parse
,
3290 isaxxmlreader_parseURL
3293 static const tid_t saxreader_iface_tids
[] = {
3294 IVBSAXXMLReader_tid
,
3297 static dispex_static_data_t saxreader_dispex
= {
3299 IVBSAXXMLReader_tid
,
3301 saxreader_iface_tids
3304 HRESULT
SAXXMLReader_create(MSXML_VERSION version
, IUnknown
*outer
, LPVOID
*ppObj
)
3308 TRACE("(%p, %p)\n", outer
, ppObj
);
3310 reader
= heap_alloc( sizeof (*reader
) );
3312 return E_OUTOFMEMORY
;
3314 reader
->IVBSAXXMLReader_iface
.lpVtbl
= &VBSAXXMLReaderVtbl
;
3315 reader
->ISAXXMLReader_iface
.lpVtbl
= &SAXXMLReaderVtbl
;
3317 memset(reader
->saxhandlers
, 0, sizeof(reader
->saxhandlers
));
3318 reader
->isParsing
= FALSE
;
3319 reader
->xmldecl_version
= NULL
;
3320 reader
->pool
.pool
= NULL
;
3321 reader
->pool
.index
= 0;
3322 reader
->pool
.len
= 0;
3323 reader
->features
= Namespaces
| NamespacePrefixes
;
3324 reader
->version
= version
;
3326 init_dispex(&reader
->dispex
, (IUnknown
*)&reader
->IVBSAXXMLReader_iface
, &saxreader_dispex
);
3328 memset(&reader
->sax
, 0, sizeof(xmlSAXHandler
));
3329 reader
->sax
.initialized
= XML_SAX2_MAGIC
;
3330 reader
->sax
.startDocument
= libxmlStartDocument
;
3331 reader
->sax
.endDocument
= libxmlEndDocument
;
3332 reader
->sax
.startElementNs
= libxmlStartElementNS
;
3333 reader
->sax
.endElementNs
= libxmlEndElementNS
;
3334 reader
->sax
.characters
= libxmlCharacters
;
3335 reader
->sax
.setDocumentLocator
= libxmlSetDocumentLocator
;
3336 reader
->sax
.comment
= libxmlComment
;
3337 reader
->sax
.error
= libxmlFatalError
;
3338 reader
->sax
.fatalError
= libxmlFatalError
;
3339 reader
->sax
.cdataBlock
= libxml_cdatablock
;
3340 reader
->sax
.resolveEntity
= libxmlresolveentity
;
3342 *ppObj
= &reader
->IVBSAXXMLReader_iface
;
3344 TRACE("returning iface %p\n", *ppObj
);
3351 HRESULT
SAXXMLReader_create(MSXML_VERSION version
, IUnknown
*pUnkOuter
, LPVOID
*ppObj
)
3353 MESSAGE("This program tried to use a SAX XML Reader object, but\n"
3354 "libxml2 support was not present at compile time.\n");