From 6457163bb27f986d09a085af5a5d971d2b302153 Mon Sep 17 00:00:00 2001 From: Piotr Caban Date: Thu, 25 Jul 2013 10:14:33 +0200 Subject: [PATCH] msvcrt: Add _wctomb_s_l implementation. --- dlls/msvcr100/msvcr100.spec | 6 +- dlls/msvcr110/msvcr110.spec | 6 +- dlls/msvcr80/msvcr80.spec | 6 +- dlls/msvcr90/msvcr90.spec | 6 +- dlls/msvcrt/msvcrt.spec | 6 +- dlls/msvcrt/tests/string.c | 2 +- dlls/msvcrt/wcs.c | 106 ++++++++++++++++++++++++++++++------ 7 files changed, 106 insertions(+), 32 deletions(-) diff --git a/dlls/msvcr100/msvcr100.spec b/dlls/msvcr100/msvcr100.spec index ef6d3544497..c71f7fa5ad3 100644 --- a/dlls/msvcr100/msvcr100.spec +++ b/dlls/msvcr100/msvcr100.spec @@ -1520,8 +1520,8 @@ @ stub _wctime32_s @ cdecl _wctime64(ptr) msvcrt._wctime64 @ stub _wctime64_s -@ stub _wctomb_l -@ stub _wctomb_s_l +@ cdecl _wctomb_l(ptr long ptr) msvcrt._wctomb_l +@ cdecl _wctomb_s_l(ptr ptr long long ptr) msvcrt._wctomb_s_l # extern _wctype @ cdecl _wdupenv_s(ptr ptr wstr) msvcrt._wdupenv_s @ extern _wenviron msvcrt._wenviron @@ -1877,7 +1877,7 @@ @ cdecl wcsxfrm(ptr wstr long) msvcrt.wcsxfrm @ cdecl wctob(long) msvcrt.wctob @ cdecl wctomb(ptr long) msvcrt.wctomb -@ stub wctomb_s +@ cdecl wctomb_s(ptr ptr long long) msvcrt.wctomb_s @ cdecl wmemcpy_s(ptr long ptr long) @ cdecl wmemmove_s(ptr long ptr long) @ varargs wprintf(wstr) msvcrt.wprintf diff --git a/dlls/msvcr110/msvcr110.spec b/dlls/msvcr110/msvcr110.spec index dd768788037..40dd029d83b 100644 --- a/dlls/msvcr110/msvcr110.spec +++ b/dlls/msvcr110/msvcr110.spec @@ -1883,8 +1883,8 @@ @ stub _wctime32_s @ cdecl _wctime64(ptr) msvcrt._wctime64 @ stub _wctime64_s -@ stub _wctomb_l -@ stub _wctomb_s_l +@ cdecl _wctomb_l(ptr long ptr) msvcrt._wctomb_l +@ cdecl _wctomb_s_l(ptr ptr long long ptr) msvcrt._wctomb_s_l # extern _wctype @ cdecl _wdupenv_s(ptr ptr wstr) msvcrt._wdupenv_s @ extern _wenviron msvcrt._wenviron @@ -2240,7 +2240,7 @@ @ cdecl wcsxfrm(ptr wstr long) msvcrt.wcsxfrm @ cdecl wctob(long) msvcrt.wctob @ cdecl wctomb(ptr long) msvcrt.wctomb -@ stub wctomb_s +@ cdecl wctomb_s(ptr ptr long long) msvcrt.wctomb_s @ cdecl wmemcpy_s(ptr long ptr long) msvcr100.wmemcpy_s @ cdecl wmemmove_s(ptr long ptr long) msvcr100.wmemmove_s @ varargs wprintf(wstr) msvcrt.wprintf diff --git a/dlls/msvcr80/msvcr80.spec b/dlls/msvcr80/msvcr80.spec index 87fbc5da3a5..68530bfdb50 100644 --- a/dlls/msvcr80/msvcr80.spec +++ b/dlls/msvcr80/msvcr80.spec @@ -1198,8 +1198,8 @@ @ stub _wctime32_s @ cdecl _wctime64(ptr) msvcrt._wctime64 @ stub _wctime64_s -@ stub _wctomb_l -@ stub _wctomb_s_l +@ cdecl _wctomb_l(ptr long ptr) msvcrt._wctomb_l +@ cdecl _wctomb_s_l(ptr ptr long long ptr) msvcrt._wctomb_s_l # extern _wctype @ cdecl _wdupenv_s(ptr ptr wstr) msvcrt._wdupenv_s @ extern _wenviron msvcrt._wenviron @@ -1556,7 +1556,7 @@ @ cdecl wcsxfrm(ptr wstr long) msvcrt.wcsxfrm @ cdecl wctob(long) msvcrt.wctob @ cdecl wctomb(ptr long) msvcrt.wctomb -@ stub wctomb_s +@ cdecl wctomb_s(ptr ptr long long) msvcrt.wctomb_s @ varargs wprintf(wstr) msvcrt.wprintf @ varargs wprintf_s(wstr) msvcrt.wprintf_s @ varargs wscanf(wstr) msvcrt.wscanf diff --git a/dlls/msvcr90/msvcr90.spec b/dlls/msvcr90/msvcr90.spec index 98000231c57..6a1657fb8d1 100644 --- a/dlls/msvcr90/msvcr90.spec +++ b/dlls/msvcr90/msvcr90.spec @@ -1174,8 +1174,8 @@ @ stub _wctime32_s @ cdecl _wctime64(ptr) msvcrt._wctime64 @ stub _wctime64_s -@ stub _wctomb_l -@ stub _wctomb_s_l +@ cdecl _wctomb_l(ptr long ptr) msvcrt._wctomb_l +@ cdecl _wctomb_s_l(ptr ptr long long ptr) msvcrt._wctomb_s_l # extern _wctype @ cdecl _wdupenv_s(ptr ptr wstr) msvcrt._wdupenv_s @ extern _wenviron msvcrt._wenviron @@ -1529,7 +1529,7 @@ @ cdecl wcsxfrm(ptr wstr long) msvcrt.wcsxfrm @ cdecl wctob(long) msvcrt.wctob @ cdecl wctomb(ptr long) msvcrt.wctomb -@ stub wctomb_s +@ cdecl wctomb_s(ptr ptr long long) msvcrt.wctomb_s @ varargs wprintf(wstr) msvcrt.wprintf @ varargs wprintf_s(wstr) msvcrt.wprintf_s @ varargs wscanf(wstr) msvcrt.wscanf diff --git a/dlls/msvcrt/msvcrt.spec b/dlls/msvcrt/msvcrt.spec index e0e628710d1..6a812a902df 100644 --- a/dlls/msvcrt/msvcrt.spec +++ b/dlls/msvcrt/msvcrt.spec @@ -1139,8 +1139,8 @@ # stub _wctime32_s(ptr long ptr) @ cdecl _wctime64(ptr) MSVCRT__wctime64 # stub _wctime64_s(ptr long ptr) -# stub _wctomb_l(ptr long ptr) -# stub _wctomb_s_l(ptr ptr long long ptr) +@ cdecl _wctomb_l(ptr long ptr) MSVCRT__wctomb_l +@ cdecl _wctomb_s_l(ptr ptr long long ptr) MSVCRT__wctomb_s_l # extern _wctype @ extern _wenviron MSVCRT__wenviron @ varargs _wexecl(wstr wstr) @@ -1510,7 +1510,7 @@ @ stub wcsxfrm(ptr wstr long) @ cdecl wctob(long) MSVCRT_wctob @ cdecl wctomb(ptr long) MSVCRT_wctomb -# stub wctomb_s(ptr ptr long long) +@ cdecl wctomb_s(ptr ptr long long) MSVCRT_wctomb_s @ varargs wprintf(wstr) MSVCRT_wprintf @ varargs wprintf_s(wstr) MSVCRT_wprintf_s @ varargs wscanf(wstr) MSVCRT_wscanf diff --git a/dlls/msvcrt/tests/string.c b/dlls/msvcrt/tests/string.c index 39934f04e5e..7edaa2343b3 100644 --- a/dlls/msvcrt/tests/string.c +++ b/dlls/msvcrt/tests/string.c @@ -2356,7 +2356,7 @@ static void test_wctomb(void) ret = p_wcrtomb((char*)dst, 0xffff, NULL); ok(ret == -1, "wcrtomb did not return -1\n"); - ok(dst[0] == 0x3f, "dst[0] = %x, expected 0x20\n", dst[0]); + ok(dst[0] == 0x3f, "dst[0] = %x, expected 0x3f\n", dst[0]); setlocale(LC_ALL, "C"); } diff --git a/dlls/msvcrt/wcs.c b/dlls/msvcrt/wcs.c index c5b630fd71f..dbb12dd0553 100644 --- a/dlls/msvcrt/wcs.c +++ b/dlls/msvcrt/wcs.c @@ -1145,6 +1145,96 @@ MSVCRT_wchar_t * CDECL MSVCRT_wcstok( MSVCRT_wchar_t *str, const MSVCRT_wchar_t return wcstok_s(str, delim, &msvcrt_get_thread_data()->wcstok_next); } +/********************************************************************* + * _wctomb_s_l (MSVCRT.@) + */ +int CDECL MSVCRT__wctomb_s_l(int *len, char *mbchar, MSVCRT_size_t size, + MSVCRT_wchar_t wch, MSVCRT__locale_t locale) +{ + MSVCRT_pthreadlocinfo locinfo; + BOOL error; + int mblen; + + if(!mbchar && size>0) { + if(len) + *len = 0; + return 0; + } + + if(len) + *len = -1; + + if(!MSVCRT_CHECK_PMT(size <= INT_MAX)) + return MSVCRT_EINVAL; + + if(!locale) + locinfo = get_locinfo(); + else + locinfo = locale->locinfo; + + if(!locinfo->lc_codepage) { + if(wch > 0xff) { + if(mbchar && size>0) + memset(mbchar, 0, size); + *MSVCRT__errno() = MSVCRT_EILSEQ; + return MSVCRT_EILSEQ; + } + + if(!MSVCRT_CHECK_PMT_ERR(size >= 1, MSVCRT_ERANGE)) + return MSVCRT_ERANGE; + + *mbchar = wch; + if(len) + *len = 1; + return 0; + } + + mblen = WideCharToMultiByte(locinfo->lc_codepage, 0, &wch, 1, mbchar, size, NULL, &error); + if(!mblen || error) { + if(!mblen && GetLastError()==ERROR_INSUFFICIENT_BUFFER) { + if(mbchar && size>0) + memset(mbchar, 0, size); + + MSVCRT_INVALID_PMT("insufficient buffer size", MSVCRT_ERANGE); + return MSVCRT_ERANGE; + } + + *MSVCRT__errno() = MSVCRT_EILSEQ; + return MSVCRT_EILSEQ; + } + + if(len) + *len = mblen; + return 0; +} + +/********************************************************************* + * wctomb_s (MSVCRT.@) + */ +int CDECL MSVCRT_wctomb_s(int *len, char *mbchar, MSVCRT_size_t size, MSVCRT_wchar_t wch) +{ + return MSVCRT__wctomb_s_l(len, mbchar, size, wch, NULL); +} + +/********************************************************************* + * _wctomb_l (MSVCRT.@) + */ +int CDECL MSVCRT__wctomb_l(char *dst, MSVCRT_wchar_t ch, MSVCRT__locale_t locale) +{ + int len; + + MSVCRT__wctomb_s_l(&len, dst, dst ? 6 : 0, ch, locale); + return len; +} + +/********************************************************************* + * wctomb (MSVCRT.@) + */ +INT CDECL MSVCRT_wctomb( char *dst, MSVCRT_wchar_t ch ) +{ + return MSVCRT__wctomb_l(dst, ch, NULL); +} + /********************************************************************* * wctob (MSVCRT.@) */ @@ -1164,22 +1254,6 @@ INT CDECL MSVCRT_wctob( MSVCRT_wint_t wchar ) return MSVCRT_EOF; } -/********************************************************************* - * wctomb (MSVCRT.@) - */ -INT CDECL MSVCRT_wctomb( char *dst, MSVCRT_wchar_t ch ) -{ - BOOL error; - INT size; - - size = WideCharToMultiByte(get_locinfo()->lc_codepage, 0, &ch, 1, dst, dst ? 6 : 0, NULL, &error); - if(!size || error) { - *MSVCRT__errno() = MSVCRT_EINVAL; - return MSVCRT_EOF; - } - return size; -} - /********************************************************************* * wcrtomb (MSVCRT.@) */