Alexandre Julliard : msvcrt: Fix wcstoul() to behave identically to strtoul().

Alexandre Julliard julliard at winehq.org
Tue Dec 17 15:58:19 CST 2019


Module: wine
Branch: master
Commit: 763868243399c6230afe03110b28c2ae271845f6
URL:    https://source.winehq.org/git/wine.git/?a=commit;h=763868243399c6230afe03110b28c2ae271845f6

Author: Alexandre Julliard <julliard at winehq.org>
Date:   Tue Dec 17 15:27:31 2019 +0100

msvcrt: Fix wcstoul() to behave identically to strtoul().

Wine-Bug: https://bugs.winehq.org/show_bug.cgi?id=48261
Signed-off-by: Alexandre Julliard <julliard at winehq.org>

---

 dlls/msvcrt/tests/string.c | 60 ++++++++++++++++++++++++++++++++++++++++++++++
 dlls/msvcrt/wcs.c          |  5 +++-
 2 files changed, 64 insertions(+), 1 deletion(-)

diff --git a/dlls/msvcrt/tests/string.c b/dlls/msvcrt/tests/string.c
index 1dfa05c744..f814a22bdb 100644
--- a/dlls/msvcrt/tests/string.c
+++ b/dlls/msvcrt/tests/string.c
@@ -3142,6 +3142,65 @@ static void test__wcstoi64(void)
     }
 }
 
+static void test__wcstol(void)
+{
+    static const struct { WCHAR str[24]; long res; unsigned long ures; int base; } tests[] =
+    {
+        { L"9", 9, 9, 10 },
+        { L" ", 0, 0 },
+        { L"-1234", -1234, -1234 },
+        { { 0x3231 }, 0, 0 }, /* PARENTHESIZED IDEOGRAPH STOCK */
+        { { 0x4e00 }, 0, 0 }, /* CJK Ideograph, First */
+        { { 0x0bef }, 0, 0 }, /* TAMIL DIGIT NINE */
+        { { 0x0e59 }, 9, 9 }, /* THAI DIGIT NINE */
+        { { 0xff19 }, 9, 9 }, /* FULLWIDTH DIGIT NINE */
+        { { 0x00b9 }, 0, 0 }, /* SUPERSCRIPT ONE */
+        { { '-',0x0e50,'x',0xff19,'1' }, -0x91, -0x91 },
+        { { '+',0x0e50,0xff17,'1' }, 071, 071 },
+        { { 0xff19,'f',0x0e59,0xff46 }, 0x9f9, 0x9f9, 16 },
+        { L"2147483647", 2147483647, 2147483647 },
+        { L"2147483648", LONG_MAX, 2147483648 },
+        { L"4294967295", LONG_MAX, 4294967295 },
+        { L"4294967296", LONG_MAX, ULONG_MAX },
+        { L"9223372036854775807", LONG_MAX, ULONG_MAX },
+        { L"-2147483647", -2147483647, -2147483647 },
+        { L"-2147483648", LONG_MIN, LONG_MIN },
+        { L"-4294967295", LONG_MIN, 1 },
+        { L"-4294967296", LONG_MIN, 1 },
+        { L"-9223372036854775807", LONG_MIN, 1 },
+    };
+    static const WCHAR zeros[] = {
+        0x660, 0x6f0, 0x966, 0x9e6, 0xa66, 0xae6, 0xb66, 0xc66, 0xce6,
+        0xd66, 0xe50, 0xed0, 0xf20, 0x1040, 0x17e0, 0x1810, 0xff10
+    };
+    int i;
+
+    long res;
+    unsigned long ures;
+    WCHAR *endpos;
+
+    for (i = 0; i < ARRAY_SIZE(tests); i++)
+    {
+        res = wcstol( tests[i].str, &endpos, tests[i].base );
+        ok( res == tests[i].res, "%u: %s res %08lx\n",
+            i, wine_dbgstr_w(tests[i].str), res );
+        if (!res) ok( endpos == tests[i].str, "%u: wrong endpos %p/%p\n", i, endpos, tests[i].str );
+        ures = wcstoul( tests[i].str, &endpos, tests[i].base );
+        ok( ures == tests[i].ures, "%u: %s res %08lx\n",
+            i, wine_dbgstr_w(tests[i].str), ures );
+    }
+
+    /* Test various unicode digits */
+    for (i = 0; i < ARRAY_SIZE(zeros); ++i) {
+        WCHAR tmp[] = {zeros[i] + 4, zeros[i], zeros[i] + 5, 0};
+        res = wcstol(tmp, NULL, 0);
+        ok(res == 405, "with zero = U+%04X: got %d, expected 405\n", zeros[i], (int)res);
+        tmp[1] = zeros[i] + 10;
+        res = wcstol(tmp, NULL, 16);
+        ok(res == 4, "with zero = U+%04X: got %d, expected 4\n", zeros[i], (int)res);
+    }
+}
+
 static void test_atoi(void)
 {
     int r;
@@ -4066,6 +4125,7 @@ START_TEST(string)
     test__atodbl();
     test__stricmp();
     test__wcstoi64();
+    test__wcstol();
     test_atoi();
     test_atol();
     test_atof();
diff --git a/dlls/msvcrt/wcs.c b/dlls/msvcrt/wcs.c
index 1ae292423c..8b240e97c0 100644
--- a/dlls/msvcrt/wcs.c
+++ b/dlls/msvcrt/wcs.c
@@ -2487,11 +2487,14 @@ unsigned __int64 CDECL MSVCRT__wcstoui64(const MSVCRT_wchar_t *nptr,
 MSVCRT_ulong __cdecl MSVCRT__wcstoul_l(const MSVCRT_wchar_t *s,
         MSVCRT_wchar_t **end, int base, MSVCRT__locale_t locale)
 {
-    unsigned __int64 ret = MSVCRT__wcstoui64_l(s, end, base, locale);
+    __int64 ret = MSVCRT__wcstoi64_l(s, end, base, locale);
 
     if(ret > MSVCRT_ULONG_MAX) {
         ret = MSVCRT_ULONG_MAX;
         *MSVCRT__errno() = MSVCRT_ERANGE;
+    }else if(ret < -(__int64)MSVCRT_ULONG_MAX) {
+        ret = 1;
+        *MSVCRT__errno() = MSVCRT_ERANGE;
     }
     return ret;
 }




More information about the wine-cvs mailing list