Signed-off-by: David Kahurani k.kahurani@gmail.com
-- v7: xmllite/writer: Implement WriteSurrogateCharEntity. xmllite/writer: Implement WriteRawChars. xmllite/writer: Implement WriteChars.
From: David Kahurani k.kahurani@gmail.com
Signed-off-by: David Kahurani k.kahurani@gmail.com --- dlls/xmllite/tests/writer.c | 137 ++++++++++++++++++++++++++++++ dlls/xmllite/writer.c | 165 +++++++++++++++++++----------------- 2 files changed, 225 insertions(+), 77 deletions(-)
diff --git a/dlls/xmllite/tests/writer.c b/dlls/xmllite/tests/writer.c index d15fe8b64df..25257624f50 100644 --- a/dlls/xmllite/tests/writer.c +++ b/dlls/xmllite/tests/writer.c @@ -453,6 +453,9 @@ static void test_invalid_output_encoding(IXmlWriter *writer, IUnknown *output) hr = IXmlWriter_WriteWhitespace(writer, L" "); ok(hr == MX_E_ENCODING, "Unexpected hr %#lx.\n", hr);
+ hr = IXmlWriter_WriteChars(writer, L"a", 1); + ok(hr == MX_E_ENCODING, "Unexpected hr %#lx.\n", hr); + hr = IXmlWriter_Flush(writer); ok(hr == S_OK, "Failed to flush, hr %#lx.\n", hr);
@@ -1497,6 +1500,15 @@ static void test_writer_state(void) check_writer_state(writer, WR_E_INVALIDACTION); IStream_Release(stream);
+ /* WriteChars */ + stream = writer_set_output(writer); + + hr = IXmlWriter_WriteChars(writer, L"a", 1); + ok(hr == WR_E_INVALIDACTION, "Unexpected hr %#lx.\n", hr); + + check_writer_state(writer, WR_E_INVALIDACTION); + + IStream_Release(stream); IXmlWriter_Release(writer); }
@@ -2123,6 +2135,130 @@ static void test_WriteString(void) IStream_Release(stream); }
+static void test_WriteChars(void) +{ + IXmlWriter *writer; + IStream *stream; + HRESULT hr; + static WCHAR raw[] = {'s', 'a', 'm', 0xd800, 0xdc00, 'p', 'l', 'e', 0}; + + hr = CreateXmlWriter(&IID_IXmlWriter, (void**)&writer, NULL); + ok(hr == S_OK, "Unexpected hr %#lx.\n", hr); + + hr = IXmlWriter_WriteChars(writer, NULL, 0); + ok(hr == S_OK, "Unexpected hr %#lx.\n", hr); + + hr = IXmlWriter_WriteChars(writer, NULL, 5); + ok(hr == E_INVALIDARG, "Unexpected hr %#lx.\n", hr); + + hr = IXmlWriter_WriteChars(writer, L"", 0); + ok(hr == S_OK, "Unexpected hr %#lx.\n", hr); + + hr = IXmlWriter_WriteChars(writer, L"", 5); + ok(hr == E_UNEXPECTED, "Unexpected hr %#lx.\n", hr); + + stream = writer_set_output(writer); + + hr = IXmlWriter_WriteChars(writer, L"a", 1); + ok(hr == WR_E_INVALIDACTION, "Unexpected hr %#lx.\n", hr); + + hr = IXmlWriter_WriteStartElement(writer, NULL, L"chars", NULL); + ok(hr == WR_E_INVALIDACTION, "Unexpected hr %#lx.\n", hr); + + IStream_Release(stream); + + stream = writer_set_output(writer); + + hr = IXmlWriter_WriteStartElement(writer, NULL, L"chars", NULL); + ok(hr == S_OK, "Unexpected hr %#lx.\n", hr); + + hr = IXmlWriter_WriteChars(writer, NULL, 5); + ok(hr == E_INVALIDARG, "Unexpected hr %#lx.\n", hr); + + hr = IXmlWriter_WriteChars(writer, L"<chars>", 20); + ok(hr == WC_E_XMLCHARACTER, "Unexpected hr %#lx.\n", hr); + + hr = IXmlWriter_WriteChars(writer, L"<chars>", 7); + ok(hr == S_OK, "Unexpected hr %#lx.\n", hr); + + hr = IXmlWriter_Flush(writer); + ok(hr == S_OK, "Unexpected hr %#lx.\n", hr); + + CHECK_OUTPUT(stream, + "<chars><chars><chars>"); + IStream_Release(stream); + + stream = writer_set_output(writer); + + hr = IXmlWriter_WriteStartElement(writer, NULL, L"chars", NULL); + ok(hr == S_OK, "Unexpected hr %#lx.\n", hr); + + hr = IXmlWriter_WriteChars(writer, raw, 8); + ok(hr == S_OK, "Unexpected hr %#lx.\n", hr); + + raw[3] = 0xdc00; + raw[4] = 0xd800; + hr = IXmlWriter_WriteChars(writer, raw, 8); + ok(hr == WR_E_INVALIDSURROGATEPAIR, "Unexpected hr %#lx.\n", hr); + + hr = IXmlWriter_Flush(writer); + ok(hr == S_OK, "Unexpected hr %#lx.\n", hr); + + CHECK_OUTPUT(stream, "<chars>sam\U00010000plesam"); + IStream_Release(stream); + + stream = writer_set_output(writer); + + hr = IXmlWriter_WriteStartElement(writer, NULL, L"chars", NULL); + ok(hr == S_OK, "Unexpected hr %#lx.\n", hr); + + hr = IXmlWriter_WriteChars(writer, NULL, 0); + ok(hr == S_OK, "Unexpected hr %#lx.\n", hr); + + hr = IXmlWriter_WriteFullEndElement(writer); + ok(hr == S_OK, "Unexpected hr %#lx.\n", hr); + + hr = IXmlWriter_Flush(writer); + ok(hr == S_OK, "Unexpected hr %#lx.\n", hr); + + CHECK_OUTPUT(stream, + "<chars></chars>"); + IStream_Release(stream); + + stream = writer_set_output(writer); + + hr = IXmlWriter_WriteStartElement(writer, NULL, L"chars", NULL); + ok(hr == S_OK, "Unexpected hr %#lx.\n", hr); + + hr = IXmlWriter_WriteChars(writer, L"", 0); + ok(hr == S_OK, "Unexpected hr %#lx.\n", hr); + + hr = IXmlWriter_Flush(writer); + ok(hr == S_OK, "Unexpected hr %#lx.\n", hr); + + CHECK_OUTPUT(stream, + "<chars"); + + IStream_Release(stream); + + stream = writer_set_output(writer); + + hr = IXmlWriter_WriteStartElement(writer, NULL, L"c", NULL); + ok(hr == S_OK, "Unexpected hr %#lx.\n", hr); + + hr = IXmlWriter_WriteChars(writer, L"", 5); + ok(hr == WC_E_XMLCHARACTER, "Unexpected hr %#lx.\n", hr); + + hr = IXmlWriter_Flush(writer); + ok(hr == S_OK, "Unexpected hr %#lx.\n", hr); + + CHECK_OUTPUT(stream, + "<c>"); + + IXmlWriter_Release(writer); + IStream_Release(stream); +} + static void test_WriteDocType(void) { static const struct @@ -2650,6 +2786,7 @@ START_TEST(writer) test_WriteAttributeString(); test_WriteFullEndElement(); test_WriteCharEntity(); + test_WriteChars(); test_WriteString(); test_WriteDocType(); test_WriteWhitespace(); diff --git a/dlls/xmllite/writer.c b/dlls/xmllite/writer.c index def165656ef..9a2e75ec452 100644 --- a/dlls/xmllite/writer.c +++ b/dlls/xmllite/writer.c @@ -1104,28 +1104,110 @@ static HRESULT WINAPI xmlwriter_WriteCharEntity(IXmlWriter *iface, WCHAR ch) return S_OK; }
-static HRESULT WINAPI xmlwriter_WriteChars(IXmlWriter *iface, const WCHAR *pwch, UINT cwch) +static HRESULT writer_get_next_write_count(const WCHAR *str, unsigned int length, unsigned int *count) { - xmlwriter *This = impl_from_IXmlWriter(iface); + if (!is_char(*str)) return WC_E_XMLCHARACTER;
- FIXME("%p %s %d\n", This, wine_dbgstr_w(pwch), cwch); + if (IS_HIGH_SURROGATE(*str)) + { + if (length < 2 || !IS_LOW_SURROGATE(*(str + 1))) + return WR_E_INVALIDSURROGATEPAIR;
- switch (This->state) + *count = 2; + } + else if (IS_LOW_SURROGATE(*str)) + return WR_E_INVALIDSURROGATEPAIR; + else + *count = 1; + + return S_OK; +} + +static HRESULT write_escaped_char(xmlwriter *writer, const WCHAR *string, unsigned int count) +{ + HRESULT hr; + + switch (*string) + { + case '<': + hr = write_output_buffer(writer->output, L"<", 4); + break; + case '&': + hr = write_output_buffer(writer->output, L"&", 5); + break; + case '>': + hr = write_output_buffer(writer->output, L">", 4); + break; + default: + hr = write_output_buffer(writer->output, string, count); + } + + return hr; +} + +static HRESULT write_escaped_string(xmlwriter *writer, const WCHAR *string, unsigned int length) +{ + unsigned int count; + HRESULT hr = S_OK; + + if (length == ~0u) + { + while (*string) + { + if (FAILED(hr = writer_get_next_write_count(string, ~0u, &count))) return hr; + if (FAILED(hr = write_escaped_char(writer, string, count))) return hr; + + string += count; + } + } + else + { + while (length) + { + if (FAILED(hr = writer_get_next_write_count(string, length, &count))) return hr; + if (FAILED(hr = write_escaped_char(writer, string, count))) return hr; + + string += count; + length -= count; + } + } + + return hr; +} + +static HRESULT WINAPI xmlwriter_WriteChars(IXmlWriter *iface, const WCHAR *characters, UINT length) +{ + xmlwriter *writer = impl_from_IXmlWriter(iface); + + TRACE("%p, %s, %d.\n", iface, debugstr_wn(characters, length), length); + + if ((characters == NULL && length != 0)) + return E_INVALIDARG; + + if (length == 0) + return S_OK; + + switch (writer->state) { case XmlWriterState_Initial: return E_UNEXPECTED; case XmlWriterState_InvalidEncoding: return MX_E_ENCODING; + case XmlWriterState_ElemStarted: + writer_close_starttag(writer); + break; + case XmlWriterState_Ready: case XmlWriterState_DocClosed: + writer->state = XmlWriterState_DocClosed; return WR_E_INVALIDACTION; default: ; }
- return E_NOTIMPL; + writer->textnode = 1; + return write_escaped_string(writer, characters, length); }
- static HRESULT WINAPI xmlwriter_WriteComment(IXmlWriter *iface, LPCWSTR comment) { xmlwriter *This = impl_from_IXmlWriter(iface); @@ -1684,25 +1766,6 @@ static HRESULT WINAPI xmlwriter_WriteQualifiedName(IXmlWriter *iface, LPCWSTR pw return E_NOTIMPL; }
-static HRESULT writer_get_next_write_count(const WCHAR *str, unsigned int length, unsigned int *count) -{ - if (!is_char(*str)) return WC_E_XMLCHARACTER; - - if (IS_HIGH_SURROGATE(*str)) - { - if (length < 2 || !IS_LOW_SURROGATE(*(str + 1))) - return WR_E_INVALIDSURROGATEPAIR; - - *count = 2; - } - else if (IS_LOW_SURROGATE(*str)) - return WR_E_INVALIDSURROGATEPAIR; - else - *count = 1; - - return S_OK; -} - static HRESULT WINAPI xmlwriter_WriteRaw(IXmlWriter *iface, LPCWSTR data) { xmlwriter *This = impl_from_IXmlWriter(iface); @@ -1862,58 +1925,6 @@ static HRESULT WINAPI xmlwriter_WriteStartElement(IXmlWriter *iface, LPCWSTR pre return S_OK; }
-static HRESULT write_escaped_char(xmlwriter *writer, const WCHAR *string, unsigned int count) -{ - HRESULT hr; - - switch (*string) - { - case '<': - hr = write_output_buffer(writer->output, L"<", 4); - break; - case '&': - hr = write_output_buffer(writer->output, L"&", 5); - break; - case '>': - hr = write_output_buffer(writer->output, L">", 4); - break; - default: - hr = write_output_buffer(writer->output, string, count); - } - - return hr; -} - -static HRESULT write_escaped_string(xmlwriter *writer, const WCHAR *string, unsigned int length) -{ - unsigned int count; - HRESULT hr = S_OK; - - if (length == ~0u) - { - while (*string) - { - if (FAILED(hr = writer_get_next_write_count(string, ~0u, &count))) return hr; - if (FAILED(hr = write_escaped_char(writer, string, count))) return hr; - - string += count; - } - } - else - { - while (length) - { - if (FAILED(hr = writer_get_next_write_count(string, length, &count))) return hr; - if (FAILED(hr = write_escaped_char(writer, string, count))) return hr; - - string += count; - length -= count; - } - } - - return hr; -} - static HRESULT WINAPI xmlwriter_WriteString(IXmlWriter *iface, const WCHAR *string) { xmlwriter *This = impl_from_IXmlWriter(iface);
From: David Kahurani k.kahurani@gmail.com
Signed-off-by: David Kahurani k.kahurani@gmail.com --- dlls/xmllite/tests/writer.c | 116 ++++++++++++++++++++++++++++++++++++ dlls/xmllite/writer.c | 32 ++++++++-- 2 files changed, 143 insertions(+), 5 deletions(-)
diff --git a/dlls/xmllite/tests/writer.c b/dlls/xmllite/tests/writer.c index 25257624f50..53f3297597e 100644 --- a/dlls/xmllite/tests/writer.c +++ b/dlls/xmllite/tests/writer.c @@ -456,6 +456,9 @@ static void test_invalid_output_encoding(IXmlWriter *writer, IUnknown *output) hr = IXmlWriter_WriteChars(writer, L"a", 1); ok(hr == MX_E_ENCODING, "Unexpected hr %#lx.\n", hr);
+ hr = IXmlWriter_WriteRawChars(writer, L"a", 1); + ok(hr == MX_E_ENCODING, "Unexpected hr %#lx.\n", hr); + hr = IXmlWriter_Flush(writer); ok(hr == S_OK, "Failed to flush, hr %#lx.\n", hr);
@@ -1906,6 +1909,118 @@ static void test_WriteCharEntity(void) IStream_Release(stream); }
+static void test_WriteRawChars(void) +{ + IXmlWriter *writer; + IStream *stream; + HRESULT hr; + static WCHAR surrogates[] = {0xd800, 0xdc00, 0}; + + hr = CreateXmlWriter(&IID_IXmlWriter, (void**)&writer, NULL); + ok(hr == S_OK, "Unexpected hr %#lx.\n", hr); + + hr = IXmlWriter_WriteRawChars(writer, NULL, 0); + ok(hr == S_OK, "Unexpected hr %#lx.\n", hr); + + hr = IXmlWriter_WriteRawChars(writer, L"", 0); + ok(hr == S_OK, "Unexpected hr %#lx.\n", hr); + + hr = IXmlWriter_WriteRawChars(writer, NULL, 5); + ok(hr == E_INVALIDARG, "Unexpected hr %#lx.\n", hr); + + hr = IXmlWriter_WriteRawChars(writer, L"", 6); + ok(hr == E_UNEXPECTED, "Unexpected hr %#lx.\n", hr); + + stream = writer_set_output(writer); + + hr = IXmlWriter_WriteStartElement(writer, NULL, L"sub", NULL); + ok(hr == S_OK, "Unexpected hr %#lx.\n", hr); + + hr = IXmlWriter_WriteRawChars(writer, L"<rawChars>", 5); + ok(hr == S_OK, "Unexpected hr %#lx.\n", hr); + + hr = IXmlWriter_Flush(writer); + ok(hr == S_OK, "Unexpected hr %#lx.\n", hr); + + CHECK_OUTPUT(stream, "<sub><rawC"); + IStream_Release(stream); + + stream = writer_set_output(writer); + + hr = IXmlWriter_WriteRawChars(writer, L"a", 1); + ok(hr == S_OK, "Unexpected hr %#lx.\n", hr); + + hr = IXmlWriter_WriteStartElement(writer, NULL, L"sub", NULL); + ok(hr == S_OK, "Unexpected hr %#lx.\n", hr); + + hr = IXmlWriter_WriteRawChars(writer, L"<;;>", 10); + ok(hr == WC_E_XMLCHARACTER, "Unexpected hr %#lx.\n", hr); + + hr = IXmlWriter_Flush(writer); + ok(hr == S_OK, "Unexpected hr %#lx.\n", hr); + + CHECK_OUTPUT(stream, "<?xml version=\"1.0\" encoding=\"UTF-8\"?>a<sub><;;>"); + IStream_Release(stream); + + stream = writer_set_output(writer); + + hr = IXmlWriter_WriteStartElement(writer, NULL, L"sub", NULL); + ok(hr == S_OK, "Unexpected hr %#lx.\n", hr); + + hr = IXmlWriter_WriteRawChars(writer, surrogates, 1); + ok(hr == WR_E_INVALIDSURROGATEPAIR, "Unexpected hr %#lx.\n", hr); + + hr = IXmlWriter_WriteRawChars(writer, surrogates, 2); + ok(hr == S_OK, "Unexpected hr %#lx.\n", hr); + + hr = IXmlWriter_Flush(writer); + ok(hr == S_OK, "Unexpected hr %#lx.\n", hr); + + CHECK_OUTPUT(stream, "<sub>\U00010000"); + IStream_Release(stream); + + stream = writer_set_output(writer); + + hr = IXmlWriter_WriteStartElement(writer, NULL, L"sub", NULL); + ok(hr == S_OK, "Unexpected hr %#lx.\n", hr); + + hr = IXmlWriter_WriteRawChars(writer, L"", 5); + ok(hr == WC_E_XMLCHARACTER, "Unexpected hr %#lx.\n", hr); + + hr = IXmlWriter_Flush(writer); + ok(hr == S_OK, "Unexpected hr %#lx.\n", hr); + + CHECK_OUTPUT(stream, "<sub>"); + IStream_Release(stream); + + stream = writer_set_output(writer); + + hr = IXmlWriter_WriteStartElement(writer, NULL, L"sub", NULL); + ok(hr == S_OK, "Unexpected hr %#lx.\n", hr); + + hr = IXmlWriter_WriteRawChars(writer, L"", 0); + ok(hr == S_OK, "Unexpected hr %#lx.\n", hr); + + hr = IXmlWriter_Flush(writer); + ok(hr == S_OK, "Unexpected hr %#lx.\n", hr); + + CHECK_OUTPUT(stream, "<sub"); + + IStream_Release(stream); + + stream = writer_set_output(writer); + + /* Force document close */ + hr = IXmlWriter_WriteEndElement(writer); + ok(hr == WR_E_INVALIDACTION, "Unexpected hr %#lx.\n", hr); + + hr = IXmlWriter_WriteRawChars(writer, L"a", 1); + ok(hr == WR_E_INVALIDACTION, "Unexpected hr %#lx.\n", hr); + + IStream_Release(stream); + IXmlWriter_Release(writer); +} + static void test_WriteString(void) { static const WCHAR surrogates[] = {0xd800, 0xdc00, 'x', 'y', '\0'}; @@ -2787,6 +2902,7 @@ START_TEST(writer) test_WriteFullEndElement(); test_WriteCharEntity(); test_WriteChars(); + test_WriteRawChars(); test_WriteString(); test_WriteDocType(); test_WriteWhitespace(); diff --git a/dlls/xmllite/writer.c b/dlls/xmllite/writer.c index 9a2e75ec452..55fe6ab05d7 100644 --- a/dlls/xmllite/writer.c +++ b/dlls/xmllite/writer.c @@ -1808,13 +1808,21 @@ static HRESULT WINAPI xmlwriter_WriteRaw(IXmlWriter *iface, LPCWSTR data) return hr; }
-static HRESULT WINAPI xmlwriter_WriteRawChars(IXmlWriter *iface, const WCHAR *pwch, UINT cwch) +static HRESULT WINAPI xmlwriter_WriteRawChars(IXmlWriter *iface, const WCHAR *characters, UINT length) { - xmlwriter *This = impl_from_IXmlWriter(iface); + xmlwriter *writer = impl_from_IXmlWriter(iface); + HRESULT hr = S_OK; + unsigned int count;
- FIXME("%p %s %d\n", This, wine_dbgstr_w(pwch), cwch); + TRACE("%p, %s, %d.\n", iface, debugstr_wn(characters, length), length);
- switch (This->state) + if ((characters == NULL && length != 0)) + return E_INVALIDARG; + + if (length == 0) + return S_OK; + + switch (writer->state) { case XmlWriterState_Initial: return E_UNEXPECTED; @@ -1822,11 +1830,25 @@ static HRESULT WINAPI xmlwriter_WriteRawChars(IXmlWriter *iface, const WCHAR *p return MX_E_ENCODING; case XmlWriterState_DocClosed: return WR_E_INVALIDACTION; + case XmlWriterState_Ready: + write_xmldecl(writer, XmlStandalone_Omit); + break; + case XmlWriterState_ElemStarted: + writer_close_starttag(writer); default: ; }
- return E_NOTIMPL; + while (length) + { + if (FAILED(hr = writer_get_next_write_count(characters, length, &count))) return hr; + if (FAILED(hr = write_output_buffer(writer->output, characters, count))) return hr; + + characters += count; + length -= count; + } + + return hr; }
static HRESULT WINAPI xmlwriter_WriteStartDocument(IXmlWriter *iface, XmlStandalone standalone)
From: David Kahurani k.kahurani@gmail.com
Signed-off-by: David Kahurani k.kahurani@gmail.com --- dlls/xmllite/tests/writer.c | 65 +++++++++++++++++++++++++++++++++++-- dlls/xmllite/writer.c | 30 +++++++++++++++-- 2 files changed, 90 insertions(+), 5 deletions(-)
diff --git a/dlls/xmllite/tests/writer.c b/dlls/xmllite/tests/writer.c index 53f3297597e..572b3a9fd67 100644 --- a/dlls/xmllite/tests/writer.c +++ b/dlls/xmllite/tests/writer.c @@ -138,6 +138,8 @@ static void check_writer_state(IXmlWriter *writer, HRESULT exp_hr) { IXmlReader *reader; HRESULT hr; + WCHAR low = 0xdcef; + WCHAR high = 0xdaff;
hr = CreateXmlReader(&IID_IXmlReader, (void **)&reader, NULL); ok(hr == S_OK, "Unexpected hr %#lx.\n", hr); @@ -217,7 +219,8 @@ static void check_writer_state(IXmlWriter *writer, HRESULT exp_hr) hr = IXmlWriter_WriteString(writer, L"a"); ok(hr == exp_hr, "Unexpected hr %#lx, expected %#lx.\n", hr, exp_hr);
- /* FIXME: add WriteSurrogateCharEntity */ + hr = IXmlWriter_WriteSurrogateCharEntity(writer, low, high); + ok(hr == exp_hr, "Unexpected hr %#lx, expected %#lx.\n", hr, exp_hr);
hr = IXmlWriter_WriteWhitespace(writer, L" "); ok(hr == exp_hr, "Unexpected hr %#lx, expected %#lx.\n", hr, exp_hr); @@ -372,6 +375,8 @@ static void test_invalid_output_encoding(IXmlWriter *writer, IUnknown *output) { IXmlReader *reader; HRESULT hr; + WCHAR low = 0xdcef; + WCHAR high = 0xdaff;
hr = CreateXmlReader(&IID_IXmlReader, (void **)&reader, NULL); ok(hr == S_OK, "Unexpected hr %#lx.\n", hr); @@ -448,7 +453,8 @@ static void test_invalid_output_encoding(IXmlWriter *writer, IUnknown *output) hr = IXmlWriter_WriteString(writer, L"a"); ok(hr == MX_E_ENCODING, "Unexpected hr %#lx.\n", hr);
- /* TODO: WriteSurrogateCharEntity */ + hr = IXmlWriter_WriteSurrogateCharEntity(writer, low, high); + ok(hr == MX_E_ENCODING, "Unexpected hr %#lx.\n", hr);
hr = IXmlWriter_WriteWhitespace(writer, L" "); ok(hr == MX_E_ENCODING, "Unexpected hr %#lx.\n", hr); @@ -2021,6 +2027,60 @@ static void test_WriteRawChars(void) IXmlWriter_Release(writer); }
+static void test_WriteSurrogateCharEntity(void) +{ + IXmlWriter *writer; + IStream *stream; + HRESULT hr; + WCHAR low = 0xdcef; + WCHAR high = 0xdaff; + + hr = CreateXmlWriter(&IID_IXmlWriter, (void**)&writer, NULL); + ok(hr == S_OK, "Unexpected hr %#lx.\n", hr); + + hr = IXmlWriter_WriteSurrogateCharEntity(writer, high, low); + ok(hr == WC_E_XMLCHARACTER, "Unexpected hr %#lx.\n", hr); + + hr = IXmlWriter_WriteSurrogateCharEntity(writer, low, high); + ok(hr == E_UNEXPECTED, "Unexpected hr %#lx.\n", hr); + + stream = writer_set_output(writer); + + hr = IXmlWriter_WriteStartElement(writer, NULL, L"root", NULL); + ok(hr == S_OK, "Unexpected hr %#lx.\n", hr); + + hr = IXmlWriter_WriteSurrogateCharEntity(writer, high, low); + ok(hr == WC_E_XMLCHARACTER, "Unexpected hr %#lx.\n", hr); + + hr = IXmlWriter_Flush(writer); + ok(hr == S_OK, "Unexpected hr %#lx.\n", hr); + + CHECK_OUTPUT(stream, "<root"); + + hr = IXmlWriter_WriteSurrogateCharEntity(writer, low, high); + ok(hr == S_OK, "Unexpected hr %#lx.\n", hr); + + hr = IXmlWriter_WriteFullEndElement(writer); + ok(hr == S_OK, "Unexpected hr %#lx.\n", hr); + + hr = IXmlWriter_Flush(writer); + ok(hr == S_OK, "Unexpected hr %#lx.\n", hr); + + CHECK_OUTPUT(stream, "<root>󏳯</root>"); + IStream_Release(stream); + + stream = writer_set_output(writer); + + hr = IXmlWriter_WriteEndElement(writer); + ok(hr == WR_E_INVALIDACTION, "Unexpected hr %#lx.\n", hr); + + hr = IXmlWriter_WriteSurrogateCharEntity(writer, low, high); + ok(hr == WR_E_INVALIDACTION, "Unexpected hr %#lx.\n", hr); + + IXmlWriter_Release(writer); + IStream_Release(stream); +} + static void test_WriteString(void) { static const WCHAR surrogates[] = {0xd800, 0xdc00, 'x', 'y', '\0'}; @@ -2903,6 +2963,7 @@ START_TEST(writer) test_WriteCharEntity(); test_WriteChars(); test_WriteRawChars(); + test_WriteSurrogateCharEntity(); test_WriteString(); test_WriteDocType(); test_WriteWhitespace(); diff --git a/dlls/xmllite/writer.c b/dlls/xmllite/writer.c index 55fe6ab05d7..128d666e82c 100644 --- a/dlls/xmllite/writer.c +++ b/dlls/xmllite/writer.c @@ -1979,11 +1979,35 @@ static HRESULT WINAPI xmlwriter_WriteString(IXmlWriter *iface, const WCHAR *stri
static HRESULT WINAPI xmlwriter_WriteSurrogateCharEntity(IXmlWriter *iface, WCHAR wchLow, WCHAR wchHigh) { - xmlwriter *This = impl_from_IXmlWriter(iface); + xmlwriter *writer = impl_from_IXmlWriter(iface); + int codepoint; + WCHAR bufW[16];
- FIXME("%p %d %d\n", This, wchLow, wchHigh); + TRACE("%p, %d, %d.\n", iface, wchLow, wchHigh);
- return E_NOTIMPL; + if (!IS_SURROGATE_PAIR(wchHigh, wchLow)) + return WC_E_XMLCHARACTER; + + switch (writer->state) + { + case XmlWriterState_Initial: + return E_UNEXPECTED; + case XmlWriterState_InvalidEncoding: + return MX_E_ENCODING; + case XmlWriterState_ElemStarted: + writer_close_starttag(writer); + break; + case XmlWriterState_DocClosed: + return WR_E_INVALIDACTION; + default: + ; + } + + codepoint = ((wchHigh - 0xd800) * 0x400) + (wchLow - 0xdc00) + 0x10000; + swprintf(bufW, ARRAY_SIZE(bufW), L"&#x%X;", codepoint); + write_output_buffer(writer->output, bufW, -1); + + return S_OK; }
static HRESULT WINAPI xmlwriter_WriteWhitespace(IXmlWriter *iface, LPCWSTR text)
Hi,
It looks like your patch introduced the new failures shown below. Please investigate and fix them before resubmitting your patch. If they are not new, fixing them anyway would help a lot. Otherwise please ask for the known failures list to be updated.
The tests also ran into some preexisting test failures. If you know how to fix them that would be helpful. See the TestBot job for the details:
The full results can be found at: https://testbot.winehq.org/JobDetails.pl?Key=126978
Your paranoid android.
=== debian11 (32 bit report) ===
wmvcore: wmvcore.c:3007: Test failed: Wait timed out.
This merge request was approved by Nikolay Sivov.