[PATCH 09/14] xmllite: Implement GetNamespaceUri()
Nikolay Sivov
nsivov at codeweavers.com
Fri Dec 9 07:38:29 CST 2016
Signed-off-by: Nikolay Sivov <nsivov at codeweavers.com>
---
dlls/xmllite/reader.c | 103 +++++++++++++++++++++++++++++++++++++++++++++++---
1 file changed, 98 insertions(+), 5 deletions(-)
diff --git a/dlls/xmllite/reader.c b/dlls/xmllite/reader.c
index 09c8e30..24a061c 100644
--- a/dlls/xmllite/reader.c
+++ b/dlls/xmllite/reader.c
@@ -216,8 +216,10 @@ typedef struct
} strval;
static WCHAR emptyW[] = {0};
+static WCHAR xmlW[] = {'x','m','l',0};
static WCHAR xmlnsW[] = {'x','m','l','n','s',0};
static const strval strval_empty = { emptyW };
+static const strval strval_xml = { xmlW, 3 };
static const strval strval_xmlns = { xmlnsW, 5 };
struct attribute
@@ -2881,12 +2883,103 @@ static HRESULT WINAPI xmlreader_GetQualifiedName(IXmlReader* iface, LPCWSTR *nam
return S_OK;
}
-static HRESULT WINAPI xmlreader_GetNamespaceUri(IXmlReader* iface,
- LPCWSTR *namespaceUri,
- UINT *namespaceUri_length)
+static struct ns *reader_lookup_ns(xmlreader *reader, const strval *prefix)
{
- FIXME("(%p %p %p): stub\n", iface, namespaceUri, namespaceUri_length);
- return E_NOTIMPL;
+ struct list *nslist = prefix ? &reader->ns : &reader->nsdef;
+ struct ns *ns;
+
+ LIST_FOR_EACH_ENTRY_REV(ns, nslist, struct ns, entry) {
+ if (strval_eq(reader, prefix, &ns->prefix))
+ return ns;
+ }
+
+ return NULL;
+}
+
+static struct ns *reader_lookup_nsdef(xmlreader *reader)
+{
+ if (list_empty(&reader->nsdef))
+ return NULL;
+
+ return LIST_ENTRY(list_head(&reader->nsdef), struct ns, entry);
+}
+
+static HRESULT WINAPI xmlreader_GetNamespaceUri(IXmlReader* iface, const WCHAR **uri, UINT *len)
+{
+ xmlreader *This = impl_from_IXmlReader(iface);
+ const strval *prefix = &This->strvalues[StringValue_Prefix];
+ XmlNodeType nodetype;
+ struct ns *ns;
+ UINT length;
+
+ TRACE("(%p %p %p)\n", iface, uri, len);
+
+ if (!len)
+ len = &length;
+
+ *uri = NULL;
+ *len = 0;
+
+ switch ((nodetype = reader_get_nodetype(This)))
+ {
+ case XmlNodeType_Attribute:
+ {
+ static const WCHAR xmlns_uriW[] = {'h','t','t','p',':','/','/','w','w','w','.','w','3','.','o','r','g','/',
+ '2','0','0','0','/','x','m','l','n','s','/',0};
+ static const WCHAR xml_uriW[] = {'h','t','t','p',':','/','/','w','w','w','.','w','3','.','o','r','g','/',
+ 'X','M','L','/','1','9','9','8','/','n','a','m','e','s','p','a','c','e',0};
+ const strval *local = &This->strvalues[StringValue_LocalName];
+
+ /* check for reserved prefixes first */
+ if ((strval_eq(This, prefix, &strval_empty) && strval_eq(This, local, &strval_xmlns)) ||
+ strval_eq(This, prefix, &strval_xmlns))
+ {
+ *uri = xmlns_uriW;
+ *len = sizeof(xmlns_uriW)/sizeof(xmlns_uriW[0]) - 1;
+ }
+ else if (strval_eq(This, prefix, &strval_xml)) {
+ *uri = xml_uriW;
+ *len = sizeof(xml_uriW)/sizeof(xml_uriW[0]) - 1;
+ }
+
+ if (!*uri) {
+ ns = reader_lookup_ns(This, prefix);
+ if (ns) {
+ *uri = ns->uri.str;
+ *len = ns->uri.len;
+ }
+ else {
+ *uri = emptyW;
+ *len = 0;
+ }
+ }
+ }
+ break;
+ case XmlNodeType_Element:
+ case XmlNodeType_EndElement:
+ {
+ ns = reader_lookup_ns(This, prefix);
+
+ /* pick top default ns if any */
+ if (!ns)
+ ns = reader_lookup_nsdef(This);
+
+ if (ns) {
+ *uri = ns->uri.str;
+ *len = ns->uri.len;
+ }
+ else {
+ *uri = emptyW;
+ *len = 0;
+ }
+ }
+ break;
+ default:
+ FIXME("Unhandled node type %d\n", nodetype);
+ return E_NOTIMPL;
+ }
+
+ return S_OK;
}
static HRESULT WINAPI xmlreader_GetLocalName(IXmlReader* iface, LPCWSTR *name, UINT *len)
--
2.10.2
More information about the wine-patches
mailing list