msxml3: Skip leading space characters when loading from BSTR.
This commit is contained in:
parent
6589516db1
commit
e736c3e983
|
@ -78,7 +78,7 @@ static const WCHAR PropertyResolveExternalsW[] = {'R','e','s','o','l','v','e','E
|
||||||
* tests can go here (data shared between all instances).
|
* tests can go here (data shared between all instances).
|
||||||
* We need to preserve this when reloading a document,
|
* We need to preserve this when reloading a document,
|
||||||
* and also need access to it from the libxml backend. */
|
* and also need access to it from the libxml backend. */
|
||||||
typedef struct _domdoc_properties {
|
typedef struct {
|
||||||
MSXML_VERSION version;
|
MSXML_VERSION version;
|
||||||
VARIANT_BOOL preserving;
|
VARIANT_BOOL preserving;
|
||||||
IXMLDOMSchemaCollection2* schemaCache;
|
IXMLDOMSchemaCollection2* schemaCache;
|
||||||
|
@ -285,7 +285,7 @@ static xmldoc_priv * create_priv(void)
|
||||||
return priv;
|
return priv;
|
||||||
}
|
}
|
||||||
|
|
||||||
static domdoc_properties * create_properties(MSXML_VERSION version)
|
static domdoc_properties *create_properties(MSXML_VERSION version)
|
||||||
{
|
{
|
||||||
domdoc_properties *properties = heap_alloc(sizeof(domdoc_properties));
|
domdoc_properties *properties = heap_alloc(sizeof(domdoc_properties));
|
||||||
|
|
||||||
|
@ -2230,18 +2230,17 @@ static HRESULT WINAPI domdoc_abort(
|
||||||
return E_NOTIMPL;
|
return E_NOTIMPL;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
/* don't rely on data to be in BSTR format, treat it as WCHAR string */
|
/* don't rely on data to be in BSTR format, treat it as WCHAR string */
|
||||||
static HRESULT WINAPI domdoc_loadXML(
|
static HRESULT WINAPI domdoc_loadXML(
|
||||||
IXMLDOMDocument3 *iface,
|
IXMLDOMDocument3 *iface,
|
||||||
BSTR bstrXML,
|
BSTR data,
|
||||||
VARIANT_BOOL* isSuccessful )
|
VARIANT_BOOL* isSuccessful )
|
||||||
{
|
{
|
||||||
domdoc *This = impl_from_IXMLDOMDocument3( iface );
|
domdoc *This = impl_from_IXMLDOMDocument3( iface );
|
||||||
xmlDocPtr xmldoc = NULL;
|
xmlDocPtr xmldoc = NULL;
|
||||||
HRESULT hr = S_FALSE, hr2;
|
HRESULT hr = S_FALSE, hr2;
|
||||||
|
|
||||||
TRACE("(%p)->(%s %p)\n", This, debugstr_w( bstrXML ), isSuccessful );
|
TRACE("(%p)->(%s %p)\n", This, debugstr_w(data), isSuccessful );
|
||||||
|
|
||||||
assert ( &This->node );
|
assert ( &This->node );
|
||||||
|
|
||||||
|
@ -2249,9 +2248,16 @@ static HRESULT WINAPI domdoc_loadXML(
|
||||||
{
|
{
|
||||||
*isSuccessful = VARIANT_FALSE;
|
*isSuccessful = VARIANT_FALSE;
|
||||||
|
|
||||||
if ( bstrXML )
|
if (data)
|
||||||
{
|
{
|
||||||
xmldoc = doparse(This, (LPCSTR)bstrXML, lstrlenW(bstrXML) * sizeof(*bstrXML), XML_CHAR_ENCODING_UTF16LE);
|
WCHAR *ptr = data;
|
||||||
|
|
||||||
|
/* skip leading spaces if needed */
|
||||||
|
if (This->properties->version == MSXML_DEFAULT || This->properties->version == MSXML26)
|
||||||
|
while (*ptr)
|
||||||
|
if (isspaceW(*ptr)) ptr++; else break;
|
||||||
|
|
||||||
|
xmldoc = doparse(This, (char*)ptr, strlenW(ptr)*sizeof(WCHAR), XML_CHAR_ENCODING_UTF16LE);
|
||||||
if ( !xmldoc )
|
if ( !xmldoc )
|
||||||
{
|
{
|
||||||
This->error = E_FAIL;
|
This->error = E_FAIL;
|
||||||
|
|
|
@ -59,24 +59,24 @@ struct clsid_version_t
|
||||||
static const struct clsid_version_t clsid_versions_table[] =
|
static const struct clsid_version_t clsid_versions_table[] =
|
||||||
{
|
{
|
||||||
{ &CLSID_DOMDocument, MSXML_DEFAULT },
|
{ &CLSID_DOMDocument, MSXML_DEFAULT },
|
||||||
{ &CLSID_DOMDocument2, MSXML_DEFAULT },
|
{ &CLSID_DOMDocument2, MSXML2 },
|
||||||
{ &CLSID_DOMDocument26, MSXML_DEFAULT },
|
{ &CLSID_DOMDocument26, MSXML26 },
|
||||||
{ &CLSID_DOMDocument30, MSXML3 },
|
{ &CLSID_DOMDocument30, MSXML3 },
|
||||||
{ &CLSID_DOMDocument40, MSXML4 },
|
{ &CLSID_DOMDocument40, MSXML4 },
|
||||||
{ &CLSID_DOMDocument60, MSXML6 },
|
{ &CLSID_DOMDocument60, MSXML6 },
|
||||||
|
|
||||||
{ &CLSID_DOMFreeThreadedDocument, MSXML_DEFAULT },
|
{ &CLSID_DOMFreeThreadedDocument, MSXML_DEFAULT },
|
||||||
{ &CLSID_FreeThreadedDOMDocument, MSXML_DEFAULT },
|
{ &CLSID_FreeThreadedDOMDocument, MSXML_DEFAULT },
|
||||||
{ &CLSID_FreeThreadedDOMDocument26, MSXML_DEFAULT },
|
{ &CLSID_FreeThreadedDOMDocument26, MSXML26 },
|
||||||
{ &CLSID_FreeThreadedDOMDocument30, MSXML3 },
|
{ &CLSID_FreeThreadedDOMDocument30, MSXML3 },
|
||||||
{ &CLSID_FreeThreadedDOMDocument40, MSXML4 },
|
{ &CLSID_FreeThreadedDOMDocument40, MSXML4 },
|
||||||
{ &CLSID_FreeThreadedDOMDocument60, MSXML6 },
|
{ &CLSID_FreeThreadedDOMDocument60, MSXML6 },
|
||||||
|
|
||||||
{ &CLSID_XMLSchemaCache, MSXML_DEFAULT },
|
{ &CLSID_XMLSchemaCache, MSXML_DEFAULT },
|
||||||
{ &CLSID_XMLSchemaCache26, MSXML_DEFAULT },
|
{ &CLSID_XMLSchemaCache26, MSXML26 },
|
||||||
{ &CLSID_XMLSchemaCache30, MSXML3 },
|
{ &CLSID_XMLSchemaCache30, MSXML3 },
|
||||||
{ &CLSID_XMLSchemaCache40, MSXML4 },
|
{ &CLSID_XMLSchemaCache40, MSXML4 },
|
||||||
{ &CLSID_XMLSchemaCache60, MSXML6 },
|
{ &CLSID_XMLSchemaCache60, MSXML6 },
|
||||||
|
|
||||||
{ &CLSID_MXXMLWriter, MSXML_DEFAULT },
|
{ &CLSID_MXXMLWriter, MSXML_DEFAULT },
|
||||||
{ &CLSID_MXXMLWriter30, MSXML3 },
|
{ &CLSID_MXXMLWriter30, MSXML3 },
|
||||||
|
|
|
@ -31,9 +31,11 @@
|
||||||
|
|
||||||
typedef enum {
|
typedef enum {
|
||||||
MSXML_DEFAULT = 0,
|
MSXML_DEFAULT = 0,
|
||||||
MSXML3 = 30,
|
MSXML2 = 20,
|
||||||
MSXML4 = 40,
|
MSXML26 = 26,
|
||||||
MSXML6 = 60
|
MSXML3 = 30,
|
||||||
|
MSXML4 = 40,
|
||||||
|
MSXML6 = 60
|
||||||
} MSXML_VERSION;
|
} MSXML_VERSION;
|
||||||
|
|
||||||
/* typelibs */
|
/* typelibs */
|
||||||
|
|
|
@ -41,6 +41,9 @@
|
||||||
|
|
||||||
#include "wine/test.h"
|
#include "wine/test.h"
|
||||||
|
|
||||||
|
/* undef the #define in msxml2 so that we can access all versions */
|
||||||
|
#undef CLSID_DOMDocument
|
||||||
|
|
||||||
DEFINE_GUID(SID_SContainerDispatch, 0xb722be00, 0x4e68, 0x101b, 0xa2, 0xbc, 0x00, 0xaa, 0x00, 0x40, 0x47, 0x70);
|
DEFINE_GUID(SID_SContainerDispatch, 0xb722be00, 0x4e68, 0x101b, 0xa2, 0xbc, 0x00, 0xaa, 0x00, 0x40, 0x47, 0x70);
|
||||||
DEFINE_GUID(SID_UnknownSID, 0x75dd09cb, 0x6c40, 0x11d5, 0x85, 0x43, 0x00, 0xc0, 0x4f, 0xa0, 0xfb, 0xa3);
|
DEFINE_GUID(SID_UnknownSID, 0x75dd09cb, 0x6c40, 0x11d5, 0x85, 0x43, 0x00, 0xc0, 0x4f, 0xa0, 0xfb, 0xa3);
|
||||||
DEFINE_GUID(GUID_NULL,0,0,0,0,0,0,0,0,0,0,0);
|
DEFINE_GUID(GUID_NULL,0,0,0,0,0,0,0,0,0,0,0);
|
||||||
|
@ -1737,15 +1740,6 @@ static const char xpath_simple_list[] =
|
||||||
" <d/>"
|
" <d/>"
|
||||||
"</root>";
|
"</root>";
|
||||||
|
|
||||||
static const char* leading_spaces[] = {
|
|
||||||
"\n<?xml version=\"1.0\"?><root/>",
|
|
||||||
" <?xml version=\"1.0\"?><root/>",
|
|
||||||
"\t<?xml version=\"1.0\"?><root/>",
|
|
||||||
"\r\n<?xml version=\"1.0\"?><root/>",
|
|
||||||
"\r<?xml version=\"1.0\"?><root/>",
|
|
||||||
0
|
|
||||||
};
|
|
||||||
|
|
||||||
static const char default_ns_doc[] = {
|
static const char default_ns_doc[] = {
|
||||||
"<?xml version=\"1.0\"?>"
|
"<?xml version=\"1.0\"?>"
|
||||||
"<a xmlns:ns=\"nshref\" xml:lang=\"ru\" ns:b=\"b attr\" xml:c=\"c attr\" "
|
"<a xmlns:ns=\"nshref\" xml:lang=\"ru\" ns:b=\"b attr\" xml:c=\"c attr\" "
|
||||||
|
@ -1834,7 +1828,7 @@ static void* _create_object(const GUID *clsid, const char *name, const IID *iid,
|
||||||
|
|
||||||
#define _create(cls) cls, #cls
|
#define _create(cls) cls, #cls
|
||||||
|
|
||||||
#define create_document(iid) _create_object(&_create(CLSID_DOMDocument), iid, __LINE__)
|
#define create_document(iid) _create_object(&_create(CLSID_DOMDocument2), iid, __LINE__)
|
||||||
#define create_document_version(v, iid) _create_object(&_create(CLSID_DOMDocument ## v), iid, __LINE__)
|
#define create_document_version(v, iid) _create_object(&_create(CLSID_DOMDocument ## v), iid, __LINE__)
|
||||||
#define create_cache(iid) _create_object(&_create(CLSID_XMLSchemaCache), iid, __LINE__)
|
#define create_cache(iid) _create_object(&_create(CLSID_XMLSchemaCache), iid, __LINE__)
|
||||||
#define create_cache_version(v, iid) _create_object(&_create(CLSID_XMLSchemaCache ## v), iid, __LINE__)
|
#define create_cache_version(v, iid) _create_object(&_create(CLSID_XMLSchemaCache ## v), iid, __LINE__)
|
||||||
|
@ -2012,6 +2006,38 @@ static char *list_to_string(IXMLDOMNodeList *list)
|
||||||
#define expect_node(node, expstr) { char str[4096]; node_to_string(node, str); ok(strcmp(str, expstr)==0, "Invalid node: %s, expected %s\n", str, expstr); }
|
#define expect_node(node, expstr) { char str[4096]; node_to_string(node, str); ok(strcmp(str, expstr)==0, "Invalid node: %s, expected %s\n", str, expstr); }
|
||||||
#define expect_list_and_release(list, expstr) { char *str = list_to_string(list); ok(strcmp(str, expstr)==0, "Invalid node list: %s, expected %s\n", str, expstr); if (list) IXMLDOMNodeList_Release(list); }
|
#define expect_list_and_release(list, expstr) { char *str = list_to_string(list); ok(strcmp(str, expstr)==0, "Invalid node list: %s, expected %s\n", str, expstr); if (list) IXMLDOMNodeList_Release(list); }
|
||||||
|
|
||||||
|
struct docload_ret_t {
|
||||||
|
VARIANT_BOOL b;
|
||||||
|
HRESULT hr;
|
||||||
|
};
|
||||||
|
|
||||||
|
struct leading_spaces_t {
|
||||||
|
const CLSID *clsid;
|
||||||
|
const char *name;
|
||||||
|
struct docload_ret_t ret[2]; /* 0 - ::load(), 1 - ::loadXML() */
|
||||||
|
};
|
||||||
|
|
||||||
|
static const struct leading_spaces_t leading_spaces_classdata[] = {
|
||||||
|
{ &CLSID_DOMDocument, "CLSID_DOMDocument", {{VARIANT_FALSE, S_FALSE }, {VARIANT_TRUE, S_OK } }},
|
||||||
|
{ &CLSID_DOMDocument2, "CLSID_DOMDocument2", {{VARIANT_FALSE, S_FALSE }, {VARIANT_FALSE, S_FALSE } }},
|
||||||
|
{ &CLSID_DOMDocument26, "CLSID_DOMDocument26", {{VARIANT_FALSE, S_FALSE }, {VARIANT_TRUE, S_OK } }},
|
||||||
|
{ &CLSID_DOMDocument30, "CLSID_DOMDocument30", {{VARIANT_FALSE, S_FALSE }, {VARIANT_FALSE, S_FALSE } }},
|
||||||
|
{ &CLSID_DOMDocument40, "CLSID_DOMDocument40", {{VARIANT_FALSE, S_FALSE }, {VARIANT_FALSE, S_FALSE } }},
|
||||||
|
{ &CLSID_DOMDocument60, "CLSID_DOMDocument60", {{VARIANT_FALSE, S_FALSE }, {VARIANT_FALSE, S_FALSE } }},
|
||||||
|
{ NULL }
|
||||||
|
};
|
||||||
|
|
||||||
|
static const char* leading_spaces_xmldata[] = {
|
||||||
|
"\n<?xml version=\"1.0\" encoding=\"UTF-16\" ?><root/>",
|
||||||
|
" <?xml version=\"1.0\"?><root/>",
|
||||||
|
"\n<?xml version=\"1.0\"?><root/>",
|
||||||
|
"\t<?xml version=\"1.0\"?><root/>",
|
||||||
|
"\r\n<?xml version=\"1.0\"?><root/>",
|
||||||
|
"\r<?xml version=\"1.0\"?><root/>",
|
||||||
|
"\r\r\r\r\t\t \n\n <?xml version=\"1.0\"?><root/>",
|
||||||
|
0
|
||||||
|
};
|
||||||
|
|
||||||
static void test_domdoc( void )
|
static void test_domdoc( void )
|
||||||
{
|
{
|
||||||
HRESULT r, hr;
|
HRESULT r, hr;
|
||||||
|
@ -2024,13 +2050,59 @@ static void test_domdoc( void )
|
||||||
IXMLDOMAttribute *node_attr = NULL;
|
IXMLDOMAttribute *node_attr = NULL;
|
||||||
IXMLDOMNode *nodeChild = NULL;
|
IXMLDOMNode *nodeChild = NULL;
|
||||||
IXMLDOMProcessingInstruction *nodePI = NULL;
|
IXMLDOMProcessingInstruction *nodePI = NULL;
|
||||||
|
const struct leading_spaces_t *class_ptr;
|
||||||
|
const char **data_ptr;
|
||||||
VARIANT_BOOL b;
|
VARIANT_BOOL b;
|
||||||
VARIANT var;
|
VARIANT var;
|
||||||
BSTR str;
|
BSTR str;
|
||||||
LONG code, ref;
|
LONG code, ref;
|
||||||
LONG nLength = 0;
|
LONG nLength = 0;
|
||||||
WCHAR buff[100];
|
WCHAR buff[100];
|
||||||
const char **ptr;
|
int index;
|
||||||
|
|
||||||
|
/* Load document with leading spaces
|
||||||
|
*
|
||||||
|
* Test all CLSIDs with all test data XML strings
|
||||||
|
*/
|
||||||
|
class_ptr = leading_spaces_classdata;
|
||||||
|
index = 0;
|
||||||
|
while (class_ptr->clsid)
|
||||||
|
{
|
||||||
|
HRESULT hr;
|
||||||
|
int i;
|
||||||
|
|
||||||
|
hr = CoCreateInstance(class_ptr->clsid, NULL, CLSCTX_INPROC_SERVER,
|
||||||
|
&IID_IXMLDOMDocument, (void**)&doc);
|
||||||
|
if (hr != S_OK) {
|
||||||
|
win_skip("%d: failed to create class instance for %s\n", index, class_ptr->name);
|
||||||
|
class_ptr++;
|
||||||
|
index++;
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
data_ptr = leading_spaces_xmldata;
|
||||||
|
i = 0;
|
||||||
|
while (*data_ptr) {
|
||||||
|
BSTR data = _bstr_(*data_ptr);
|
||||||
|
|
||||||
|
b = 0xc;
|
||||||
|
V_VT(&var) = VT_BSTR;
|
||||||
|
V_BSTR(&var) = data;
|
||||||
|
hr = IXMLDOMDocument_load(doc, var, &b);
|
||||||
|
EXPECT_HR(hr, class_ptr->ret[0].hr);
|
||||||
|
ok(b == class_ptr->ret[0].b, "%d:%d, got %d, expected %d\n", index, i, b, class_ptr->ret[0].b);
|
||||||
|
|
||||||
|
b = 0xc;
|
||||||
|
hr = IXMLDOMDocument_loadXML(doc, data, &b);
|
||||||
|
EXPECT_HR(hr, class_ptr->ret[1].hr);
|
||||||
|
ok(b == class_ptr->ret[1].b, "%d:%d, got %d, expected %d\n", index, i, b, class_ptr->ret[1].b);
|
||||||
|
|
||||||
|
data_ptr++;
|
||||||
|
i++;
|
||||||
|
}
|
||||||
|
class_ptr++;
|
||||||
|
index++;
|
||||||
|
}
|
||||||
|
|
||||||
doc = create_document(&IID_IXMLDOMDocument);
|
doc = create_document(&IID_IXMLDOMDocument);
|
||||||
if (!doc) return;
|
if (!doc) return;
|
||||||
|
@ -2050,19 +2122,6 @@ if (0)
|
||||||
EXPECT_HR(hr, S_FALSE);
|
EXPECT_HR(hr, S_FALSE);
|
||||||
ok( b == VARIANT_FALSE, "failed to load XML string\n");
|
ok( b == VARIANT_FALSE, "failed to load XML string\n");
|
||||||
|
|
||||||
/* load document with leading spaces */
|
|
||||||
ptr = leading_spaces;
|
|
||||||
while (*ptr)
|
|
||||||
{
|
|
||||||
b = VARIANT_TRUE;
|
|
||||||
V_VT(&var) = VT_BSTR;
|
|
||||||
V_BSTR(&var) = _bstr_(*ptr);
|
|
||||||
hr = IXMLDOMDocument_load( doc, var, &b);
|
|
||||||
EXPECT_HR(hr, S_FALSE);
|
|
||||||
ok( b == VARIANT_FALSE, "got %x\n", b);
|
|
||||||
ptr++;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* try to load a document from a nonexistent file */
|
/* try to load a document from a nonexistent file */
|
||||||
b = VARIANT_TRUE;
|
b = VARIANT_TRUE;
|
||||||
str = SysAllocString( nonexistent_fileW );
|
str = SysAllocString( nonexistent_fileW );
|
||||||
|
|
Loading…
Reference in New Issue