[PATCH 3/8] msxml3: Implement domdoc schema validation
Adam Martinson
amartinson at codeweavers.com
Thu Oct 28 20:14:03 CDT 2010
---
dlls/msxml3/domdoc.c | 127 ++++++++++++++++++++++++++++++++------------
dlls/msxml3/tests/domdoc.c | 2 +-
2 files changed, 93 insertions(+), 36 deletions(-)
diff --git a/dlls/msxml3/domdoc.c b/dlls/msxml3/domdoc.c
index 8a21402..75f6c1c 100644
--- a/dlls/msxml3/domdoc.c
+++ b/dlls/msxml3/domdoc.c
@@ -116,7 +116,7 @@ struct domdoc
VARIANT_BOOL resolving;
VARIANT_BOOL preserving;
domdoc_properties* properties;
- IXMLDOMSchemaCollection *schema;
+ IXMLDOMSchemaCollection2* schema;
bsc_t *bsc;
HRESULT error;
@@ -875,7 +875,7 @@ static ULONG WINAPI domdoc_Release(
if (This->site)
IUnknown_Release( This->site );
destroy_xmlnode(&This->node);
- if(This->schema) IXMLDOMSchemaCollection_Release( This->schema );
+ if(This->schema) IXMLDOMSchemaCollection2_Release(This->schema);
if (This->stream) IStream_Release(This->stream);
HeapFree( GetProcessHeap(), 0, This );
}
@@ -2385,7 +2385,7 @@ static HRESULT WINAPI domdoc_get_schemas(
{
domdoc *This = impl_from_IXMLDOMDocument3( iface );
HRESULT hr = S_FALSE;
- IXMLDOMSchemaCollection *cur_schema = This->schema;
+ IXMLDOMSchemaCollection2* cur_schema = This->schema;
TRACE("(%p)->(%p)\n", This, var1);
@@ -2394,7 +2394,7 @@ static HRESULT WINAPI domdoc_get_schemas(
if(cur_schema)
{
- hr = IXMLDOMSchemaCollection_QueryInterface(cur_schema, &IID_IDispatch, (void**)&V_DISPATCH(var1));
+ hr = IXMLDOMSchemaCollection2_QueryInterface(cur_schema, &IID_IDispatch, (void**)&V_DISPATCH(var1));
if(SUCCEEDED(hr))
V_VT(var1) = VT_DISPATCH;
}
@@ -2407,7 +2407,7 @@ static HRESULT WINAPI domdoc_putref_schemas(
{
domdoc *This = impl_from_IXMLDOMDocument3( iface );
HRESULT hr = E_FAIL;
- IXMLDOMSchemaCollection *new_schema = NULL;
+ IXMLDOMSchemaCollection2* new_schema = NULL;
FIXME("(%p): semi-stub\n", This);
switch(V_VT(&var1))
@@ -2431,8 +2431,8 @@ static HRESULT WINAPI domdoc_putref_schemas(
if(SUCCEEDED(hr))
{
- IXMLDOMSchemaCollection *old_schema = InterlockedExchangePointer((void**)&This->schema, new_schema);
- if(old_schema) IXMLDOMSchemaCollection_Release(old_schema);
+ IXMLDOMSchemaCollection2* old_schema = InterlockedExchangePointer((void**)&This->schema, new_schema);
+ if(old_schema) IXMLDOMSchemaCollection2_Release(old_schema);
}
return hr;
@@ -2442,7 +2442,7 @@ static void LIBXML2_LOG_CALLBACK validate_error(void* ctx, char const* msg, ...)
{
va_list ap;
va_start(ap, msg);
- LIBXML2_CALLBACK_ERR(domdoc_validate, msg, ap);
+ LIBXML2_CALLBACK_ERR(domdoc_validateNode, msg, ap);
va_end(ap);
}
@@ -2450,44 +2450,111 @@ static void LIBXML2_LOG_CALLBACK validate_warning(void* ctx, char const* msg, ..
{
va_list ap;
va_start(ap, msg);
- LIBXML2_CALLBACK_WARN(domdoc_validate, msg, ap);
+ LIBXML2_CALLBACK_WARN(domdoc_validateNode, msg, ap);
va_end(ap);
}
-static HRESULT WINAPI domdoc_validate(
+static HRESULT WINAPI domdoc_validateNode(
IXMLDOMDocument3* iface,
+ IXMLDOMNode* node,
IXMLDOMParseError** err)
{
- domdoc *This = impl_from_IXMLDOMDocument3( iface );
- LONG state;
- xmlValidCtxtPtr vctx;
+ domdoc* This = impl_from_IXMLDOMDocument3(iface);
+ LONG state, err_code = 0;
+ HRESULT hr = S_OK;
+ int validated = 0;
- TRACE("(%p)->(%p)\n", This, err);
+ TRACE("(%p)->(%p, %p)\n", This, node, err);
domdoc_get_readyState(iface, &state);
if (state != READYSTATE_COMPLETE)
{
if (err)
- *err = create_parseError(0, NULL, NULL, NULL, 0, 0, 0);
+ *err = create_parseError(err_code, NULL, NULL, NULL, 0, 0, 0);
return E_PENDING;
}
- vctx = xmlNewValidCtxt();
- vctx->error = validate_error;
- vctx->warning = validate_warning;
+ if (!node)
+ {
+ if (err)
+ *err = create_parseError(err_code, NULL, NULL, NULL, 0, 0, 0);
+ return E_POINTER;
+ }
+
+ if (!get_node_obj(node)->node || get_node_obj(node)->node->doc != get_doc(This))
+ {
+ if (err)
+ *err = create_parseError(err_code, NULL, NULL, NULL, 0, 0, 0);
+ return E_FAIL;
+ }
- if (xmlValidateDocument(vctx, get_doc(This)))
+ if (!(get_doc(This)->properties & XML_DOC_WELLFORMED))
{
+ ERR("doc not well-formed");
if (err)
- *err = create_parseError(0, NULL, NULL, NULL, 0, 0, 0);
+ *err = create_parseError(E_XML_NOTWF, NULL, NULL, NULL, 0, 0, 0);
+ return S_FALSE;
+ }
+
+ /* DTD validation */
+ if (get_doc(This)->intSubset || get_doc(This)->extSubset)
+ {
+ xmlValidCtxtPtr vctx = xmlNewValidCtxt();
+ vctx->error = validate_error;
+ vctx->warning = validate_warning;
+ ++validated;
+
+ if (!((node == (IXMLDOMNode*)iface)?
+ xmlValidateDocument(vctx, get_doc(This)) :
+ xmlValidateElement(vctx, get_doc(This), get_node_obj(node)->node)))
+ {
+ /* TODO: get a real error code here */
+ TRACE("DTD validation failed\n");
+ err_code = E_XML_INVALID;
+ hr = S_FALSE;
+ }
xmlFreeValidCtxt(vctx);
- return S_OK;
}
- FIXME("partial stub!\n");
+ /* Schema validation */
+ if (hr == S_OK && This->schema != NULL)
+ {
+
+ hr = SchemaCache_validate_tree(This->schema, get_node_obj(node)->node);
+ if (!FAILED(hr))
+ {
+ ++validated;
+ /* TODO: get a real error code here */
+ TRACE("schema validation failed\n");
+ if (hr != S_OK)
+ err_code = E_XML_INVALID;
+ }
+ else
+ {
+ /* not really OK, just didn't find a schema for the ns */
+ hr = S_OK;
+ }
+ }
+
+ if (!validated)
+ {
+ TRACE("no DTD or schema found\n");
+ err_code = E_XML_NODTD;
+ hr = S_FALSE;
+ }
+
if (err)
- *err = create_parseError(0xC00CE223, NULL, NULL, NULL, 0, 0, 0);
- xmlFreeValidCtxt(vctx);
- return S_FALSE;
+ *err = create_parseError(err_code, NULL, NULL, NULL, 0, 0, 0);
+
+ return hr;
+}
+
+static HRESULT WINAPI domdoc_validate(
+ IXMLDOMDocument3* iface,
+ IXMLDOMParseError** err)
+{
+ domdoc *This = impl_from_IXMLDOMDocument3( iface );
+ TRACE("(%p)->(%p)\n", This, err);
+ return domdoc_validateNode(iface, (IXMLDOMNode*)iface, err);
}
static HRESULT WINAPI domdoc_setProperty(
@@ -2723,16 +2790,6 @@ static HRESULT WINAPI domdoc_getProperty(
return E_FAIL;
}
-static HRESULT WINAPI domdoc_validateNode(
- IXMLDOMDocument3* iface,
- IXMLDOMNode* node,
- IXMLDOMParseError** error)
-{
- domdoc *This = impl_from_IXMLDOMDocument3( iface );
- FIXME("(%p)->(%p %p): stub\n", This, node, error);
- return E_NOTIMPL;
-}
-
static HRESULT WINAPI domdoc_importNode(
IXMLDOMDocument3* iface,
IXMLDOMNode* node,
diff --git a/dlls/msxml3/tests/domdoc.c b/dlls/msxml3/tests/domdoc.c
index 86779e0..da97048 100644
--- a/dlls/msxml3/tests/domdoc.c
+++ b/dlls/msxml3/tests/domdoc.c
@@ -3477,7 +3477,7 @@ static void test_IXMLDOMDocument2(void)
res = 0;
ole_check(IXMLDOMParseError_get_errorCode(err, &res));
/* XML_E_NODTD */
- todo_wine ok(res == E_XML_NODTD, "got %08x\n", res);
+ ok(res == E_XML_NODTD, "got %08x\n", res);
IXMLDOMParseError_Release(err);
}
--
1.7.2.3
--------------070307060504060109050509--
More information about the wine-patches
mailing list