Module: wine Branch: master Commit: a7e294c064ac443a4351d1cbe84e7f52e0775d6f URL: http://source.winehq.org/git/wine.git/?a=commit;h=a7e294c064ac443a4351d1cbe8...
Author: Nikolay Sivov nsivov@codeweavers.com Date: Tue Sep 8 23:45:20 2015 +0300
libwine: Fix double byte default char initialization.
---
dlls/kernel32/tests/codepage.c | 9 ++++++++- libs/wine/wctomb.c | 16 +++++++++++----- 2 files changed, 19 insertions(+), 6 deletions(-)
diff --git a/dlls/kernel32/tests/codepage.c b/dlls/kernel32/tests/codepage.c index 71bedb7..54f62ae 100644 --- a/dlls/kernel32/tests/codepage.c +++ b/dlls/kernel32/tests/codepage.c @@ -276,12 +276,14 @@ static void test_overlapped_buffers(void) static void test_string_conversion(LPBOOL bUsedDefaultChar) { char mbc; - char mbs[5]; + char mbs[15]; int ret; WCHAR wc1 = 228; /* Western Windows-1252 character */ WCHAR wc2 = 1088; /* Russian Windows-1251 character not displayable for Windows-1252 */ static const WCHAR wcs[] = {'T', 'h', 1088, 'i', 0}; /* String with ASCII characters and a Russian character */ static const WCHAR dbwcs[] = {28953, 25152, 0}; /* String with Chinese (codepage 950) characters */ + static const WCHAR dbwcs2[] = {0x7bb8, 0x3d, 0xc813, 0xac00, 0xb77d, 0}; + static const char default_char[] = {0xa3, 0xbf, 0};
SetLastError(0xdeadbeef); ret = WideCharToMultiByte(1252, 0, &wc1, 1, &mbc, 1, NULL, bUsedDefaultChar); @@ -358,6 +360,11 @@ static void test_string_conversion(LPBOOL bUsedDefaultChar) ok(!strcmp(mbs, "??"), "mbs is %s\n", mbs); if(bUsedDefaultChar) ok(*bUsedDefaultChar == TRUE, "bUsedDefaultChar is %d\n", *bUsedDefaultChar);
+ ret = WideCharToMultiByte(936, WC_COMPOSITECHECK, dbwcs2, -1, mbs, sizeof(mbs), (const char *)default_char, bUsedDefaultChar); + ok(ret == 10, "ret is %d\n", ret); + ok(!strcmp(mbs, "\xf3\xe7\x3d\xa3\xbf\xa3\xbf\xa3\xbf"), "mbs is %s\n", mbs); + if(bUsedDefaultChar) ok(*bUsedDefaultChar == TRUE, "bUsedDefaultChar is %d\n", *bUsedDefaultChar); + /* Length-only tests */ SetLastError(0xdeadbeef); ret = WideCharToMultiByte(1252, 0, &wc2, 1, NULL, 0, NULL, bUsedDefaultChar); diff --git a/libs/wine/wctomb.c b/libs/wine/wctomb.c index 3b081d4..29a3d92 100644 --- a/libs/wine/wctomb.c +++ b/libs/wine/wctomb.c @@ -275,6 +275,14 @@ static inline int is_valid_dbcs_mapping( const struct dbcs_table *table, int fla return 1; }
+/* compute the default char for the dbcs case */ +static inline WCHAR get_defchar_dbcs( const struct dbcs_table *table, const char *defchar ) +{ + if (!defchar) return table->info.def_char; + if (!defchar[1]) return (unsigned char)defchar[0]; + return ((unsigned char)defchar[0] << 8) | (unsigned char)defchar[1]; +} + /* query necessary dst length for src string */ static int get_length_dbcs( const struct dbcs_table *table, int flags, const WCHAR *src, unsigned int srclen, @@ -282,8 +290,7 @@ static int get_length_dbcs( const struct dbcs_table *table, int flags, { const unsigned short * const uni2cp_low = table->uni2cp_low; const unsigned short * const uni2cp_high = table->uni2cp_high; - WCHAR defchar_value = table->info.def_char; - WCHAR composed; + WCHAR defchar_value, composed; int len, tmp;
if (!defchar && !used && !(flags & WC_COMPOSITECHECK)) @@ -295,7 +302,7 @@ static int get_length_dbcs( const struct dbcs_table *table, int flags, return len; }
- if (defchar) defchar_value = defchar[1] ? ((defchar[0] << 8) | defchar[1]) : defchar[0]; + defchar_value = get_defchar_dbcs( table, defchar ); if (!used) used = &tmp; /* avoid checking on every char */ *used = 0; for (len = 0; srclen; len++, srclen--, src++) @@ -376,11 +383,10 @@ static int wcstombs_dbcs_slow( const struct dbcs_table *table, int flags, { const unsigned short * const uni2cp_low = table->uni2cp_low; const unsigned short * const uni2cp_high = table->uni2cp_high; - WCHAR defchar_value = table->info.def_char; + WCHAR defchar_value = get_defchar_dbcs( table, defchar ); WCHAR composed; int len, tmp;
- if (defchar) defchar_value = defchar[1] ? ((defchar[0] << 8) | defchar[1]) : defchar[0]; if (!used) used = &tmp; /* avoid checking on every char */ *used = 0;