Module: wine Branch: master Commit: cada88a64b8484d1af906caff69e383c944e114a URL: http://source.winehq.org/git/wine.git/?a=commit;h=cada88a64b8484d1af906caff6...
Author: Daniel Lehman dlehman25@gmail.com Date: Mon Nov 28 19:37:18 2016 -0800
msvcrt: Add _lfind_s.
Signed-off-by: Daniel Lehman dlehman25@gmail.com Signed-off-by: Piotr Caban piotr@codeweavers.com Signed-off-by: Alexandre Julliard julliard@winehq.org
---
.../api-ms-win-crt-utility-l1-1-0.spec | 2 +- dlls/msvcr100/msvcr100.spec | 2 +- dlls/msvcr110/msvcr110.spec | 2 +- dlls/msvcr120/msvcr120.spec | 2 +- dlls/msvcr120_app/msvcr120_app.spec | 2 +- dlls/msvcr80/msvcr80.spec | 2 +- dlls/msvcr90/msvcr90.spec | 2 +- dlls/msvcrt/misc.c | 26 ++++++++ dlls/msvcrt/msvcrt.spec | 2 +- dlls/msvcrt/tests/misc.c | 72 ++++++++++++++++++++++ dlls/ucrtbase/ucrtbase.spec | 2 +- 11 files changed, 107 insertions(+), 9 deletions(-)
diff --git a/dlls/api-ms-win-crt-utility-l1-1-0/api-ms-win-crt-utility-l1-1-0.spec b/dlls/api-ms-win-crt-utility-l1-1-0/api-ms-win-crt-utility-l1-1-0.spec index b335cf8..12586d8 100644 --- a/dlls/api-ms-win-crt-utility-l1-1-0/api-ms-win-crt-utility-l1-1-0.spec +++ b/dlls/api-ms-win-crt-utility-l1-1-0/api-ms-win-crt-utility-l1-1-0.spec @@ -3,7 +3,7 @@ @ cdecl _byteswap_ulong(long) ucrtbase._byteswap_ulong @ cdecl _byteswap_ushort(long) ucrtbase._byteswap_ushort @ cdecl _lfind(ptr ptr ptr long ptr) ucrtbase._lfind -@ stub _lfind_s +@ cdecl _lfind_s(ptr ptr ptr long ptr ptr) ucrtbase._lfind_s @ cdecl _lrotl(long long) ucrtbase._lrotl @ cdecl _lrotr(long long) ucrtbase._lrotr @ cdecl _lsearch(ptr ptr ptr long ptr) ucrtbase._lsearch diff --git a/dlls/msvcr100/msvcr100.spec b/dlls/msvcr100/msvcr100.spec index 15d5339..a33d00a 100644 --- a/dlls/msvcr100/msvcr100.spec +++ b/dlls/msvcr100/msvcr100.spec @@ -1040,7 +1040,7 @@ @ cdecl _jn(long double) MSVCRT__jn @ cdecl _kbhit() @ cdecl _lfind(ptr ptr ptr long ptr) -@ stub _lfind_s +@ cdecl _lfind_s(ptr ptr ptr long ptr ptr) @ cdecl _loaddll(str) @ cdecl -arch=x86_64 _local_unwind(ptr ptr) @ cdecl -arch=i386 _local_unwind2(ptr long) diff --git a/dlls/msvcr110/msvcr110.spec b/dlls/msvcr110/msvcr110.spec index e4ca89d..97f39a5 100644 --- a/dlls/msvcr110/msvcr110.spec +++ b/dlls/msvcr110/msvcr110.spec @@ -1386,7 +1386,7 @@ @ cdecl _jn(long double) MSVCRT__jn @ cdecl _kbhit() @ cdecl _lfind(ptr ptr ptr long ptr) -@ stub _lfind_s +@ cdecl _lfind_s(ptr ptr ptr long ptr ptr) @ cdecl -arch=i386 _libm_sse2_acos_precise() MSVCRT___libm_sse2_acos @ cdecl -arch=i386 _libm_sse2_asin_precise() MSVCRT___libm_sse2_asin @ cdecl -arch=i386 _libm_sse2_atan_precise() MSVCRT___libm_sse2_atan diff --git a/dlls/msvcr120/msvcr120.spec b/dlls/msvcr120/msvcr120.spec index f305062..aeb42ee 100644 --- a/dlls/msvcr120/msvcr120.spec +++ b/dlls/msvcr120/msvcr120.spec @@ -1396,7 +1396,7 @@ @ cdecl _ldsign(double) MSVCR120__dsign @ cdecl _ldtest(ptr) MSVCR120__ldtest @ cdecl _lfind(ptr ptr ptr long ptr) -@ stub _lfind_s +@ cdecl _lfind_s(ptr ptr ptr long ptr ptr) @ cdecl -arch=i386 _libm_sse2_acos_precise() MSVCRT___libm_sse2_acos @ cdecl -arch=i386 _libm_sse2_asin_precise() MSVCRT___libm_sse2_asin @ cdecl -arch=i386 _libm_sse2_atan_precise() MSVCRT___libm_sse2_atan diff --git a/dlls/msvcr120_app/msvcr120_app.spec b/dlls/msvcr120_app/msvcr120_app.spec index 449e8e1..cae7585 100644 --- a/dlls/msvcr120_app/msvcr120_app.spec +++ b/dlls/msvcr120_app/msvcr120_app.spec @@ -1260,7 +1260,7 @@ @ cdecl _ldsign(double) msvcr120._ldsign @ cdecl _ldtest(ptr) msvcr120._ldtest @ cdecl _lfind(ptr ptr ptr long ptr) msvcr120._lfind -@ stub _lfind_s +@ cdecl _lfind_s(ptr ptr ptr long ptr ptr) msvcr120._lfind_s @ cdecl -arch=i386 _libm_sse2_acos_precise() msvcr120._libm_sse2_acos_precise @ cdecl -arch=i386 _libm_sse2_asin_precise() msvcr120._libm_sse2_asin_precise @ cdecl -arch=i386 _libm_sse2_atan_precise() msvcr120._libm_sse2_atan_precise diff --git a/dlls/msvcr80/msvcr80.spec b/dlls/msvcr80/msvcr80.spec index 4bcef50..ab81251 100644 --- a/dlls/msvcr80/msvcr80.spec +++ b/dlls/msvcr80/msvcr80.spec @@ -712,7 +712,7 @@ @ cdecl _jn(long double) MSVCRT__jn @ cdecl _kbhit() @ cdecl _lfind(ptr ptr ptr long ptr) -@ stub _lfind_s +@ cdecl _lfind_s(ptr ptr ptr long ptr ptr) @ cdecl _loaddll(str) @ cdecl -arch=x86_64 _local_unwind(ptr ptr) @ cdecl -arch=i386 _local_unwind2(ptr long) diff --git a/dlls/msvcr90/msvcr90.spec b/dlls/msvcr90/msvcr90.spec index 5c34e77..5f7d98f 100644 --- a/dlls/msvcr90/msvcr90.spec +++ b/dlls/msvcr90/msvcr90.spec @@ -690,7 +690,7 @@ @ cdecl _jn(long double) MSVCRT__jn @ cdecl _kbhit() @ cdecl _lfind(ptr ptr ptr long ptr) -@ stub _lfind_s +@ cdecl _lfind_s(ptr ptr ptr long ptr ptr) @ cdecl _loaddll(str) @ cdecl -arch=x86_64 _local_unwind(ptr ptr) @ cdecl -arch=i386 _local_unwind2(ptr long) diff --git a/dlls/msvcrt/misc.c b/dlls/msvcrt/misc.c index c1510ef..23a089a 100644 --- a/dlls/msvcrt/misc.c +++ b/dlls/msvcrt/misc.c @@ -103,6 +103,32 @@ void* CDECL _lfind(const void* match, const void* start, }
/********************************************************************* + * _lfind_s (MSVCRT.@) + */ +void* CDECL _lfind_s(const void* match, const void* start, + unsigned int* array_size, unsigned int elem_size, + int (CDECL *cf)(void*,const void*,const void*), + void* context) +{ + unsigned int size; + if (!MSVCRT_CHECK_PMT(match != NULL)) return NULL; + if (!MSVCRT_CHECK_PMT(array_size != NULL)) return NULL; + if (!MSVCRT_CHECK_PMT(start != NULL || *array_size == 0)) return NULL; + if (!MSVCRT_CHECK_PMT(cf != NULL)) return NULL; + if (!MSVCRT_CHECK_PMT(elem_size != 0)) return NULL; + + size = *array_size; + if (size) + do + { + if (cf(context, match, start) == 0) + return (void *)start; /* found */ + start = (const char *)start + elem_size; + } while (--size); + return NULL; +} + +/********************************************************************* * _lsearch (MSVCRT.@) */ void* CDECL _lsearch(const void* match, void* start, diff --git a/dlls/msvcrt/msvcrt.spec b/dlls/msvcrt/msvcrt.spec index 0c1d4ad..d38b0fa 100644 --- a/dlls/msvcrt/msvcrt.spec +++ b/dlls/msvcrt/msvcrt.spec @@ -655,7 +655,7 @@ @ cdecl _jn(long double) MSVCRT__jn @ cdecl _kbhit() @ cdecl _lfind(ptr ptr ptr long ptr) -# stub _lfind_s(ptr ptr ptr long ptr ptr) +@ cdecl _lfind_s(ptr ptr ptr long ptr ptr) @ cdecl _loaddll(str) @ cdecl -arch=x86_64 _local_unwind(ptr ptr) @ cdecl -arch=i386 _local_unwind2(ptr long) diff --git a/dlls/msvcrt/tests/misc.c b/dlls/msvcrt/tests/misc.c index 77f2873..a6d2833 100644 --- a/dlls/msvcrt/tests/misc.c +++ b/dlls/msvcrt/tests/misc.c @@ -59,6 +59,8 @@ static void (__cdecl *p_qsort_s)(void*, MSVCRT_size_t, MSVCRT_size_t, static double (__cdecl *p_atan)(double); static double (__cdecl *p_exp)(double); static double (__cdecl *p_tanh)(double); +static void *(__cdecl *p_lfind_s)(const void*, const void*, unsigned int*, + size_t, int (__cdecl *)(void*, const void*, const void*), void*);
static void init(void) { @@ -76,6 +78,7 @@ static void init(void) p_atan = (void *)GetProcAddress(hmod, "atan"); p_exp = (void *)GetProcAddress(hmod, "exp"); p_tanh = (void *)GetProcAddress(hmod, "tanh"); + p_lfind_s = (void *)GetProcAddress(hmod, "_lfind_s"); }
static void test_rand_s(void) @@ -597,6 +600,74 @@ static void test_thread_handle_close(void) ok(ret, "ret = %d\n", ret); }
+static int __cdecl _lfind_s_comp(void *ctx, const void *l, const void *r) +{ + *(int *)ctx = 0xdeadc0de; + return *(int *)l - *(int *)r; +} + +static void test__lfind_s(void) +{ + static const int tests[] = {9000, 8001, 7002, 6003, 1003, 5004, 4005, 3006, 2007}; + unsigned int num; + void *found; + int ctx; + int key; + + if (!p_lfind_s) + { + win_skip("_lfind_s is not available\n"); + return; + } + + key = 1234; + num = sizeof(tests)/sizeof(tests[0]); + + errno = 0xdeadbeef; + found = p_lfind_s(NULL, tests, &num, sizeof(int), _lfind_s_comp, NULL); + ok(errno == EINVAL, "errno = %d\n", errno); + ok(!found, "Expected NULL, got %p\n", found); + + errno = 0xdeadbeef; + found = p_lfind_s(&key, NULL, &num, sizeof(int), _lfind_s_comp, NULL); + ok(errno == EINVAL, "errno = %d\n", errno); + ok(!found, "Expected NULL, got %p\n", found); + + errno = 0xdeadbeef; + found = p_lfind_s(&key, tests, &num, 0, _lfind_s_comp, NULL); + ok(errno == EINVAL, "errno = %d\n", errno); + ok(!found, "Expected NULL, got %p\n", found); + + errno = 0xdeadbeef; + found = p_lfind_s(&key, tests, &num, sizeof(int), NULL, NULL); + ok(errno == EINVAL, "errno = %d\n", errno); + ok(!found, "Expected NULL, got %p\n", found); + + ctx = -1; + key = 9000; + errno = 0xdeadbeef; + found = p_lfind_s(&key, tests, &num, sizeof(int), _lfind_s_comp, &ctx); + ok(errno == 0xdeadbeef, "errno = %d\n", errno); + ok(found == tests, "Expected %p, got %p\n", tests, found); + ok(ctx == 0xdeadc0de, "Expected 0xdeadc0de, got %x\n", ctx); + + ctx = -1; + key = 2007; + errno = 0xdeadbeef; + found = p_lfind_s(&key, tests, &num, sizeof(int), _lfind_s_comp, &ctx); + ok(errno == 0xdeadbeef, "errno = %d\n", errno); + ok(found == tests+8, "Expected %p, got %p\n", tests+8, found); + ok(ctx == 0xdeadc0de, "Expected 0xdeadc0de, got %x\n", ctx); + + ctx = -1; + key = 1234; + errno = 0xdeadbeef; + found = p_lfind_s(&key, tests, &num, sizeof(int), _lfind_s_comp, &ctx); + ok(errno == 0xdeadbeef, "errno = %d\n", errno); + ok(!found, "Expected NULL, got %p\n", found); + ok(ctx == 0xdeadc0de, "Expected 0xdeadc0de, got %x\n", ctx); +} + START_TEST(misc) { int arg_c; @@ -626,4 +697,5 @@ START_TEST(misc) test_qsort_s(); test_math_functions(); test_thread_handle_close(); + test__lfind_s(); } diff --git a/dlls/ucrtbase/ucrtbase.spec b/dlls/ucrtbase/ucrtbase.spec index 0005850..6253065 100644 --- a/dlls/ucrtbase/ucrtbase.spec +++ b/dlls/ucrtbase/ucrtbase.spec @@ -542,7 +542,7 @@ @ cdecl _ldtest(ptr) MSVCR120__ldtest @ stub _ldunscale @ cdecl _lfind(ptr ptr ptr long ptr) -@ stub _lfind_s +@ cdecl _lfind_s(ptr ptr ptr long ptr ptr) @ cdecl -arch=i386 _libm_sse2_acos_precise() MSVCRT___libm_sse2_acos @ cdecl -arch=i386 _libm_sse2_asin_precise() MSVCRT___libm_sse2_asin @ cdecl -arch=i386 _libm_sse2_atan_precise() MSVCRT___libm_sse2_atan