Author: akhaldi Date: Sat Sep 20 19:35:24 2014 New Revision: 64206
URL: http://svn.reactos.org/svn/reactos?rev=64206&view=rev Log: [KERNEL32_WINETEST] * Sync with Wine 1.7.27. CORE-8540
Modified: trunk/rostests/winetests/kernel32/debugger.c trunk/rostests/winetests/kernel32/file.c trunk/rostests/winetests/kernel32/heap.c trunk/rostests/winetests/kernel32/loader.c trunk/rostests/winetests/kernel32/locale.c trunk/rostests/winetests/kernel32/pipe.c trunk/rostests/winetests/kernel32/resource.c trunk/rostests/winetests/kernel32/sync.c trunk/rostests/winetests/kernel32/thread.c trunk/rostests/winetests/kernel32/time.c trunk/rostests/winetests/kernel32/virtual.c
Modified: trunk/rostests/winetests/kernel32/debugger.c URL: http://svn.reactos.org/svn/reactos/trunk/rostests/winetests/kernel32/debugge... ============================================================================== --- trunk/rostests/winetests/kernel32/debugger.c [iso-8859-1] (original) +++ trunk/rostests/winetests/kernel32/debugger.c [iso-8859-1] Sat Sep 20 19:35:24 2014 @@ -718,6 +718,8 @@
blackbox.failures = child_failures; save_blackbox(blackbox_file, &blackbox, sizeof(blackbox)); + + HeapFree(GetProcessHeap(), 0, cmd); }
static void test_debug_children(char *name, DWORD flag, BOOL debug_child)
Modified: trunk/rostests/winetests/kernel32/file.c URL: http://svn.reactos.org/svn/reactos/trunk/rostests/winetests/kernel32/file.c?... ============================================================================== --- trunk/rostests/winetests/kernel32/file.c [iso-8859-1] (original) +++ trunk/rostests/winetests/kernel32/file.c [iso-8859-1] Sat Sep 20 19:35:24 2014 @@ -3959,6 +3959,63 @@ DeleteFileA(filename); }
+static void test_WriteFileGather(void) +{ + char temp_path[MAX_PATH], filename[MAX_PATH]; + HANDLE hfile, hiocp1, hiocp2; + DWORD ret, size; + ULONG_PTR key; + FILE_SEGMENT_ELEMENT fse[2]; + OVERLAPPED ovl, *povl = NULL; + SYSTEM_INFO si; + LPVOID buf = NULL; + + ret = GetTempPathA( MAX_PATH, temp_path ); + ok( ret != 0, "GetTempPathA error %d\n", GetLastError() ); + ok( ret < MAX_PATH, "temp path should fit into MAX_PATH\n" ); + ret = GetTempFileNameA( temp_path, "wfg", 0, filename ); + ok( ret != 0, "GetTempFileNameA error %d\n", GetLastError() ); + + hfile = CreateFileA( filename, GENERIC_READ | GENERIC_WRITE, 0, 0, CREATE_ALWAYS, + FILE_FLAG_NO_BUFFERING | FILE_FLAG_OVERLAPPED | FILE_ATTRIBUTE_NORMAL, 0 ); + ok( hfile != INVALID_HANDLE_VALUE, "CreateFile failed err %u\n", GetLastError() ); + if (hfile == INVALID_HANDLE_VALUE) return; + + hiocp1 = CreateIoCompletionPort( INVALID_HANDLE_VALUE, NULL, 999, 0 ); + hiocp2 = CreateIoCompletionPort( hfile, hiocp1, 999, 0 ); + ok( hiocp2 != 0, "CreateIoCompletionPort failed err %u\n", GetLastError() ); + + GetSystemInfo( &si ); + buf = VirtualAlloc( NULL, si.dwPageSize, MEM_COMMIT, PAGE_READWRITE ); + ok( buf != NULL, "VirtualAlloc failed err %u\n", GetLastError() ); + + memset( &ovl, 0, sizeof(ovl) ); + memset( fse, 0, sizeof(fse) ); + fse[0].Buffer = buf; + if (!WriteFileGather( hfile, fse, si.dwPageSize, NULL, &ovl )) + ok( GetLastError() == ERROR_IO_PENDING, "WriteFileGather failed err %u\n", GetLastError() ); + + ret = GetQueuedCompletionStatus( hiocp2, &size, &key, &povl, 1000 ); + ok( ret, "GetQueuedCompletionStatus failed err %u\n", GetLastError()); + ok( povl == &ovl, "wrong ovl %p\n", povl ); + + memset( &ovl, 0, sizeof(ovl) ); + memset( fse, 0, sizeof(fse) ); + fse[0].Buffer = buf; + if (!ReadFileScatter( hfile, fse, si.dwPageSize, NULL, &ovl )) + ok( GetLastError() == ERROR_IO_PENDING, "ReadFileScatter failed err %u\n", GetLastError() ); + + ret = GetQueuedCompletionStatus( hiocp2, &size, &key, &povl, 1000 ); + ok( ret, "GetQueuedCompletionStatus failed err %u\n", GetLastError()); + ok( povl == &ovl, "wrong ovl %p\n", povl ); + + CloseHandle( hfile ); + CloseHandle( hiocp1 ); + CloseHandle( hiocp2 ); + VirtualFree( buf, 0, MEM_RELEASE ); + DeleteFileA( filename ); +} + static unsigned file_map_access(unsigned access) { if (access & GENERIC_READ) access |= FILE_GENERIC_READ; @@ -4132,5 +4189,6 @@ test_GetFileInformationByHandleEx(); test_OpenFileById(); test_SetFileValidData(); + test_WriteFileGather(); test_file_access(); }
Modified: trunk/rostests/winetests/kernel32/heap.c URL: http://svn.reactos.org/svn/reactos/trunk/rostests/winetests/kernel32/heap.c?... ============================================================================== --- trunk/rostests/winetests/kernel32/heap.c [iso-8859-1] (original) +++ trunk/rostests/winetests/kernel32/heap.c [iso-8859-1] Sat Sep 20 19:35:24 2014 @@ -1127,7 +1127,7 @@
if (!(heap->flags & HEAP_GROWABLE) || heap->pattern == 0xffeeffee) /* vista layout */ { - ok( heap->flags == 0, "%s: got heap flags %08x expected 0\n", arg, heap->flags ); + ok( (heap->flags & ~HEAP_GROWABLE) == 0, "%s: got heap flags %08x\n", arg, heap->flags ); } else if (heap->pattern == 0xeeeeeeee && heap->flags == 0xeeeeeeee) {
Modified: trunk/rostests/winetests/kernel32/loader.c URL: http://svn.reactos.org/svn/reactos/trunk/rostests/winetests/kernel32/loader.... ============================================================================== --- trunk/rostests/winetests/kernel32/loader.c [iso-8859-1] (original) +++ trunk/rostests/winetests/kernel32/loader.c [iso-8859-1] Sat Sep 20 19:35:24 2014 @@ -61,8 +61,8 @@ static BOOLEAN (WINAPI *pRtlDllShutdownInProgress)(void); static NTSTATUS (WINAPI *pNtAllocateVirtualMemory)(HANDLE, PVOID *, ULONG, SIZE_T *, ULONG, ULONG); static NTSTATUS (WINAPI *pNtFreeVirtualMemory)(HANDLE, PVOID *, SIZE_T *, ULONG); -static NTSTATUS (WINAPI *pLdrLockLoaderLock)(ULONG, ULONG *, ULONG *); -static NTSTATUS (WINAPI *pLdrUnlockLoaderLock)(ULONG, ULONG); +static NTSTATUS (WINAPI *pLdrLockLoaderLock)(ULONG, ULONG *, ULONG_PTR *); +static NTSTATUS (WINAPI *pLdrUnlockLoaderLock)(ULONG, ULONG_PTR); static void (WINAPI *pRtlAcquirePebLock)(void); static void (WINAPI *pRtlReleasePebLock)(void); static PVOID (WINAPI *pResolveDelayLoadedAPI)(PVOID, PCIMAGE_DELAYLOAD_DESCRIPTOR, @@ -1367,7 +1367,7 @@ if (ret == WAIT_OBJECT_0) break; else if (ret == WAIT_OBJECT_0 + 1) { - ULONG loader_lock_magic; + ULONG_PTR loader_lock_magic; trace("%04u: mutex_thread_proc: Entering loader lock\n", GetCurrentThreadId()); ret = pLdrLockLoaderLock(0, NULL, &loader_lock_magic); ok(!ret, "LdrLockLoaderLock error %#x\n", ret);
Modified: trunk/rostests/winetests/kernel32/locale.c URL: http://svn.reactos.org/svn/reactos/trunk/rostests/winetests/kernel32/locale.... ============================================================================== --- trunk/rostests/winetests/kernel32/locale.c [iso-8859-1] (original) +++ trunk/rostests/winetests/kernel32/locale.c [iso-8859-1] Sat Sep 20 19:35:24 2014 @@ -93,27 +93,36 @@ static INT (WINAPI *pCompareStringOrdinal)(const WCHAR *, INT, const WCHAR *, INT, BOOL); static INT (WINAPI *pCompareStringEx)(LPCWSTR, DWORD, LPCWSTR, INT, LPCWSTR, INT, LPNLSVERSIONINFO, LPVOID, LPARAM); +static INT (WINAPI *pGetGeoInfoA)(GEOID, GEOTYPE, LPSTR, INT, LANGID); +static INT (WINAPI *pGetGeoInfoW)(GEOID, GEOTYPE, LPWSTR, INT, LANGID); +static BOOL (WINAPI *pEnumSystemGeoID)(GEOCLASS, GEOID, GEO_ENUMPROC);
static void InitFunctionPointers(void) { hKernel32 = GetModuleHandleA("kernel32"); - pEnumSystemLanguageGroupsA = (void*)GetProcAddress(hKernel32, "EnumSystemLanguageGroupsA"); - pEnumLanguageGroupLocalesA = (void*)GetProcAddress(hKernel32, "EnumLanguageGroupLocalesA"); - pLocaleNameToLCID = (void*)GetProcAddress(hKernel32, "LocaleNameToLCID"); - pLCIDToLocaleName = (void*)GetProcAddress(hKernel32, "LCIDToLocaleName"); - pLCMapStringEx = (void*)GetProcAddress(hKernel32, "LCMapStringEx"); - pFoldStringA = (void*)GetProcAddress(hKernel32, "FoldStringA"); - pFoldStringW = (void*)GetProcAddress(hKernel32, "FoldStringW"); - pIsValidLanguageGroup = (void*)GetProcAddress(hKernel32, "IsValidLanguageGroup"); - pEnumUILanguagesA = (void*)GetProcAddress(hKernel32, "EnumUILanguagesA"); - pEnumSystemLocalesEx = (void*)GetProcAddress(hKernel32, "EnumSystemLocalesEx"); - pIdnToNameprepUnicode = (void*)GetProcAddress(hKernel32, "IdnToNameprepUnicode"); - pIdnToAscii = (void*)GetProcAddress(hKernel32, "IdnToAscii"); - pIdnToUnicode = (void*)GetProcAddress(hKernel32, "IdnToUnicode"); - pGetLocaleInfoEx = (void*)GetProcAddress(hKernel32, "GetLocaleInfoEx"); - pIsValidLocaleName = (void*)GetProcAddress(hKernel32, "IsValidLocaleName"); - pCompareStringOrdinal = (void*)GetProcAddress(hKernel32, "CompareStringOrdinal"); - pCompareStringEx = (void*)GetProcAddress(hKernel32, "CompareStringEx"); + +#define X(f) p##f = (void*)GetProcAddress(hKernel32, #f) + X(EnumSystemLanguageGroupsA); + X(EnumLanguageGroupLocalesA); + X(LocaleNameToLCID); + X(LCIDToLocaleName); + X(LCMapStringEx); + X(FoldStringA); + X(FoldStringW); + X(IsValidLanguageGroup); + X(EnumUILanguagesA); + X(EnumSystemLocalesEx); + X(IdnToNameprepUnicode); + X(IdnToAscii); + X(IdnToUnicode); + X(GetLocaleInfoEx); + X(IsValidLocaleName); + X(CompareStringOrdinal); + X(CompareStringEx); + X(GetGeoInfoA); + X(GetGeoInfoW); + X(EnumSystemGeoID); +#undef X }
#define eq(received, expected, label, type) \ @@ -2532,6 +2541,7 @@ 0x0C66, /* Telugu */ 0x0CE6, /* Kannada */ 0x0D66, /* Maylayalam */ + 0x0DE6, /* Sinhala Lith */ 0x0E50, /* Thai */ 0x0ED0, /* Laos */ 0x0F20, /* Tibet */ @@ -2563,6 +2573,7 @@ 0xA8D0, /* Saurashtra */ 0xA900, /* Kayah Li */ 0xA9D0, /* Javanese */ + 0xA9F0, /* Myanmar Tai Laing */ 0xAA50, /* Cham */ 0xABF0, /* Meetei Mayek */ 0xff10, /* Pliene chasse (?) */ @@ -3059,7 +3070,6 @@ BOOL ret; LCID lcid = MAKELCID(MAKELANGID(LANG_ENGLISH, SUBLANG_ENGLISH_US), SORT_DEFAULT);
- trace("EnumDateFormatsA 0\n"); date_fmt_buf[0] = 0; SetLastError(0xdeadbeef); ret = EnumDateFormatsA(enum_datetime_procA, lcid, 0); @@ -3070,7 +3080,7 @@ else { ok(ret, "EnumDateFormatsA(0) error %d\n", GetLastError()); - trace("%s\n", date_fmt_buf); + trace("EnumDateFormatsA(0): %s\n", date_fmt_buf); /* test the 1st enumerated format */ if ((p = strchr(date_fmt_buf, '\n'))) *p = 0; ret = GetLocaleInfoA(lcid, LOCALE_SSHORTDATE, buf, sizeof(buf)); @@ -3078,7 +3088,6 @@ ok(!lstrcmpA(date_fmt_buf, buf), "expected "%s" got "%s"\n", date_fmt_buf, buf); }
- trace("EnumDateFormatsA LOCALE_USE_CP_ACP\n"); date_fmt_buf[0] = 0; SetLastError(0xdeadbeef); ret = EnumDateFormatsA(enum_datetime_procA, lcid, LOCALE_USE_CP_ACP); @@ -3089,7 +3098,7 @@ else { ok(ret, "EnumDateFormatsA(LOCALE_USE_CP_ACP) error %d\n", GetLastError()); - trace("%s\n", date_fmt_buf); + trace("EnumDateFormatsA(LOCALE_USE_CP_ACP): %s\n", date_fmt_buf); /* test the 1st enumerated format */ if ((p = strchr(date_fmt_buf, '\n'))) *p = 0; ret = GetLocaleInfoA(lcid, LOCALE_SSHORTDATE, buf, sizeof(buf)); @@ -3097,39 +3106,36 @@ ok(!lstrcmpA(date_fmt_buf, buf), "expected "%s" got "%s"\n", date_fmt_buf, buf); }
- trace("EnumDateFormatsA DATE_SHORTDATE\n"); date_fmt_buf[0] = 0; ret = EnumDateFormatsA(enum_datetime_procA, lcid, DATE_SHORTDATE); ok(ret, "EnumDateFormatsA(DATE_SHORTDATE) error %d\n", GetLastError()); - trace("%s\n", date_fmt_buf); + trace("EnumDateFormatsA(DATE_SHORTDATE): %s\n", date_fmt_buf); /* test the 1st enumerated format */ if ((p = strchr(date_fmt_buf, '\n'))) *p = 0; ret = GetLocaleInfoA(lcid, LOCALE_SSHORTDATE, buf, sizeof(buf)); ok(ret, "GetLocaleInfoA(LOCALE_SSHORTDATE) error %d\n", GetLastError()); ok(!lstrcmpA(date_fmt_buf, buf), "expected "%s" got "%s"\n", date_fmt_buf, buf);
- trace("EnumDateFormatsA DATE_LONGDATE\n"); date_fmt_buf[0] = 0; ret = EnumDateFormatsA(enum_datetime_procA, lcid, DATE_LONGDATE); ok(ret, "EnumDateFormatsA(DATE_LONGDATE) error %d\n", GetLastError()); - trace("%s\n", date_fmt_buf); + trace("EnumDateFormatsA(DATE_LONGDATE): %s\n", date_fmt_buf); /* test the 1st enumerated format */ if ((p = strchr(date_fmt_buf, '\n'))) *p = 0; ret = GetLocaleInfoA(lcid, LOCALE_SLONGDATE, buf, sizeof(buf)); ok(ret, "GetLocaleInfoA(LOCALE_SLONGDATE) error %d\n", GetLastError()); ok(!lstrcmpA(date_fmt_buf, buf), "expected "%s" got "%s"\n", date_fmt_buf, buf);
- trace("EnumDateFormatsA DATE_YEARMONTH\n"); date_fmt_buf[0] = 0; SetLastError(0xdeadbeef); ret = EnumDateFormatsA(enum_datetime_procA, lcid, DATE_YEARMONTH); if (!ret && (GetLastError() == ERROR_INVALID_FLAGS)) { - skip("DATE_YEARMONTH is only present on W2K and later\n"); + win_skip("DATE_YEARMONTH is only present on W2K and later\n"); return; } ok(ret, "EnumDateFormatsA(DATE_YEARMONTH) error %d\n", GetLastError()); - trace("%s\n", date_fmt_buf); + trace("EnumDateFormatsA(DATE_YEARMONTH): %s\n", date_fmt_buf); /* test the 1st enumerated format */ if ((p = strchr(date_fmt_buf, '\n'))) *p = 0; ret = GetLocaleInfoA(lcid, LOCALE_SYEARMONTH, buf, sizeof(buf)); @@ -3144,22 +3150,20 @@ BOOL ret; LCID lcid = MAKELCID(MAKELANGID(LANG_ENGLISH, SUBLANG_ENGLISH_US), SORT_DEFAULT);
- trace("EnumTimeFormatsA 0\n"); date_fmt_buf[0] = 0; ret = EnumTimeFormatsA(enum_datetime_procA, lcid, 0); ok(ret, "EnumTimeFormatsA(0) error %d\n", GetLastError()); - trace("%s\n", date_fmt_buf); + trace("EnumTimeFormatsA(0): %s\n", date_fmt_buf); /* test the 1st enumerated format */ if ((p = strchr(date_fmt_buf, '\n'))) *p = 0; ret = GetLocaleInfoA(lcid, LOCALE_STIMEFORMAT, buf, sizeof(buf)); ok(ret, "GetLocaleInfoA(LOCALE_STIMEFORMAT) error %d\n", GetLastError()); ok(!lstrcmpA(date_fmt_buf, buf), "expected "%s" got "%s"\n", date_fmt_buf, buf);
- trace("EnumTimeFormatsA LOCALE_USE_CP_ACP\n"); date_fmt_buf[0] = 0; ret = EnumTimeFormatsA(enum_datetime_procA, lcid, LOCALE_USE_CP_ACP); ok(ret, "EnumTimeFormatsA(LOCALE_USE_CP_ACP) error %d\n", GetLastError()); - trace("%s\n", date_fmt_buf); + trace("EnumTimeFormatsA(LOCALE_USE_CP_ACP): %s\n", date_fmt_buf); /* test the 1st enumerated format */ if ((p = strchr(date_fmt_buf, '\n'))) *p = 0; ret = GetLocaleInfoA(lcid, LOCALE_STIMEFORMAT, buf, sizeof(buf)); @@ -3182,7 +3186,7 @@ ret = GetCPInfo(CP_UTF7, &cpinfo); if (!ret && GetLastError() == ERROR_INVALID_PARAMETER) { - skip("Codepage CP_UTF7 is not installed/available\n"); + win_skip("Codepage CP_UTF7 is not installed/available\n"); } else { @@ -3198,7 +3202,7 @@ ret = GetCPInfo(CP_UTF8, &cpinfo); if (!ret && GetLastError() == ERROR_INVALID_PARAMETER) { - skip("Codepage CP_UTF8 is not installed/available\n"); + win_skip("Codepage CP_UTF8 is not installed/available\n"); } else { @@ -3279,6 +3283,7 @@ static const WCHAR space_special[] = {0x09, 0x0d, 0x85};
WORD types[20]; + WCHAR ch; int i;
memset(types,0,sizeof(types)); @@ -3335,6 +3340,21 @@ GetStringTypeW(CT_CTYPE1, space_special, 3, types); for (i = 0; i < 3; i++) ok(types[i] & C1_SPACE || broken(types[i] == C1_CNTRL) || broken(types[i] == 0), "incorrect types returned for %x -> (%x does not have %x)\n",space_special[i], types[i], C1_SPACE ); + + /* surrogate pairs */ + ch = 0xd800; + memset(types, 0, sizeof(types)); + GetStringTypeW(CT_CTYPE3, &ch, 1, types); + if (types[0] == C3_NOTAPPLICABLE) + win_skip("C3_HIGHSURROGATE/C3_LOWSURROGATE are not supported.\n"); + else { + ok(types[0] == C3_HIGHSURROGATE, "got %x\n", types[0]); + + ch = 0xdc00; + memset(types, 0, sizeof(types)); + GetStringTypeW(CT_CTYPE3, &ch, 1, types); + ok(types[0] == C3_LOWSURROGATE, "got %x\n", types[0]); + } }
static void test_IdnToNameprepUnicode(void) @@ -3829,6 +3849,153 @@ ok(ret == CSTR_LESS_THAN, "Got %u, expected %u\n", ret, CSTR_LESS_THAN); }
+static void test_GetGeoInfo(void) +{ + char buffA[20]; + INT ret; + + if (!pGetGeoInfoA) + { + win_skip("GetGeoInfo is not available.\n"); + return; + } + + /* unassigned id */ + SetLastError(0xdeadbeef); + ret = pGetGeoInfoA(344, GEO_ISO2, NULL, 0, 0); + ok(ret == 0, "got %d\n", ret); + ok(GetLastError() == ERROR_INVALID_PARAMETER, "got %d\n", GetLastError()); + + ret = pGetGeoInfoA(203, GEO_ISO2, NULL, 0, 0); + ok(ret == 3, "got %d\n", ret); + + ret = pGetGeoInfoA(203, GEO_ISO3, NULL, 0, 0); + ok(ret == 4, "got %d\n", ret); + + ret = pGetGeoInfoA(203, GEO_ISO2, buffA, 3, 0); + ok(ret == 3, "got %d\n", ret); + ok(!strcmp(buffA, "RU"), "got %s\n", buffA); + + /* buffer pointer not NULL, length is 0 - return required length */ + buffA[0] = 'a'; + SetLastError(0xdeadbeef); + ret = pGetGeoInfoA(203, GEO_ISO2, buffA, 0, 0); + ok(ret == 3, "got %d\n", ret); + ok(buffA[0] == 'a', "got %c\n", buffA[0]); + + ret = pGetGeoInfoA(203, GEO_ISO3, buffA, 4, 0); + ok(ret == 4, "got %d\n", ret); + ok(!strcmp(buffA, "RUS"), "got %s\n", buffA); + + /* shorter buffer */ + SetLastError(0xdeadbeef); + buffA[1] = buffA[2] = 0; + ret = pGetGeoInfoA(203, GEO_ISO2, buffA, 2, 0); + ok(ret == 0, "got %d\n", ret); + ok(!strcmp(buffA, "RU"), "got %s\n", buffA); + ok(GetLastError() == ERROR_INSUFFICIENT_BUFFER, "got %d\n", GetLastError()); + + /* GEO_NATION returns GEOID in a string form */ + buffA[0] = 0; + ret = pGetGeoInfoA(203, GEO_NATION, buffA, 20, 0); + ok(ret == 4, "got %d\n", ret); + ok(!strcmp(buffA, "203"), "got %s\n", buffA); + + /* GEO_PARENT */ + buffA[0] = 0; + ret = pGetGeoInfoA(203, GEO_PARENT, buffA, 20, 0); + if (ret == 0) + win_skip("GEO_PARENT not supported.\n"); + else + { + ok(ret == 6, "got %d\n", ret); + ok(!strcmp(buffA, "47609"), "got %s\n", buffA); + } + + buffA[0] = 0; + ret = pGetGeoInfoA(203, GEO_ISO_UN_NUMBER, buffA, 20, 0); + if (ret == 0) + win_skip("GEO_ISO_UN_NUMBER not supported.\n"); + else + { + ok(ret == 4, "got %d\n", ret); + ok(!strcmp(buffA, "643"), "got %s\n", buffA); + } + + /* try invalid type value */ + SetLastError(0xdeadbeef); + ret = pGetGeoInfoA(203, GEO_PARENT + 1, NULL, 0, 0); + ok(ret == 0, "got %d\n", ret); + ok(GetLastError() == ERROR_INVALID_FLAGS, "got %d\n", GetLastError()); +} + +static int geoidenum_count; +static BOOL CALLBACK test_geoid_enumproc(GEOID geoid) +{ + INT ret = pGetGeoInfoA(geoid, GEO_ISO2, NULL, 0, 0); + ok(ret == 3, "got %d for %d\n", ret, geoid); + /* valid geoid starts at 2 */ + ok(geoid >= 2, "got geoid %d\n", geoid); + + return geoidenum_count++ < 5; +} + +static BOOL CALLBACK test_geoid_enumproc2(GEOID geoid) +{ + geoidenum_count++; + return TRUE; +} + +static void test_EnumSystemGeoID(void) +{ + BOOL ret; + + if (!pEnumSystemGeoID) + { + win_skip("EnumSystemGeoID is not available.\n"); + return; + } + + SetLastError(0xdeadbeef); + ret = pEnumSystemGeoID(GEOCLASS_NATION, 0, NULL); + ok(!ret, "got %d\n", ret); + ok(GetLastError() == ERROR_INVALID_PARAMETER, "got %d\n", GetLastError()); + + SetLastError(0xdeadbeef); + ret = pEnumSystemGeoID(GEOCLASS_NATION+1, 0, test_geoid_enumproc); + ok(!ret, "got %d\n", ret); + ok(GetLastError() == ERROR_INVALID_FLAGS, "got %d\n", GetLastError()); + + SetLastError(0xdeadbeef); + ret = pEnumSystemGeoID(GEOCLASS_NATION+1, 0, NULL); + ok(!ret, "got %d\n", ret); + ok(GetLastError() == ERROR_INVALID_PARAMETER, "got %d\n", GetLastError()); + + ret = pEnumSystemGeoID(GEOCLASS_NATION, 0, test_geoid_enumproc); + ok(ret, "got %d\n", ret); + + /* only first level is enumerated, not the whole hierarchy */ + geoidenum_count = 0; + ret = pEnumSystemGeoID(GEOCLASS_NATION, 39070, test_geoid_enumproc2); + if (ret == 0) + win_skip("Parent GEOID is not supported in EnumSystemGeoID.\n"); + else + ok(ret && geoidenum_count > 0, "got %d, count %d\n", ret, geoidenum_count); + + geoidenum_count = 0; + ret = pEnumSystemGeoID(GEOCLASS_REGION, 39070, test_geoid_enumproc2); + if (ret == 0) + win_skip("GEOCLASS_REGION is not supported in EnumSystemGeoID.\n"); + else + { + ok(ret && geoidenum_count > 0, "got %d, count %d\n", ret, geoidenum_count); + + geoidenum_count = 0; + ret = pEnumSystemGeoID(GEOCLASS_REGION, 0, test_geoid_enumproc2); + ok(ret && geoidenum_count > 0, "got %d, count %d\n", ret, geoidenum_count); + } +} + START_TEST(locale) { InitFunctionPointers(); @@ -3864,6 +4031,8 @@ test_IdnToUnicode(); test_IsValidLocaleName(); test_CompareStringOrdinal(); + test_GetGeoInfo(); + test_EnumSystemGeoID(); /* this requires collation table patch to make it MS compatible */ if (0) test_sorting(); }
Modified: trunk/rostests/winetests/kernel32/pipe.c URL: http://svn.reactos.org/svn/reactos/trunk/rostests/winetests/kernel32/pipe.c?... ============================================================================== --- trunk/rostests/winetests/kernel32/pipe.c [iso-8859-1] (original) +++ trunk/rostests/winetests/kernel32/pipe.c [iso-8859-1] Sat Sep 20 19:35:24 2014 @@ -43,6 +43,72 @@ user_apc_ran = TRUE; }
+ +enum rpcThreadOp +{ + RPC_READFILE +}; + +struct rpcThreadArgs +{ + ULONG_PTR returnValue; + DWORD lastError; + enum rpcThreadOp op; + ULONG_PTR args[5]; +}; + +static DWORD CALLBACK rpcThreadMain(LPVOID arg) +{ + struct rpcThreadArgs *rpcargs = (struct rpcThreadArgs *)arg; + trace("rpcThreadMain starting\n"); + SetLastError( rpcargs->lastError ); + + switch (rpcargs->op) + { + case RPC_READFILE: + rpcargs->returnValue = (ULONG_PTR)ReadFile( (HANDLE)rpcargs->args[0], /* hFile */ + (LPVOID)rpcargs->args[1], /* buffer */ + (DWORD)rpcargs->args[2], /* bytesToRead */ + (LPDWORD)rpcargs->args[3], /* bytesRead */ + (LPOVERLAPPED)rpcargs->args[4] ); /* overlapped */ + break; + + default: + SetLastError( ERROR_CALL_NOT_IMPLEMENTED ); + rpcargs->returnValue = 0; + break; + } + + rpcargs->lastError = GetLastError(); + trace("rpcThreadMain returning\n"); + return 0; +} + +/* Runs ReadFile(...) from a different thread */ +static BOOL RpcReadFile(HANDLE hFile, LPVOID buffer, DWORD bytesToRead, LPDWORD bytesRead, LPOVERLAPPED overlapped) +{ + struct rpcThreadArgs rpcargs; + HANDLE thread; + DWORD threadId; + + rpcargs.returnValue = 0; + rpcargs.lastError = GetLastError(); + rpcargs.op = RPC_READFILE; + rpcargs.args[0] = (ULONG_PTR)hFile; + rpcargs.args[1] = (ULONG_PTR)buffer; + rpcargs.args[2] = (ULONG_PTR)bytesToRead; + rpcargs.args[3] = (ULONG_PTR)bytesRead; + rpcargs.args[4] = (ULONG_PTR)overlapped; + + thread = CreateThread(NULL, 0, rpcThreadMain, (void *)&rpcargs, 0, &threadId); + ok(thread != NULL, "CreateThread failed. %d\n", GetLastError()); + ok(WaitForSingleObject(thread, INFINITE) == WAIT_OBJECT_0, "WaitForSingleObject failed with %d.\n", GetLastError()); + CloseHandle(thread); + + SetLastError(rpcargs.lastError); + return (BOOL)rpcargs.returnValue; +} + static void test_CreateNamedPipe(int pipemode) { HANDLE hnp; @@ -60,6 +126,12 @@ trace("test_CreateNamedPipe starting in byte mode\n"); else trace("test_CreateNamedPipe starting in message mode\n"); + + /* Wait for non existing pipe */ + ret = WaitNamedPipeA(PIPENAME, 2000); + ok(ret == 0, "WaitNamedPipe returned %d for non existing pipe\n", ret); + ok(GetLastError() == ERROR_FILE_NOT_FOUND, "wrong error %u\n", GetLastError()); + /* Bad parameter checks */ hnp = CreateNamedPipeA("not a named pipe", PIPE_ACCESS_DUPLEX, pipemode | PIPE_WAIT, /* nMaxInstances */ 1, @@ -119,6 +191,21 @@ HANDLE hFile2;
/* Make sure we can read and write a few bytes in both directions */ + memset(ibuf, 0, sizeof(ibuf)); + ok(WriteFile(hnp, obuf, sizeof(obuf), &written, NULL), "WriteFile\n"); + ok(written == sizeof(obuf), "write file len\n"); + ok(ReadFile(hFile, ibuf, sizeof(ibuf), &readden, NULL), "ReadFile\n"); + ok(readden == sizeof(obuf), "read got %d bytes\n", readden); + ok(memcmp(obuf, ibuf, written) == 0, "content check\n"); + + memset(ibuf, 0, sizeof(ibuf)); + ok(WriteFile(hFile, obuf2, sizeof(obuf2), &written, NULL), "WriteFile\n"); + ok(written == sizeof(obuf2), "write file len\n"); + ok(ReadFile(hnp, ibuf, sizeof(ibuf), &readden, NULL), "ReadFile\n"); + ok(readden == sizeof(obuf2), "read got %d bytes\n", readden); + ok(memcmp(obuf2, ibuf, written) == 0, "content check\n"); + + /* Now the same again, but with an additional call to PeekNamedPipe */ memset(ibuf, 0, sizeof(ibuf)); ok(WriteFile(hnp, obuf, sizeof(obuf), &written, NULL), "WriteFile\n"); ok(written == sizeof(obuf), "write file len 1\n"); @@ -139,6 +226,65 @@ ok(readden == sizeof(obuf2), "read 2 got %d bytes\n", readden); ok(memcmp(obuf2, ibuf, written) == 0, "content 2 check\n");
+ /* Test how ReadFile behaves when the buffer is not big enough for the whole message */ + memset(ibuf, 0, sizeof(ibuf)); + ok(WriteFile(hnp, obuf2, sizeof(obuf2), &written, NULL), "WriteFile\n"); + ok(written == sizeof(obuf2), "write file len\n"); + ok(ReadFile(hFile, ibuf, 4, &readden, NULL), "ReadFile\n"); + ok(readden == 4, "read got %d bytes\n", readden); + ok(ReadFile(hFile, ibuf + 4, sizeof(ibuf) - 4, &readden, NULL), "ReadFile\n"); + ok(readden == sizeof(obuf2) - 4, "read got %d bytes\n", readden); + ok(memcmp(obuf2, ibuf, written) == 0, "content check\n"); + + memset(ibuf, 0, sizeof(ibuf)); + ok(WriteFile(hFile, obuf, sizeof(obuf), &written, NULL), "WriteFile\n"); + ok(written == sizeof(obuf), "write file len\n"); + if (pipemode == PIPE_TYPE_BYTE) + { + ok(ReadFile(hnp, ibuf, 4, &readden, NULL), "ReadFile\n"); + } + else + { + SetLastError(0xdeadbeef); + todo_wine + ok(!ReadFile(hnp, ibuf, 4, &readden, NULL), "ReadFile\n"); + todo_wine + ok(GetLastError() == ERROR_MORE_DATA, "wrong error\n"); + } + ok(readden == 4, "read got %d bytes\n", readden); + ok(ReadFile(hnp, ibuf + 4, sizeof(ibuf) - 4, &readden, NULL), "ReadFile\n"); + ok(readden == sizeof(obuf) - 4, "read got %d bytes\n", readden); + ok(memcmp(obuf, ibuf, written) == 0, "content check\n"); + + /* Similar to above, but use a read buffer size small enough to read in three parts */ + memset(ibuf, 0, sizeof(ibuf)); + ok(WriteFile(hFile, obuf2, sizeof(obuf2), &written, NULL), "WriteFile\n"); + ok(written == sizeof(obuf2), "write file len\n"); + if (pipemode == PIPE_TYPE_BYTE) + { + ok(ReadFile(hnp, ibuf, 4, &readden, NULL), "ReadFile\n"); + ok(readden == 4, "read got %d bytes\n", readden); + ok(ReadFile(hnp, ibuf + 4, 4, &readden, NULL), "ReadFile\n"); + } + else + { + SetLastError(0xdeadbeef); + todo_wine + ok(!ReadFile(hnp, ibuf, 4, &readden, NULL), "ReadFile\n"); + todo_wine + ok(GetLastError() == ERROR_MORE_DATA, "wrong error\n"); + ok(readden == 4, "read got %d bytes\n", readden); + SetLastError(0xdeadbeef); + todo_wine + ok(!ReadFile(hnp, ibuf + 4, 4, &readden, NULL), "ReadFile\n"); + todo_wine + ok(GetLastError() == ERROR_MORE_DATA, "wrong error\n"); + } + ok(readden == 4, "read got %d bytes\n", readden); + ok(ReadFile(hnp, ibuf + 8, sizeof(ibuf) - 8, &readden, NULL), "ReadFile\n"); + ok(readden == sizeof(obuf2) - 8, "read got %d bytes\n", readden); + ok(memcmp(obuf2, ibuf, written) == 0, "content check\n"); + /* Test reading of multiple writes */ memset(ibuf, 0, sizeof(ibuf)); ok(WriteFile(hnp, obuf, sizeof(obuf), &written, NULL), "WriteFile3a\n"); @@ -147,20 +293,13 @@ ok(written == sizeof(obuf2), "write file len 3b\n"); ok(PeekNamedPipe(hFile, ibuf, sizeof(ibuf), &readden, &avail, NULL), "Peek3\n"); if (pipemode == PIPE_TYPE_BYTE) { - if (readden != sizeof(obuf)) /* Linux only returns the first message */ - ok(readden == sizeof(obuf) + sizeof(obuf2), "peek3 got %d bytes\n", readden); - else - todo_wine ok(readden == sizeof(obuf) + sizeof(obuf2), "peek3 got %d bytes\n", readden); + todo_wine ok(readden == sizeof(obuf) + sizeof(obuf2), "peek3 got %d bytes\n", readden); } else { - if (readden != sizeof(obuf) + sizeof(obuf2)) /* MacOS returns both messages */ - ok(readden == sizeof(obuf), "peek3 got %d bytes\n", readden); - else - todo_wine ok(readden == sizeof(obuf), "peek3 got %d bytes\n", readden); - } - if (avail != sizeof(obuf)) /* older Linux kernels only return the first write here */ - ok(avail == sizeof(obuf) + sizeof(obuf2), "peek3 got %d bytes available\n", avail); + ok(readden == sizeof(obuf), "peek3 got %d bytes\n", readden); + } + ok(avail == sizeof(obuf) + sizeof(obuf2), "peek3 got %d bytes available\n", avail); pbuf = ibuf; ok(memcmp(obuf, pbuf, sizeof(obuf)) == 0, "pipe content 3a check\n"); if (pipemode == PIPE_TYPE_BYTE && readden >= sizeof(obuf)+sizeof(obuf2)) { @@ -182,21 +321,13 @@ ok(written == sizeof(obuf2), "write file len 4b\n"); ok(PeekNamedPipe(hnp, ibuf, sizeof(ibuf), &readden, &avail, NULL), "Peek4\n"); if (pipemode == PIPE_TYPE_BYTE) { - if (readden != sizeof(obuf)) /* Linux only returns the first message */ - /* should return all 23 bytes */ - ok(readden == sizeof(obuf) + sizeof(obuf2), "peek4 got %d bytes\n", readden); - else - todo_wine ok(readden == sizeof(obuf) + sizeof(obuf2), "peek4 got %d bytes\n", readden); + todo_wine ok(readden == sizeof(obuf) + sizeof(obuf2), "peek4 got %d bytes\n", readden); } else { - if (readden != sizeof(obuf) + sizeof(obuf2)) /* MacOS returns both messages */ - ok(readden == sizeof(obuf), "peek4 got %d bytes\n", readden); - else - todo_wine ok(readden == sizeof(obuf), "peek4 got %d bytes\n", readden); - } - if (avail != sizeof(obuf)) /* older Linux kernels only return the first write here */ - ok(avail == sizeof(obuf) + sizeof(obuf2), "peek4 got %d bytes available\n", avail); + ok(readden == sizeof(obuf), "peek4 got %d bytes\n", readden); + } + ok(avail == sizeof(obuf) + sizeof(obuf2), "peek4 got %d bytes available\n", avail); pbuf = ibuf; ok(memcmp(obuf, pbuf, sizeof(obuf)) == 0, "pipe content 4a check\n"); if (pipemode == PIPE_TYPE_BYTE && readden >= sizeof(obuf)+sizeof(obuf2)) { @@ -227,9 +358,7 @@ ok(!SetNamedPipeHandleState(hFile, &lpmode, NULL, NULL), "Change mode\n"); } else { - todo_wine { - ok(SetNamedPipeHandleState(hFile, &lpmode, NULL, NULL), "Change mode\n"); - } + ok(SetNamedPipeHandleState(hFile, &lpmode, NULL, NULL), "Change mode\n");
memset(ibuf, 0, sizeof(ibuf)); ok(WriteFile(hnp, obuf, sizeof(obuf), &written, NULL), "WriteFile5a\n"); @@ -237,14 +366,8 @@ ok(WriteFile(hnp, obuf2, sizeof(obuf2), &written, NULL), " WriteFile5b\n"); ok(written == sizeof(obuf2), "write file len 3b\n"); ok(PeekNamedPipe(hFile, ibuf, sizeof(ibuf), &readden, &avail, NULL), "Peek5\n"); - if (readden != sizeof(obuf) + sizeof(obuf2)) /* MacOS returns both writes */ - ok(readden == sizeof(obuf), "peek5 got %d bytes\n", readden); - else - todo_wine ok(readden == sizeof(obuf), "peek5 got %d bytes\n", readden); - if (avail != sizeof(obuf)) /* older Linux kernels only return the first write here */ - ok(avail == sizeof(obuf) + sizeof(obuf2), "peek5 got %d bytes available\n", avail); - else - todo_wine ok(avail == sizeof(obuf) + sizeof(obuf2), "peek5 got %d bytes available\n", avail); + ok(readden == sizeof(obuf), "peek5 got %d bytes\n", readden); + ok(avail == sizeof(obuf) + sizeof(obuf2), "peek5 got %d bytes available\n", avail); pbuf = ibuf; ok(memcmp(obuf, pbuf, sizeof(obuf)) == 0, "content 5a check\n"); ok(ReadFile(hFile, ibuf, sizeof(ibuf), &readden, NULL), "ReadFile\n"); @@ -253,7 +376,9 @@ } pbuf = ibuf; ok(memcmp(obuf, pbuf, sizeof(obuf)) == 0, "content 5a check\n"); - + if (readden <= sizeof(obuf)) + ok(ReadFile(hFile, ibuf, sizeof(ibuf), &readden, NULL), "ReadFile\n"); + /* Multiple writes in the reverse direction */ /* the write of obuf2 from write4 should still be in the buffer */ ok(PeekNamedPipe(hnp, ibuf, sizeof(ibuf), &readden, &avail, NULL), "Peek6a\n"); @@ -273,12 +398,8 @@ ok(WriteFile(hFile, obuf2, sizeof(obuf2), &written, NULL), " WriteFile6b\n"); ok(written == sizeof(obuf2), "write file len 6b\n"); ok(PeekNamedPipe(hnp, ibuf, sizeof(ibuf), &readden, &avail, NULL), "Peek6\n"); - if (readden != sizeof(obuf) + sizeof(obuf2)) /* MacOS returns both writes */ - ok(readden == sizeof(obuf), "peek6 got %d bytes\n", readden); - else - todo_wine ok(readden == sizeof(obuf), "peek6 got %d bytes\n", readden); - if (avail != sizeof(obuf)) /* older Linux kernels only return the first write here */ - ok(avail == sizeof(obuf) + sizeof(obuf2), "peek6b got %d bytes available\n", avail); + ok(readden == sizeof(obuf), "peek6 got %d bytes\n", readden); + ok(avail == sizeof(obuf) + sizeof(obuf2), "peek6b got %d bytes available\n", avail); pbuf = ibuf; ok(memcmp(obuf, pbuf, sizeof(obuf)) == 0, "content 6a check\n"); ok(ReadFile(hnp, ibuf, sizeof(ibuf), &readden, NULL), "ReadFile\n"); @@ -287,6 +408,129 @@ } pbuf = ibuf; ok(memcmp(obuf, pbuf, sizeof(obuf)) == 0, "content 6a check\n"); + if (readden <= sizeof(obuf)) + ok(ReadFile(hnp, ibuf, sizeof(ibuf), &readden, NULL), "ReadFile\n"); + + /* Test how ReadFile behaves when the buffer is not big enough for the whole message */ + memset(ibuf, 0, sizeof(ibuf)); + ok(WriteFile(hnp, obuf2, sizeof(obuf2), &written, NULL), "WriteFile 7\n"); + ok(written == sizeof(obuf2), "write file len 7\n"); + SetLastError(0xdeadbeef); + todo_wine + ok(!ReadFile(hFile, ibuf, 4, &readden, NULL), "ReadFile 7\n"); + todo_wine + ok(GetLastError() == ERROR_MORE_DATA, "wrong error 7\n"); + ok(readden == 4, "read got %d bytes 7\n", readden); + ok(ReadFile(hFile, ibuf + 4, sizeof(ibuf) - 4, &readden, NULL), "ReadFile 7\n"); + ok(readden == sizeof(obuf2) - 4, "read got %d bytes 7\n", readden); + ok(memcmp(obuf2, ibuf, written) == 0, "content check 7\n"); + + memset(ibuf, 0, sizeof(ibuf)); + ok(WriteFile(hFile, obuf, sizeof(obuf), &written, NULL), "WriteFile 8\n"); + ok(written == sizeof(obuf), "write file len 8\n"); + SetLastError(0xdeadbeef); + todo_wine + ok(!ReadFile(hnp, ibuf, 4, &readden, NULL), "ReadFile 8\n"); + todo_wine + ok(GetLastError() == ERROR_MORE_DATA, "wrong error 8\n"); + ok(readden == 4, "read got %d bytes 8\n", readden); + ok(ReadFile(hnp, ibuf + 4, sizeof(ibuf) - 4, &readden, NULL), "ReadFile 8\n"); + ok(readden == sizeof(obuf) - 4, "read got %d bytes 8\n", readden); + ok(memcmp(obuf, ibuf, written) == 0, "content check 8\n"); + + /* The following test shows that when doing a partial read of a message, the rest + * is still in the pipe, and can be received from a second thread. This shows + * especially that the content is _not_ stored in thread-local-storage until it is + * completely transmitted. The same method works even across multiple processes. */ + memset(ibuf, 0, sizeof(ibuf)); + ok(WriteFile(hnp, obuf, sizeof(obuf), &written, NULL), "WriteFile 9\n"); + ok(written == sizeof(obuf), "write file len 9\n"); + ok(WriteFile(hnp, obuf2, sizeof(obuf2), &written, NULL), "WriteFile 9\n"); + ok(written == sizeof(obuf2), "write file len 9\n"); + SetLastError(0xdeadbeef); + todo_wine + ok(!ReadFile(hFile, ibuf, 4, &readden, NULL), "ReadFile 9\n"); + todo_wine + ok(GetLastError() == ERROR_MORE_DATA, "wrong error 9\n"); + ok(readden == 4, "read got %d bytes 9\n", readden); + SetLastError(0xdeadbeef); + ret = RpcReadFile(hFile, ibuf + 4, 4, &readden, NULL); + todo_wine + ok(!ret, "RpcReadFile 9\n"); + todo_wine + ok(GetLastError() == ERROR_MORE_DATA, "wrong error 9\n"); + ok(readden == 4, "read got %d bytes 9\n", readden); + ret = RpcReadFile(hFile, ibuf + 8, sizeof(ibuf), &readden, NULL); + ok(ret, "RpcReadFile 9\n"); + todo_wine + ok(readden == sizeof(obuf) - 8, "read got %d bytes 9\n", readden); + ok(memcmp(obuf, ibuf, sizeof(obuf)) == 0, "content check 9\n"); + if (readden <= sizeof(obuf) - 8) /* blocks forever if second part was already received */ + { + memset(ibuf, 0, sizeof(ibuf)); + SetLastError(0xdeadbeef); + ret = RpcReadFile(hFile, ibuf, 4, &readden, NULL); + ok(!ret, "RpcReadFile 9\n"); + todo_wine + ok(GetLastError() == ERROR_MORE_DATA, "wrong error 9\n"); + ok(readden == 4, "read got %d bytes 9\n", readden); + SetLastError(0xdeadbeef); + todo_wine + ok(!ReadFile(hFile, ibuf + 4, 4, &readden, NULL), "ReadFile 9\n"); + todo_wine + ok(GetLastError() == ERROR_MORE_DATA, "wrong error 9\n"); + ok(readden == 4, "read got %d bytes 9\n", readden); + ret = RpcReadFile(hFile, ibuf + 8, sizeof(ibuf), &readden, NULL); + ok(ret, "RpcReadFile 9\n"); + ok(readden == sizeof(obuf2) - 8, "read got %d bytes 9\n", readden); + ok(memcmp(obuf2, ibuf, sizeof(obuf2)) == 0, "content check 9\n"); + } + + /* Now the reverse direction */ + memset(ibuf, 0, sizeof(ibuf)); + ok(WriteFile(hFile, obuf2, sizeof(obuf2), &written, NULL), "WriteFile 10\n"); + ok(written == sizeof(obuf2), "write file len 10\n"); + ok(WriteFile(hFile, obuf, sizeof(obuf), &written, NULL), "WriteFile 10\n"); + ok(written == sizeof(obuf), "write file len 10\n"); + SetLastError(0xdeadbeef); + todo_wine + ok(!ReadFile(hnp, ibuf, 4, &readden, NULL), "ReadFile 10\n"); + todo_wine + ok(GetLastError() == ERROR_MORE_DATA, "wrong error 10\n"); + ok(readden == 4, "read got %d bytes 10\n", readden); + SetLastError(0xdeadbeef); + ret = RpcReadFile(hnp, ibuf + 4, 4, &readden, NULL); + todo_wine + ok(!ret, "RpcReadFile 10\n"); + todo_wine + ok(GetLastError() == ERROR_MORE_DATA, "wrong error 10\n"); + ok(readden == 4, "read got %d bytes 10\n", readden); + ret = RpcReadFile(hnp, ibuf + 8, sizeof(ibuf), &readden, NULL); + ok(ret, "RpcReadFile 10\n"); + todo_wine + ok(readden == sizeof(obuf2) - 8, "read got %d bytes 10\n", readden); + ok(memcmp(obuf2, ibuf, sizeof(obuf2)) == 0, "content check 10\n"); + if (readden <= sizeof(obuf2) - 8) /* blocks forever if second part was already received */ + { + memset(ibuf, 0, sizeof(ibuf)); + SetLastError(0xdeadbeef); + ret = RpcReadFile(hnp, ibuf, 4, &readden, NULL); + ok(!ret, "RpcReadFile 10\n"); + todo_wine + ok(GetLastError() == ERROR_MORE_DATA, "wrong error 10\n"); + ok(readden == 4, "read got %d bytes 10\n", readden); + SetLastError(0xdeadbeef); + todo_wine + ok(!ReadFile(hnp, ibuf + 4, 4, &readden, NULL), "ReadFile 10\n"); + todo_wine + ok(GetLastError() == ERROR_MORE_DATA, "wrong error 10\n"); + ok(readden == 4, "read got %d bytes 10\n", readden); + ret = RpcReadFile(hnp, ibuf + 8, sizeof(ibuf), &readden, NULL); + ok(ret, "RpcReadFile 10\n"); + ok(readden == sizeof(obuf) - 8, "read got %d bytes 10\n", readden); + ok(memcmp(obuf, ibuf, sizeof(obuf)) == 0, "content check 10\n"); + } + }
/* Picky conformance tests */ @@ -1656,11 +1900,9 @@ /* lpSecurityAttrib */ NULL); ok(server != INVALID_HANDLE_VALUE, "cf failed\n"); ret = GetNamedPipeHandleStateA(server, NULL, NULL, NULL, NULL, NULL, 0); - todo_wine ok(ret, "GetNamedPipeHandleState failed: %d\n", GetLastError()); ret = GetNamedPipeHandleStateA(server, &state, &instances, NULL, NULL, NULL, 0); - todo_wine ok(ret, "GetNamedPipeHandleState failed: %d\n", GetLastError()); if (ret) { @@ -1681,7 +1923,6 @@ state = PIPE_READMODE_MESSAGE; SetLastError(0xdeadbeef); ret = SetNamedPipeHandleState(server, &state, NULL, NULL); - todo_wine ok(!ret && GetLastError() == ERROR_INVALID_PARAMETER, "expected ERROR_INVALID_PARAMETER, got %d\n", GetLastError());
@@ -1691,13 +1932,11 @@
state = PIPE_READMODE_BYTE; ret = SetNamedPipeHandleState(client, &state, NULL, NULL); - todo_wine ok(ret, "SetNamedPipeHandleState failed: %d\n", GetLastError()); /* A byte-mode pipe client can't be changed to message mode, either. */ state = PIPE_READMODE_MESSAGE; SetLastError(0xdeadbeef); ret = SetNamedPipeHandleState(server, &state, NULL, NULL); - todo_wine ok(!ret && GetLastError() == ERROR_INVALID_PARAMETER, "expected ERROR_INVALID_PARAMETER, got %d\n", GetLastError());
@@ -1713,11 +1952,9 @@ /* lpSecurityAttrib */ NULL); ok(server != INVALID_HANDLE_VALUE, "cf failed\n"); ret = GetNamedPipeHandleStateA(server, NULL, NULL, NULL, NULL, NULL, 0); - todo_wine ok(ret, "GetNamedPipeHandleState failed: %d\n", GetLastError()); ret = GetNamedPipeHandleStateA(server, &state, &instances, NULL, NULL, NULL, 0); - todo_wine ok(ret, "GetNamedPipeHandleState failed: %d\n", GetLastError()); if (ret) { @@ -1729,7 +1966,6 @@ */ state = PIPE_READMODE_BYTE; ret = SetNamedPipeHandleState(server, &state, NULL, NULL); - todo_wine ok(ret, "SetNamedPipeHandleState failed: %d\n", GetLastError());
client = CreateFileA(PIPENAME, GENERIC_READ|GENERIC_WRITE, 0, NULL, @@ -1738,13 +1974,11 @@
state = PIPE_READMODE_MESSAGE; ret = SetNamedPipeHandleState(client, &state, NULL, NULL); - todo_wine ok(ret, "SetNamedPipeHandleState failed: %d\n", GetLastError()); /* A message-mode pipe client can also be changed to byte mode. */ state = PIPE_READMODE_BYTE; ret = SetNamedPipeHandleState(client, &state, NULL, NULL); - todo_wine ok(ret, "SetNamedPipeHandleState failed: %d\n", GetLastError());
CloseHandle(client); @@ -1851,6 +2085,14 @@
wait = WaitForSingleObjectEx(event, 0, TRUE); ok(wait == WAIT_IO_COMPLETION || wait == WAIT_OBJECT_0, "WaitForSingleObject returned %x\n", wait); + if (wait == WAIT_TIMEOUT) + { + ret = ReadFile(client, read_buf, sizeof(read_buf), &num_bytes, NULL); + ok(ret == TRUE, "ReadFile failed\n"); + ok(completion_called == 0, "completion routine called during ReadFile\n"); + wait = WaitForSingleObjectEx(event, 0, TRUE); + ok(wait == WAIT_IO_COMPLETION || wait == WAIT_OBJECT_0, "WaitForSingleObject returned %x\n", wait); + }
ok(completion_called == 1, "completion routine not called\n"); ok(completion_errorcode == 0, "completion called with error %x\n", completion_errorcode);
Modified: trunk/rostests/winetests/kernel32/resource.c URL: http://svn.reactos.org/svn/reactos/trunk/rostests/winetests/kernel32/resourc... ============================================================================== --- trunk/rostests/winetests/kernel32/resource.c [iso-8859-1] (original) +++ trunk/rostests/winetests/kernel32/resource.c [iso-8859-1] Sat Sep 20 19:35:24 2014 @@ -394,6 +394,7 @@ int i; IMAGE_DOS_HEADER *dos; IMAGE_NT_HEADERS *nt; + IMAGE_OPTIONAL_HEADER *opt; IMAGE_SECTION_HEADER *sec; IMAGE_RESOURCE_DIRECTORY *dir; HANDLE file, mapping; @@ -415,6 +416,7 @@ goto end;
nt = (void*) ((BYTE*) dos + dos->e_lfanew); + opt = &nt->OptionalHeader; sec = (void*) &nt[1];
for(i = 0; i < max_sections; i++) @@ -444,6 +446,10 @@ verify->NumberOfNamedEntries, dir->NumberOfNamedEntries); ok( dir->NumberOfIdEntries == verify->NumberOfIdEntries, "NumberOfIdEntries should be %d instead of %d\n", verify->NumberOfIdEntries, dir->NumberOfIdEntries); + + ok(opt->DataDirectory[IMAGE_FILE_RESOURCE_DIRECTORY].VirtualAddress == sec[verify->rsrc_section].VirtualAddress, + "VirtualAddress in optional header should be %d instead of %d\n", + sec[verify->rsrc_section].VirtualAddress, opt->DataDirectory[IMAGE_FILE_RESOURCE_DIRECTORY].VirtualAddress); }
end:
Modified: trunk/rostests/winetests/kernel32/sync.c URL: http://svn.reactos.org/svn/reactos/trunk/rostests/winetests/kernel32/sync.c?... ============================================================================== --- trunk/rostests/winetests/kernel32/sync.c [iso-8859-1] (original) +++ trunk/rostests/winetests/kernel32/sync.c [iso-8859-1] Sat Sep 20 19:35:24 2014 @@ -24,8 +24,9 @@ #include <stdio.h> #include <windef.h> #include <winbase.h> - -#include "wine/test.h" +#include <winternl.h> + +#include <wine/test.h>
static BOOL (WINAPI *pChangeTimerQueueTimer)(HANDLE, HANDLE, ULONG, ULONG); static HANDLE (WINAPI *pCreateTimerQueue)(void); @@ -55,6 +56,7 @@ static VOID (WINAPI *pReleaseSRWLockShared)(PSRWLOCK); static BOOLEAN (WINAPI *pTryAcquireSRWLockExclusive)(PSRWLOCK); static BOOLEAN (WINAPI *pTryAcquireSRWLockShared)(PSRWLOCK); +static NTSTATUS (WINAPI *pNtWaitForMultipleObjects)(ULONG,const HANDLE*,BOOLEAN,BOOLEAN,const LARGE_INTEGER*);
static void test_signalandwait(void) { @@ -1153,15 +1155,32 @@ }
/* a manual-reset event remains signaled, an auto-reset event is cleared */ - r = WaitForMultipleObjects(MAXIMUM_WAIT_OBJECTS, maxevents, 0, 0); + r = WaitForMultipleObjects(MAXIMUM_WAIT_OBJECTS, maxevents, FALSE, 0); ok( r == WAIT_OBJECT_0, "should signal lowest handle first, got %d\n", r); - r = WaitForMultipleObjects(MAXIMUM_WAIT_OBJECTS, maxevents, 0, 0); + r = WaitForMultipleObjects(MAXIMUM_WAIT_OBJECTS, maxevents, FALSE, 0); ok( r == WAIT_OBJECT_0, "should signal handle #0 first, got %d\n", r); ok(ResetEvent(maxevents[0]), "ResetEvent\n"); for (i=1; i<MAXIMUM_WAIT_OBJECTS; i++) { /* the lowest index is checked first and remaining events are untouched */ - r = WaitForMultipleObjects(MAXIMUM_WAIT_OBJECTS, maxevents, 0, 0); + r = WaitForMultipleObjects(MAXIMUM_WAIT_OBJECTS, maxevents, FALSE, 0); + ok( r == WAIT_OBJECT_0+i, "should signal handle #%d first, got %d\n", i, r); + } + + /* run same test with Nt* call */ + for (i=0; i<MAXIMUM_WAIT_OBJECTS; i++) + SetEvent(maxevents[i]); + + /* a manual-reset event remains signaled, an auto-reset event is cleared */ + r = pNtWaitForMultipleObjects(MAXIMUM_WAIT_OBJECTS, maxevents, TRUE, FALSE, NULL); + ok( r == WAIT_OBJECT_0, "should signal lowest handle first, got %d\n", r); + r = pNtWaitForMultipleObjects(MAXIMUM_WAIT_OBJECTS, maxevents, TRUE, FALSE, NULL); + ok( r == WAIT_OBJECT_0, "should signal handle #0 first, got %d\n", r); + ok(ResetEvent(maxevents[0]), "ResetEvent\n"); + for (i=1; i<MAXIMUM_WAIT_OBJECTS; i++) + { + /* the lowest index is checked first and remaining events are untouched */ + r = pNtWaitForMultipleObjects(MAXIMUM_WAIT_OBJECTS, maxevents, TRUE, FALSE, NULL); ok( r == WAIT_OBJECT_0+i, "should signal handle #%d first, got %d\n", i, r); }
@@ -2117,7 +2136,7 @@ { /* seq 15 */ while (srwlock_seq < 15) Sleep(1); - Sleep(50); /* some delay, such that thread2 can try to acquire a second exclusive lock */ + Sleep(50); /* some delay, so that thread2 can try to acquire a second exclusive lock */ if (InterlockedIncrement(&srwlock_seq) != 16) InterlockedIncrement(&srwlock_base_errors.wrong_execution_order);
@@ -2287,6 +2306,8 @@ START_TEST(sync) { HMODULE hdll = GetModuleHandleA("kernel32.dll"); + HMODULE hntdll = GetModuleHandleA("ntdll.dll"); + pChangeTimerQueueTimer = (void*)GetProcAddress(hdll, "ChangeTimerQueueTimer"); pCreateTimerQueue = (void*)GetProcAddress(hdll, "CreateTimerQueue"); pCreateTimerQueueTimer = (void*)GetProcAddress(hdll, "CreateTimerQueueTimer"); @@ -2312,6 +2333,7 @@ pReleaseSRWLockShared = (void *)GetProcAddress(hdll, "ReleaseSRWLockShared"); pTryAcquireSRWLockExclusive = (void *)GetProcAddress(hdll, "TryAcquireSRWLockExclusive"); pTryAcquireSRWLockShared = (void *)GetProcAddress(hdll, "TryAcquireSRWLockShared"); + pNtWaitForMultipleObjects = (void *)GetProcAddress(hntdll, "NtWaitForMultipleObjects");
test_signalandwait(); test_mutex();
Modified: trunk/rostests/winetests/kernel32/thread.c URL: http://svn.reactos.org/svn/reactos/trunk/rostests/winetests/kernel32/thread.... ============================================================================== --- trunk/rostests/winetests/kernel32/thread.c [iso-8859-1] (original) +++ trunk/rostests/winetests/kernel32/thread.c [iso-8859-1] Sat Sep 20 19:35:24 2014 @@ -1576,6 +1576,7 @@ b = pGetCurrentActCtx(&handle); ok(b, "GetCurentActCtx failed: %u\n", GetLastError()); ok(handle != 0, "no active context\n"); + pReleaseActCtx(handle);
param.handle = NULL; b = pGetCurrentActCtx(¶m.handle); @@ -1588,6 +1589,7 @@ ret = WaitForSingleObject(thread, 1000); ok(ret == WAIT_OBJECT_0, "wait timeout\n"); ok(param.thread_context == context, "got wrong thread context %p, %p\n", param.thread_context, context); + pReleaseActCtx(param.thread_context); CloseHandle(thread);
/* similar test for CreateRemoteThread() */ @@ -1598,7 +1600,10 @@ ret = WaitForSingleObject(thread, 1000); ok(ret == WAIT_OBJECT_0, "wait timeout\n"); ok(param.thread_context == context, "got wrong thread context %p, %p\n", param.thread_context, context); + pReleaseActCtx(param.thread_context); CloseHandle(thread); + + pReleaseActCtx(param.handle);
b = pDeactivateActCtx(0, cookie); ok(b, "DeactivateActCtx failed: %u\n", GetLastError());
Modified: trunk/rostests/winetests/kernel32/time.c URL: http://svn.reactos.org/svn/reactos/trunk/rostests/winetests/kernel32/time.c?... ============================================================================== --- trunk/rostests/winetests/kernel32/time.c [iso-8859-1] (original) +++ trunk/rostests/winetests/kernel32/time.c [iso-8859-1] Sat Sep 20 19:35:24 2014 @@ -667,7 +667,7 @@ char bufferA[20]; WCHAR bufferW[20]; DWORD val1, val2; - int ret; + int ret, ret2;
if (!pGetCalendarInfoA || !pGetCalendarInfoW) { @@ -716,6 +716,21 @@ ret = pGetCalendarInfoW( 0x0409, CAL_GREGORIAN, CAL_ITWODIGITYEARMAX, NULL, 0, NULL ); ok( ret, "GetCalendarInfoW failed err %u\n", GetLastError() ); ok( ret == 5, "wrong size %u\n", ret ); + + ret = pGetCalendarInfoA( LANG_SYSTEM_DEFAULT, CAL_GREGORIAN, CAL_SDAYNAME1, + bufferA, sizeof(bufferA), NULL); + ok( ret, "GetCalendarInfoA failed err %u\n", GetLastError() ); + ret2 = pGetCalendarInfoA( LANG_SYSTEM_DEFAULT, CAL_GREGORIAN, CAL_SDAYNAME1, + bufferA, 0, NULL); + ok( ret2, "GetCalendarInfoA failed err %u\n", GetLastError() ); + ok( ret == ret2, "got %d, expected %d\n", ret2, ret ); + + ret2 = pGetCalendarInfoW( LANG_SYSTEM_DEFAULT, CAL_GREGORIAN, CAL_SDAYNAME1, + bufferW, sizeof(bufferW), NULL); + ok( ret2, "GetCalendarInfoW failed err %u\n", GetLastError() ); + ret2 = WideCharToMultiByte( CP_ACP, 0, bufferW, -1, NULL, 0, NULL, NULL ); + ok( ret == ret2, "got %d, expected %d\n", ret, ret2 ); + }
START_TEST(time)
Modified: trunk/rostests/winetests/kernel32/virtual.c URL: http://svn.reactos.org/svn/reactos/trunk/rostests/winetests/kernel32/virtual... ============================================================================== --- trunk/rostests/winetests/kernel32/virtual.c [iso-8859-1] (original) +++ trunk/rostests/winetests/kernel32/virtual.c [iso-8859-1] Sat Sep 20 19:35:24 2014 @@ -2447,7 +2447,7 @@ DeleteFileA(file_name); }
-static void test_shared_memory(int is_child) +static void test_shared_memory(BOOL is_child) { HANDLE mapping; LONG *p; @@ -2489,6 +2489,51 @@ CloseHandle(mapping); }
+static void test_shared_memory_ro(BOOL is_child, DWORD child_access) +{ + HANDLE mapping; + LONG *p; + + SetLastError(0xdeadbef); + mapping = CreateFileMappingA(INVALID_HANDLE_VALUE, NULL, PAGE_READWRITE, 0, 4096, "winetest_virtual.c_ro"); + ok(mapping != 0, "CreateFileMapping error %d\n", GetLastError()); + if (is_child) + ok(GetLastError() == ERROR_ALREADY_EXISTS, "expected ERROR_ALREADY_EXISTS, got %d\n", GetLastError()); + + SetLastError(0xdeadbef); + p = MapViewOfFile(mapping, is_child ? child_access : FILE_MAP_READ, 0, 0, 4096); + ok(p != NULL, "MapViewOfFile error %d\n", GetLastError()); + + if (is_child) + { + *p = 0xdeadbeef; + } + else + { + char **argv; + char cmdline[MAX_PATH]; + PROCESS_INFORMATION pi; + STARTUPINFOA si = { sizeof(si) }; + DWORD ret; + + winetest_get_mainargs(&argv); + sprintf(cmdline, ""%s" virtual sharedmemro %x", argv[0], child_access); + ret = CreateProcessA(argv[0], cmdline, NULL, NULL, FALSE, 0, NULL, NULL, &si, &pi); + ok(ret, "CreateProcess(%s) error %d\n", cmdline, GetLastError()); + winetest_wait_child_process(pi.hProcess); + CloseHandle(pi.hThread); + CloseHandle(pi.hProcess); + + if(child_access & FILE_MAP_WRITE) + ok(*p == 0xdeadbeef, "*p = %x, expected 0xdeadbeef\n", *p); + else + ok(!*p, "*p = %x, expected 0\n", *p); + } + + UnmapViewOfFile(p); + CloseHandle(mapping); +} + START_TEST(virtual) { int argc; @@ -2504,7 +2549,19 @@ } if (!strcmp(argv[2], "sharedmem")) { - test_shared_memory(1); + test_shared_memory(TRUE); + return; + } + if (!strcmp(argv[2], "sharedmemro")) + { + if(!winetest_interactive) + { + skip("CORE-8541: Skipping test_shared_memory_ro(TRUE, strtol(argv[3], NULL, 16))\n"); + } + else + { + test_shared_memory_ro(TRUE, strtol(argv[3], NULL, 16)); + } return; } while (1) @@ -2532,7 +2589,10 @@ pNtMapViewOfSection = (void *)GetProcAddress(GetModuleHandleA("ntdll.dll"), "NtMapViewOfSection"); pNtUnmapViewOfSection = (void *)GetProcAddress(GetModuleHandleA("ntdll.dll"), "NtUnmapViewOfSection");
- test_shared_memory(0); + test_shared_memory(FALSE); + test_shared_memory_ro(FALSE, FILE_MAP_READ|FILE_MAP_WRITE); + test_shared_memory_ro(FALSE, FILE_MAP_COPY); + test_shared_memory_ro(FALSE, FILE_MAP_COPY|FILE_MAP_WRITE); test_mapping(); test_CreateFileMapping_protection(); test_VirtualAlloc_protection();