ReactOS  0.4.15-dev-506-ga3ec01c
sync.c
Go to the documentation of this file.
1 /*
2  * Synchronization tests
3  *
4  * Copyright 2005 Mike McCormack for CodeWeavers
5  *
6  * This library is free software; you can redistribute it and/or
7  * modify it under the terms of the GNU Lesser General Public
8  * License as published by the Free Software Foundation; either
9  * version 2.1 of the License, or (at your option) any later version.
10  *
11  * This library is distributed in the hope that it will be useful,
12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14  * Lesser General Public License for more details.
15  *
16  * You should have received a copy of the GNU Lesser General Public
17  * License along with this library; if not, write to the Free Software
18  * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
19  */
20 
21 #include <stdarg.h>
22 #include <stdlib.h>
23 #include <stdio.h>
24 #include <windef.h>
25 #include <winbase.h>
26 #include <winternl.h>
27 
28 #include "wine/test.h"
29 
30 #ifdef __REACTOS__
31 #define QueryDepthSList(x) RtlQueryDepthSList(x)
32 #define InterlockedPushEntrySList(x,y) RtlInterlockedPushEntrySList(x,y)
33 #define InterlockedPopEntrySList(x) RtlInterlockedPopEntrySList(x)
34 #define InterlockedFlushSList(x) RtlInterlockedFlushSList(x)
35 #endif
36 
37 #undef __fastcall
38 #define __fastcall __stdcall
39 
40 static HANDLE (WINAPI *pCreateMemoryResourceNotification)(MEMORY_RESOURCE_NOTIFICATION_TYPE);
41 static BOOL (WINAPI *pQueryMemoryResourceNotification)(HANDLE, PBOOL);
42 static VOID (WINAPI *pInitOnceInitialize)(PINIT_ONCE);
43 static BOOL (WINAPI *pInitOnceExecuteOnce)(PINIT_ONCE,PINIT_ONCE_FN,PVOID,LPVOID*);
44 static BOOL (WINAPI *pInitOnceBeginInitialize)(PINIT_ONCE,DWORD,BOOL*,LPVOID*);
45 static BOOL (WINAPI *pInitOnceComplete)(PINIT_ONCE,DWORD,LPVOID);
46 
47 static VOID (WINAPI *pInitializeConditionVariable)(PCONDITION_VARIABLE);
48 static BOOL (WINAPI *pSleepConditionVariableCS)(PCONDITION_VARIABLE,PCRITICAL_SECTION,DWORD);
49 static BOOL (WINAPI *pSleepConditionVariableSRW)(PCONDITION_VARIABLE,PSRWLOCK,DWORD,ULONG);
50 static VOID (WINAPI *pWakeAllConditionVariable)(PCONDITION_VARIABLE);
51 static VOID (WINAPI *pWakeConditionVariable)(PCONDITION_VARIABLE);
52 
53 static VOID (WINAPI *pInitializeSRWLock)(PSRWLOCK);
54 static VOID (WINAPI *pAcquireSRWLockExclusive)(PSRWLOCK);
55 static VOID (WINAPI *pAcquireSRWLockShared)(PSRWLOCK);
56 static VOID (WINAPI *pReleaseSRWLockExclusive)(PSRWLOCK);
57 static VOID (WINAPI *pReleaseSRWLockShared)(PSRWLOCK);
58 static BOOLEAN (WINAPI *pTryAcquireSRWLockExclusive)(PSRWLOCK);
59 static BOOLEAN (WINAPI *pTryAcquireSRWLockShared)(PSRWLOCK);
60 
61 static NTSTATUS (WINAPI *pNtAllocateVirtualMemory)(HANDLE, PVOID *, ULONG, SIZE_T *, ULONG, ULONG);
62 static NTSTATUS (WINAPI *pNtFreeVirtualMemory)(HANDLE, PVOID *, SIZE_T *, ULONG);
63 static NTSTATUS (WINAPI *pNtWaitForSingleObject)(HANDLE, BOOLEAN, const LARGE_INTEGER *);
64 static NTSTATUS (WINAPI *pNtWaitForMultipleObjects)(ULONG,const HANDLE*,BOOLEAN,BOOLEAN,const LARGE_INTEGER*);
65 static PSLIST_ENTRY (__fastcall *pRtlInterlockedPushListSList)(PSLIST_HEADER list, PSLIST_ENTRY first,
67 static PSLIST_ENTRY (WINAPI *pRtlInterlockedPushListSListEx)(PSLIST_HEADER list, PSLIST_ENTRY first,
69 
70 #ifdef __i386__
71 
72 #include "pshpack1.h"
73 struct fastcall_thunk
74 {
75  BYTE pop_edx; /* popl %edx (ret addr) */
76  BYTE pop_eax; /* popl %eax (func) */
77  BYTE pop_ecx; /* popl %ecx (param 1) */
78  BYTE xchg[3]; /* xchgl (%esp),%edx (param 2) */
79  WORD jmp_eax; /* jmp *%eax */
80 };
81 #include "poppack.h"
82 
83 static void * (WINAPI *call_fastcall_func4)(void *func, const void *a, const void *b, const void *c, const void *d);
84 
85 static void init_fastcall_thunk(void)
86 {
87  struct fastcall_thunk *thunk = VirtualAlloc(NULL, sizeof(*thunk), MEM_COMMIT, PAGE_EXECUTE_READWRITE);
88  thunk->pop_edx = 0x5a; /* popl %edx */
89  thunk->pop_eax = 0x58; /* popl %eax */
90  thunk->pop_ecx = 0x59; /* popl %ecx */
91  thunk->xchg[0] = 0x87; /* xchgl (%esp),%edx */
92  thunk->xchg[1] = 0x14;
93  thunk->xchg[2] = 0x24;
94  thunk->jmp_eax = 0xe0ff; /* jmp *%eax */
95  call_fastcall_func4 = (void *)thunk;
96 }
97 
98 #define call_func4(func, a, b, c, d) call_fastcall_func4(func, (const void *)(a), \
99  (const void *)(b), (const void *)(c), (const void *)(d))
100 
101 #else /* __i386__ */
102 
103 #define init_fastcall_thunk() do { } while(0)
104 #define call_func4(func, a, b, c, d) func(a, b, c, d)
105 
106 #endif /* __i386__ */
107 
108 static void test_signalandwait(void)
109 {
110  DWORD r;
111  HANDLE event[2], semaphore[2], file;
112  int i;
113 
114  /* invalid parameters */
115  r = SignalObjectAndWait(NULL, NULL, 0, 0);
116  ok( r == WAIT_FAILED, "should fail\n");
117 
118  event[0] = CreateEventW(NULL, 0, 0, NULL);
119  event[1] = CreateEventW(NULL, 1, 1, NULL);
120 
121  ok( event[0] && event[1], "failed to create event flags\n");
122 
123  r = SignalObjectAndWait(event[0], NULL, 0, FALSE);
124  ok( r == WAIT_FAILED, "should fail\n");
125 
126  r = SignalObjectAndWait(NULL, event[0], 0, FALSE);
127  ok( r == WAIT_FAILED, "should fail\n");
128 
129 
130  /* valid parameters */
131  r = SignalObjectAndWait(event[0], event[1], 0, FALSE);
132  ok( r == WAIT_OBJECT_0, "should succeed\n");
133 
134  /* event[0] is now signalled - we repeat this test multiple times
135  * to ensure that the wineserver handles this situation properly. */
136  for (i = 0; i < 10000; i++)
137  {
138  r = SignalObjectAndWait(event[0], event[0], 0, FALSE);
139  ok(r == WAIT_OBJECT_0, "should succeed\n");
140  }
141 
142  /* event[0] is not signalled */
143  r = WaitForSingleObject(event[0], 0);
144  ok( r == WAIT_TIMEOUT, "event was signalled\n");
145 
146  r = SignalObjectAndWait(event[0], event[0], 0, FALSE);
147  ok( r == WAIT_OBJECT_0, "should succeed\n");
148 
149  /* clear event[1] and check for a timeout */
150  ok(ResetEvent(event[1]), "failed to clear event[1]\n");
151  r = SignalObjectAndWait(event[0], event[1], 0, FALSE);
152  ok( r == WAIT_TIMEOUT, "should timeout\n");
153 
154  CloseHandle(event[0]);
155  CloseHandle(event[1]);
156 
157  /* semaphores */
158  semaphore[0] = CreateSemaphoreW( NULL, 0, 1, NULL );
159  semaphore[1] = CreateSemaphoreW( NULL, 1, 1, NULL );
160  ok( semaphore[0] && semaphore[1], "failed to create semaphore\n");
161 
163  ok( r == WAIT_OBJECT_0, "should succeed\n");
164 
166  ok( r == WAIT_FAILED, "should fail\n");
167 
169  ok( r == FALSE, "should fail\n");
170 
172  ok( r == TRUE, "should succeed\n");
173 
176 
177  /* try a registry key */
181  ok( r == WAIT_FAILED, "should fail\n");
182  ok( ERROR_INVALID_HANDLE == GetLastError(), "should return invalid handle error\n");
183  CloseHandle(file);
184 }
185 
186 static void test_mutex(void)
187 {
188  DWORD wait_ret;
189  BOOL ret;
190  HANDLE hCreated;
191  HANDLE hOpened;
192  int i;
193  DWORD failed = 0;
194 
195  SetLastError(0xdeadbeef);
196  hOpened = OpenMutexA(0, FALSE, "WineTestMutex");
197  ok(hOpened == NULL, "OpenMutex succeeded\n");
198  ok(GetLastError() == ERROR_FILE_NOT_FOUND, "wrong error %u\n", GetLastError());
199 
200  SetLastError(0xdeadbeef);
201  hCreated = CreateMutexA(NULL, FALSE, "WineTestMutex");
202  ok(hCreated != NULL, "CreateMutex failed with error %d\n", GetLastError());
203 
204  SetLastError(0xdeadbeef);
205  hOpened = OpenMutexA(0, FALSE, "WineTestMutex");
206 todo_wine
207  ok(hOpened == NULL, "OpenMutex succeeded\n");
208 todo_wine
209  ok(GetLastError() == ERROR_ACCESS_DENIED, "wrong error %u\n", GetLastError());
210 
211  SetLastError(0xdeadbeef);
212  hOpened = OpenMutexA(GENERIC_EXECUTE, FALSE, "WineTestMutex");
213  ok(hOpened != NULL, "OpenMutex failed with error %d\n", GetLastError());
214  wait_ret = WaitForSingleObject(hOpened, INFINITE);
215  ok(wait_ret == WAIT_OBJECT_0, "WaitForSingleObject failed with error %d\n", GetLastError());
216  CloseHandle(hOpened);
217 
218  for(i=0; i < 31; i++)
219  {
220  wait_ret = WaitForSingleObject(hCreated, INFINITE);
221  ok(wait_ret == WAIT_OBJECT_0, "WaitForSingleObject failed with error 0x%08x\n", wait_ret);
222  }
223 
224  SetLastError(0xdeadbeef);
225  hOpened = OpenMutexA(GENERIC_READ | GENERIC_WRITE, FALSE, "WineTestMutex");
226  ok(hOpened != NULL, "OpenMutex failed with error %d\n", GetLastError());
227  wait_ret = WaitForSingleObject(hOpened, INFINITE);
228  ok(wait_ret == WAIT_FAILED, "WaitForSingleObject succeeded\n");
229  CloseHandle(hOpened);
230 
231  for (i = 0; i < 32; i++)
232  {
233  SetLastError(0xdeadbeef);
234  hOpened = OpenMutexA(0x1 << i, FALSE, "WineTestMutex");
235  if(hOpened != NULL)
236  {
237  SetLastError(0xdeadbeef);
238  ret = ReleaseMutex(hOpened);
239  ok(ret, "ReleaseMutex failed with error %d, access %x\n", GetLastError(), 1 << i);
240  CloseHandle(hOpened);
241  }
242  else
243  {
244  if ((1 << i) == ACCESS_SYSTEM_SECURITY)
245  todo_wine ok(GetLastError() == ERROR_PRIVILEGE_NOT_HELD, "wrong error %u, access %x\n", GetLastError(), 1 << i);
246  else
247  todo_wine ok(GetLastError() == ERROR_ACCESS_DENIED, "wrong error %u, , access %x\n", GetLastError(), 1 << i);
248  ReleaseMutex(hCreated);
249  failed |=0x1 << i;
250  }
251  }
252 
253 todo_wine
254  ok( failed == 0x0de0fffe, "open succeeded when it shouldn't: %x\n", failed);
255 
256  SetLastError(0xdeadbeef);
257  ret = ReleaseMutex(hCreated);
258  ok(!ret && (GetLastError() == ERROR_NOT_OWNER),
259  "ReleaseMutex should have failed with ERROR_NOT_OWNER instead of %d\n", GetLastError());
260 
261  /* test case sensitivity */
262 
263  SetLastError(0xdeadbeef);
264  hOpened = OpenMutexA(READ_CONTROL, FALSE, "WINETESTMUTEX");
265  ok(!hOpened, "OpenMutex succeeded\n");
266  ok(GetLastError() == ERROR_FILE_NOT_FOUND, "wrong error %u\n", GetLastError());
267 
268  SetLastError(0xdeadbeef);
269  hOpened = OpenMutexA(READ_CONTROL, FALSE, "winetestmutex");
270  ok(!hOpened, "OpenMutex succeeded\n");
271  ok(GetLastError() == ERROR_FILE_NOT_FOUND, "wrong error %u\n", GetLastError());
272 
273  SetLastError(0xdeadbeef);
274  hOpened = OpenMutexA(READ_CONTROL, FALSE, NULL);
275  ok(!hOpened, "OpenMutex succeeded\n");
276  ok(GetLastError() == ERROR_INVALID_PARAMETER, "wrong error %u\n", GetLastError());
277 
278  SetLastError(0xdeadbeef);
279  hOpened = OpenMutexW(READ_CONTROL, FALSE, NULL);
280  ok(!hOpened, "OpenMutex succeeded\n");
281  ok(GetLastError() == ERROR_INVALID_PARAMETER, "wrong error %u\n", GetLastError());
282 
283  SetLastError(0xdeadbeef);
284  hOpened = CreateMutexA(NULL, FALSE, "WineTestMutex");
285  ok(hOpened != NULL, "CreateMutex failed with error %d\n", GetLastError());
286  ok(GetLastError() == ERROR_ALREADY_EXISTS, "wrong error %u\n", GetLastError());
287  CloseHandle(hOpened);
288 
289  SetLastError(0xdeadbeef);
290  hOpened = CreateMutexA(NULL, FALSE, "WINETESTMUTEX");
291  ok(hOpened != NULL, "CreateMutex failed with error %d\n", GetLastError());
292  ok(GetLastError() == 0, "wrong error %u\n", GetLastError());
293  CloseHandle(hOpened);
294 
295  CloseHandle(hCreated);
296 }
297 
298 static void test_slist(void)
299 {
300  struct item
301  {
303  int value;
304  } item1, item2, item3, *item;
305  SLIST_HEADER slist_header;
307  USHORT size;
308  int i;
309 
310  item1.value = 1;
311  item2.value = 2;
312  item3.value = 3;
313 
314  memset(&slist_header, 0xff, sizeof(slist_header));
315  InitializeSListHead(&slist_header);
316  size = QueryDepthSList(&slist_header);
317  ok(size == 0, "Expected size == 0, got %u\n", size);
318 
319  /* test PushEntry, PopEntry and Flush */
320  entry = InterlockedPushEntrySList(&slist_header, &item1.entry);
321  ok(entry == NULL, "Expected entry == NULL, got %p\n", entry);
322  size = QueryDepthSList(&slist_header);
323  ok(size == 1, "Expected size == 1, got %u\n", size);
324 
325  entry = InterlockedPushEntrySList(&slist_header, &item2.entry);
326  ok(entry != NULL, "Expected entry != NULL, got %p\n", entry);
327  item = CONTAINING_RECORD(entry, struct item, entry);
328  ok(item->value == 1, "Expected item->value == 1, got %u\n", item->value);
329  size = QueryDepthSList(&slist_header);
330  ok(size == 2, "Expected size == 2, got %u\n", size);
331 
332  entry = InterlockedPushEntrySList(&slist_header, &item3.entry);
333  ok(entry != NULL, "Expected entry != NULL, got %p\n", entry);
334  item = CONTAINING_RECORD(entry, struct item, entry);
335  ok(item->value == 2, "Expected item->value == 2, got %u\n", item->value);
336  size = QueryDepthSList(&slist_header);
337  ok(size == 3, "Expected size == 3, got %u\n", size);
338 
339  entry = InterlockedPopEntrySList(&slist_header);
340  ok(entry != NULL, "Expected entry != NULL, got %p\n", entry);
341  item = CONTAINING_RECORD(entry, struct item, entry);
342  ok(item->value == 3, "Expected item->value == 3, got %u\n", item->value);
343  size = QueryDepthSList(&slist_header);
344  ok(size == 2, "Expected size == 2, got %u\n", size);
345 
346  entry = InterlockedFlushSList(&slist_header);
347  ok(entry != NULL, "Expected entry != NULL, got %p\n", entry);
348  item = CONTAINING_RECORD(entry, struct item, entry);
349  ok(item->value == 2, "Expected item->value == 2, got %u\n", item->value);
350  item = CONTAINING_RECORD(item->entry.Next, struct item, entry);
351  ok(item->value == 1, "Expected item->value == 1, got %u\n", item->value);
352  size = QueryDepthSList(&slist_header);
353  ok(size == 0, "Expected size == 0, got %u\n", size);
354  entry = InterlockedPopEntrySList(&slist_header);
355  ok(entry == NULL, "Expected entry == NULL, got %p\n", entry);
356 
357  /* test RtlInterlockedPushListSList */
358  entry = InterlockedPushEntrySList(&slist_header, &item3.entry);
359  ok(entry == NULL, "Expected entry == NULL, got %p\n", entry);
360  entry = call_func4(pRtlInterlockedPushListSList, &slist_header, &item2.entry, &item1.entry, 42);
361  ok(entry != NULL, "Expected entry != NULL, got %p\n", entry);
362  item = CONTAINING_RECORD(entry, struct item, entry);
363  ok(item->value == 3, "Expected item->value == 3, got %u\n", item->value);
364  size = QueryDepthSList(&slist_header);
365  ok(size == 43, "Expected size == 43, got %u\n", size);
366 
367  entry = InterlockedPopEntrySList(&slist_header);
368  ok(entry != NULL, "Expected entry != NULL, got %p\n", entry);
369  item = CONTAINING_RECORD(entry, struct item, entry);
370  ok(item->value == 2, "Expected item->value == 2, got %u\n", item->value);
371  size = QueryDepthSList(&slist_header);
372  ok(size == 42, "Expected size == 42, got %u\n", size);
373 
374  entry = InterlockedPopEntrySList(&slist_header);
375  ok(entry != NULL, "Expected entry != NULL, got %p\n", entry);
376  item = CONTAINING_RECORD(entry, struct item, entry);
377  ok(item->value == 1, "Expected item->value == 1, got %u\n", item->value);
378  size = QueryDepthSList(&slist_header);
379  ok(size == 41, "Expected size == 41, got %u\n", size);
380 
381  entry = InterlockedPopEntrySList(&slist_header);
382  ok(entry != NULL, "Expected entry != NULL, got %p\n", entry);
383  item = CONTAINING_RECORD(entry, struct item, entry);
384  ok(item->value == 3, "Expected item->value == 3, got %u\n", item->value);
385  size = QueryDepthSList(&slist_header);
386  ok(size == 40, "Expected size == 40, got %u\n", size);
387 
388  entry = InterlockedPopEntrySList(&slist_header);
389  ok(entry == NULL, "Expected entry == NULL, got %p\n", entry);
390  size = QueryDepthSList(&slist_header);
391  ok(size == 40, "Expected size == 40, got %u\n", size);
392 
393  entry = InterlockedFlushSList(&slist_header);
394  ok(entry == NULL, "Expected entry == NULL, got %p\n", entry);
395  size = QueryDepthSList(&slist_header);
396  ok(size == 40 || broken(size == 0) /* >= Win 8 */, "Expected size == 40, got %u\n", size);
397 
398  entry = InterlockedPushEntrySList(&slist_header, &item1.entry);
399  ok(entry == NULL, "Expected entry == NULL, got %p\n", entry);
400  entry = InterlockedFlushSList(&slist_header);
401  ok(entry != NULL, "Expected entry != NULL, got %p\n", entry);
402  item = CONTAINING_RECORD(entry, struct item, entry);
403  ok(item->value == 1, "Expected item->value == 1, got %u\n", item->value);
404  size = QueryDepthSList(&slist_header);
405  ok(size == 0, "Expected size == 0, got %u\n", size);
406 
407  /* test RtlInterlockedPushListSListEx */
408  if (pRtlInterlockedPushListSListEx)
409  {
410  entry = InterlockedPushEntrySList(&slist_header, &item3.entry);
411  ok(entry == NULL, "Expected entry == NULL, got %p\n", entry);
412  entry = pRtlInterlockedPushListSListEx(&slist_header, &item2.entry, &item1.entry, 42);
413  ok(entry != NULL, "Expected entry != NULL, got %p\n", entry);
414  item = CONTAINING_RECORD(entry, struct item, entry);
415  ok(item->value == 3, "Expected item->value == 3, got %u\n", item->value);
416  size = QueryDepthSList(&slist_header);
417  ok(size == 43, "Expected size == 43, got %u\n", size);
418 
419  entry = InterlockedFlushSList(&slist_header);
420  ok(entry != NULL, "Expected entry != NULL, got %p\n", entry);
421  item = CONTAINING_RECORD(entry, struct item, entry);
422  ok(item->value == 2, "Expected item->value == 2, got %u\n", item->value);
423  item = CONTAINING_RECORD(item->entry.Next, struct item, entry);
424  ok(item->value == 1, "Expected item->value == 1, got %u\n", item->value);
425  item = CONTAINING_RECORD(item->entry.Next, struct item, entry);
426  ok(item->value == 3, "Expected item->value == 3, got %u\n", item->value);
427  size = QueryDepthSList(&slist_header);
428  ok(size == 0, "Expected size == 0, got %u\n", size);
429  }
430  else
431  win_skip("RtlInterlockedPushListSListEx not available, skipping tests\n");
432 
433  /* test with a lot of items */
434  for (i = 0; i < 65536; i++)
435  {
436  item = HeapAlloc(GetProcessHeap(), 0, sizeof(*item));
437  item->value = i + 1;
438  entry = InterlockedPushEntrySList(&slist_header, &item->entry);
439  if (i)
440  {
441  ok(entry != NULL, "Expected entry != NULL, got %p\n", entry);
442  item = CONTAINING_RECORD(entry, struct item, entry);
443  ok(item->value == i, "Expected item->value == %u, got %u\n", i, item->value);
444  }
445  else
446  {
447  ok(entry == NULL, "Expected entry == NULL, got %p\n", entry);
448  }
449  size = QueryDepthSList(&slist_header);
450  ok(size == ((i + 1) & 0xffff), "Expected size == %u, got %u\n", (i + 1) & 0xffff, size);
451  }
452 
453  entry = InterlockedFlushSList(&slist_header);
454  for (i = 65536; i > 0; i--)
455  {
456  ok(entry != NULL, "Expected entry != NULL, got %p\n", entry);
457  item = CONTAINING_RECORD(entry, struct item, entry);
458  ok(item->value == i, "Expected item->value == %u, got %u\n", i, item->value);
459  entry = item->entry.Next;
461  }
462  ok(entry == NULL, "Expected entry == NULL, got %p\n", entry);
463  size = QueryDepthSList(&slist_header);
464  ok(size == 0, "Expected size == 0, got %u\n", size);
465  entry = InterlockedPopEntrySList(&slist_header);
466  ok(entry == NULL, "Expected entry == NULL, got %p\n", entry);
467 }
468 
469 static void test_event(void)
470 {
471  HANDLE handle, handle2;
474  ACL acl;
475  DWORD ret;
476  BOOL val;
477 
478  /* no sd */
479  handle = CreateEventA(NULL, FALSE, FALSE, __FILE__ ": Test Event");
480  ok(handle != NULL, "CreateEventW with blank sd failed with error %d\n", GetLastError());
482 
483  sa.nLength = sizeof(sa);
484  sa.lpSecurityDescriptor = &sd;
485  sa.bInheritHandle = FALSE;
486 
488 
489  /* blank sd */
490  handle = CreateEventA(&sa, FALSE, FALSE, __FILE__ ": Test Event");
491  ok(handle != NULL, "CreateEventW with blank sd failed with error %d\n", GetLastError());
493 
494  /* sd with NULL dacl */
496  handle = CreateEventA(&sa, FALSE, FALSE, __FILE__ ": Test Event");
497  ok(handle != NULL, "CreateEventW with blank sd failed with error %d\n", GetLastError());
499 
500  /* sd with empty dacl */
501  InitializeAcl(&acl, sizeof(acl), ACL_REVISION);
503  handle = CreateEventA(&sa, FALSE, FALSE, __FILE__ ": Test Event");
504  ok(handle != NULL, "CreateEventW with blank sd failed with error %d\n", GetLastError());
506 
507  /* test case sensitivity */
508 
509  SetLastError(0xdeadbeef);
510  handle = CreateEventA(NULL, FALSE, FALSE, __FILE__ ": Test Event");
511  ok( handle != NULL, "CreateEvent failed with error %u\n", GetLastError());
512  ok( GetLastError() == 0, "wrong error %u\n", GetLastError());
513 
514  SetLastError(0xdeadbeef);
515  handle2 = CreateEventA(NULL, FALSE, FALSE, __FILE__ ": Test Event");
516  ok( handle2 != NULL, "CreateEvent failed with error %d\n", GetLastError());
517  ok( GetLastError() == ERROR_ALREADY_EXISTS, "wrong error %u\n", GetLastError());
518  CloseHandle( handle2 );
519 
520  SetLastError(0xdeadbeef);
521  handle2 = CreateEventA(NULL, FALSE, FALSE, __FILE__ ": TEST EVENT");
522  ok( handle2 != NULL, "CreateEvent failed with error %d\n", GetLastError());
523  ok( GetLastError() == 0, "wrong error %u\n", GetLastError());
524  CloseHandle( handle2 );
525 
526  SetLastError(0xdeadbeef);
527  handle2 = OpenEventA( EVENT_ALL_ACCESS, FALSE, __FILE__ ": Test Event");
528  ok( handle2 != NULL, "OpenEvent failed with error %d\n", GetLastError());
529  CloseHandle( handle2 );
530 
531  SetLastError(0xdeadbeef);
532  handle2 = OpenEventA( EVENT_ALL_ACCESS, FALSE, __FILE__ ": TEST EVENT");
533  ok( !handle2, "OpenEvent succeeded\n");
534  ok( GetLastError() == ERROR_FILE_NOT_FOUND, "wrong error %u\n", GetLastError());
535 
536  SetLastError(0xdeadbeef);
537  handle2 = OpenEventA( EVENT_ALL_ACCESS, FALSE, NULL );
538  ok( !handle2, "OpenEvent succeeded\n");
539  ok( GetLastError() == ERROR_INVALID_PARAMETER, "wrong error %u\n", GetLastError());
540 
541  SetLastError(0xdeadbeef);
542  handle2 = OpenEventW( EVENT_ALL_ACCESS, FALSE, NULL );
543  ok( !handle2, "OpenEvent succeeded\n");
544  ok( GetLastError() == ERROR_INVALID_PARAMETER, "wrong error %u\n", GetLastError());
545 
546  CloseHandle( handle );
547 
548  /* resource notifications are events too */
549 
550  if (!pCreateMemoryResourceNotification || !pQueryMemoryResourceNotification)
551  {
552  trace( "memory resource notifications not supported\n" );
553  return;
554  }
555  handle = pCreateMemoryResourceNotification( HighMemoryResourceNotification + 1 );
556  ok( !handle, "CreateMemoryResourceNotification succeeded\n" );
557  ok( GetLastError() == ERROR_INVALID_PARAMETER, "wrong error %u\n", GetLastError() );
558  ret = pQueryMemoryResourceNotification( handle, &val );
559  ok( !ret, "QueryMemoryResourceNotification succeeded\n" );
560  ok( GetLastError() == ERROR_INVALID_PARAMETER, "wrong error %u\n", GetLastError() );
561 
562  handle = pCreateMemoryResourceNotification( LowMemoryResourceNotification );
563  ok( handle != 0, "CreateMemoryResourceNotification failed err %u\n", GetLastError() );
564  ret = WaitForSingleObject( handle, 10 );
565  ok( ret == WAIT_OBJECT_0 || ret == WAIT_TIMEOUT, "WaitForSingleObject wrong ret %u\n", ret );
566 
567  val = ~0;
568  ret = pQueryMemoryResourceNotification( handle, &val );
569  ok( ret, "QueryMemoryResourceNotification failed err %u\n", GetLastError() );
570  ok( val == FALSE || val == TRUE, "wrong value %u\n", val );
571  ret = CloseHandle( handle );
572  ok( ret, "CloseHandle failed err %u\n", GetLastError() );
573 
574  handle = CreateEventA(NULL, FALSE, FALSE, __FILE__ ": Test Event");
575  val = ~0;
576  ret = pQueryMemoryResourceNotification( handle, &val );
577  ok( ret, "QueryMemoryResourceNotification failed err %u\n", GetLastError() );
578  ok( val == FALSE || val == TRUE, "wrong value %u\n", val );
579  CloseHandle( handle );
580 }
581 
582 static void test_semaphore(void)
583 {
584  HANDLE handle, handle2;
585 
586  /* test case sensitivity */
587 
588  SetLastError(0xdeadbeef);
589  handle = CreateSemaphoreA(NULL, 0, 1, __FILE__ ": Test Semaphore");
590  ok(handle != NULL, "CreateSemaphore failed with error %u\n", GetLastError());
591  ok(GetLastError() == 0, "wrong error %u\n", GetLastError());
592 
593  SetLastError(0xdeadbeef);
594  handle2 = CreateSemaphoreA(NULL, 0, 1, __FILE__ ": Test Semaphore");
595  ok( handle2 != NULL, "CreateSemaphore failed with error %d\n", GetLastError());
596  ok( GetLastError() == ERROR_ALREADY_EXISTS, "wrong error %u\n", GetLastError());
597  CloseHandle( handle2 );
598 
599  SetLastError(0xdeadbeef);
600  handle2 = CreateSemaphoreA(NULL, 0, 1, __FILE__ ": TEST SEMAPHORE");
601  ok( handle2 != NULL, "CreateSemaphore failed with error %d\n", GetLastError());
602  ok( GetLastError() == 0, "wrong error %u\n", GetLastError());
603  CloseHandle( handle2 );
604 
605  SetLastError(0xdeadbeef);
606  handle2 = OpenSemaphoreA( SEMAPHORE_ALL_ACCESS, FALSE, __FILE__ ": Test Semaphore");
607  ok( handle2 != NULL, "OpenSemaphore failed with error %d\n", GetLastError());
608  CloseHandle( handle2 );
609 
610  SetLastError(0xdeadbeef);
611  handle2 = OpenSemaphoreA( SEMAPHORE_ALL_ACCESS, FALSE, __FILE__ ": TEST SEMAPHORE");
612  ok( !handle2, "OpenSemaphore succeeded\n");
613  ok( GetLastError() == ERROR_FILE_NOT_FOUND, "wrong error %u\n", GetLastError());
614 
615  SetLastError(0xdeadbeef);
617  ok( !handle2, "OpenSemaphore succeeded\n");
618  ok( GetLastError() == ERROR_INVALID_PARAMETER, "wrong error %u\n", GetLastError());
619 
620  SetLastError(0xdeadbeef);
622  ok( !handle2, "OpenSemaphore succeeded\n");
623  ok( GetLastError() == ERROR_INVALID_PARAMETER, "wrong error %u\n", GetLastError());
624 
625  CloseHandle( handle );
626 }
627 
628 static void test_waitable_timer(void)
629 {
630  HANDLE handle, handle2;
631 
632  /* test case sensitivity */
633 
634  SetLastError(0xdeadbeef);
635  handle = CreateWaitableTimerA(NULL, FALSE, __FILE__ ": Test WaitableTimer");
636  ok(handle != NULL, "CreateWaitableTimer failed with error %u\n", GetLastError());
637  ok(GetLastError() == 0, "wrong error %u\n", GetLastError());
638 
639  SetLastError(0xdeadbeef);
640  handle2 = CreateWaitableTimerA(NULL, FALSE, __FILE__ ": Test WaitableTimer");
641  ok( handle2 != NULL, "CreateWaitableTimer failed with error %d\n", GetLastError());
642  ok( GetLastError() == ERROR_ALREADY_EXISTS, "wrong error %u\n", GetLastError());
643  CloseHandle( handle2 );
644 
645  SetLastError(0xdeadbeef);
646  handle2 = CreateWaitableTimerA(NULL, FALSE, __FILE__ ": TEST WAITABLETIMER");
647  ok( handle2 != NULL, "CreateWaitableTimer failed with error %d\n", GetLastError());
648  ok( GetLastError() == 0, "wrong error %u\n", GetLastError());
649  CloseHandle( handle2 );
650 
651  SetLastError(0xdeadbeef);
652  handle2 = OpenWaitableTimerA( TIMER_ALL_ACCESS, FALSE, __FILE__ ": Test WaitableTimer");
653  ok( handle2 != NULL, "OpenWaitableTimer failed with error %d\n", GetLastError());
654  CloseHandle( handle2 );
655 
656  SetLastError(0xdeadbeef);
657  handle2 = OpenWaitableTimerA( TIMER_ALL_ACCESS, FALSE, __FILE__ ": TEST WAITABLETIMER");
658  ok( !handle2, "OpenWaitableTimer succeeded\n");
659  ok( GetLastError() == ERROR_FILE_NOT_FOUND, "wrong error %u\n", GetLastError());
660 
661  SetLastError(0xdeadbeef);
663  ok( !handle2, "OpenWaitableTimer failed with error %d\n", GetLastError());
664  ok( GetLastError() == ERROR_INVALID_PARAMETER, "wrong error %u\n", GetLastError());
665 
666  SetLastError(0xdeadbeef);
668  ok( !handle2, "OpenWaitableTimer failed with error %d\n", GetLastError());
669  ok( GetLastError() == ERROR_INVALID_PARAMETER, "wrong error %u\n", GetLastError());
670 
671  CloseHandle( handle );
672 }
673 
674 static HANDLE sem = 0;
675 
676 static void CALLBACK iocp_callback(DWORD dwErrorCode, DWORD dwNumberOfBytesTransferred, LPOVERLAPPED lpOverlapped)
677 {
679 }
680 
682 
683 static void test_iocp_callback(void)
684 {
685  char temp_path[MAX_PATH];
686  char filename[MAX_PATH];
687  DWORD ret;
688  BOOL retb;
689  static const char prefix[] = "pfx";
690  HANDLE hFile;
691  HMODULE hmod = GetModuleHandleA("kernel32.dll");
693  const char *buffer = "12345678123456781234567812345678";
695 
696  p_BindIoCompletionCallback = (void*)GetProcAddress(hmod, "BindIoCompletionCallback");
697  if(!p_BindIoCompletionCallback) {
698  win_skip("BindIoCompletionCallback not found in this DLL\n");
699  return;
700  }
701 
702  sem = CreateSemaphoreW(NULL, 0, 1, NULL);
703  ok(sem != INVALID_HANDLE_VALUE, "Creating a semaphore failed\n");
704 
706  ok(ret != 0, "GetTempPathA error %d\n", GetLastError());
707  ok(ret < MAX_PATH, "temp path should fit into MAX_PATH\n");
708 
709  ret = GetTempFileNameA(temp_path, prefix, 0, filename);
710  ok(ret != 0, "GetTempFileNameA error %d\n", GetLastError());
711 
714  ok(hFile != INVALID_HANDLE_VALUE, "CreateFileA: error %d\n", GetLastError());
715 
716  retb = p_BindIoCompletionCallback(hFile, iocp_callback, 0);
717  ok(retb == FALSE, "BindIoCompletionCallback succeeded on a file that wasn't created with FILE_FLAG_OVERLAPPED\n");
718  ok(GetLastError() == ERROR_INVALID_PARAMETER, "Last error is %d\n", GetLastError());
719 
720  ret = CloseHandle(hFile);
721  ok( ret, "CloseHandle: error %d\n", GetLastError());
723  ok( ret, "DeleteFileA: error %d\n", GetLastError());
724 
727  ok(hFile != INVALID_HANDLE_VALUE, "CreateFileA: error %d\n", GetLastError());
728 
729  retb = p_BindIoCompletionCallback(hFile, iocp_callback, 0);
730  ok(retb == TRUE, "BindIoCompletionCallback failed\n");
731 
732  memset(&overlapped, 0, sizeof(overlapped));
733  retb = WriteFile(hFile, buffer, 4, &bytesWritten, &overlapped);
734  ok(retb == TRUE || GetLastError() == ERROR_IO_PENDING, "WriteFile failed, lastError = %d\n", GetLastError());
735 
736  ret = WaitForSingleObject(sem, 5000);
737  ok(ret == WAIT_OBJECT_0, "Wait for the IO completion callback failed\n");
738  CloseHandle(sem);
739 
740  retb = p_BindIoCompletionCallback(hFile, iocp_callback, 0);
741  ok(retb == FALSE, "BindIoCompletionCallback succeeded when setting the same callback on the file again\n");
742  ok(GetLastError() == ERROR_INVALID_PARAMETER, "Last error is %d\n", GetLastError());
743  retb = p_BindIoCompletionCallback(hFile, NULL, 0);
744  ok(retb == FALSE, "BindIoCompletionCallback succeeded when setting the callback to NULL\n");
745  ok(GetLastError() == ERROR_INVALID_PARAMETER, "Last error is %d\n", GetLastError());
746 
747  ret = CloseHandle(hFile);
748  ok( ret, "CloseHandle: error %d\n", GetLastError());
750  ok( ret, "DeleteFileA: error %d\n", GetLastError());
751 
752  /* win2k3 requires the Flags parameter to be zero */
753  SetLastError(0xdeadbeef);
756  ok(hFile != INVALID_HANDLE_VALUE, "CreateFileA: error %d\n", GetLastError());
757  retb = p_BindIoCompletionCallback(hFile, iocp_callback, 12345);
758  if (!retb)
760  "Expected ERROR_INVALID_PARAMETER, got %d\n", GetLastError());
761  else
762  ok(retb == TRUE, "BindIoCompletionCallback failed with Flags != 0\n");
763  ret = CloseHandle(hFile);
764  ok( ret, "CloseHandle: error %d\n", GetLastError());
766  ok( ret, "DeleteFileA: error %d\n", GetLastError());
767 
768  retb = p_BindIoCompletionCallback(NULL, iocp_callback, 0);
769  ok(retb == FALSE, "BindIoCompletionCallback succeeded on a NULL file\n");
771  GetLastError() == ERROR_INVALID_PARAMETER, /* vista */
772  "Last error is %d\n", GetLastError());
773 }
774 
775 static void CALLBACK timer_queue_cb1(PVOID p, BOOLEAN timedOut)
776 {
777  int *pn = p;
779  ok(timedOut, "Timer callbacks should always time out\n");
780  ++*pn;
781 }
782 
784 {
788 };
789 
790 static void CALLBACK timer_queue_cb2(PVOID p, BOOLEAN timedOut)
791 {
792  struct timer_queue_data1 *d = p;
793  ok(timedOut, "Timer callbacks should always time out\n");
794  if (d->t && ++d->num_calls == d->max_calls)
795  {
796  BOOL ret;
797  SetLastError(0xdeadbeef);
798  /* Note, XP SP2 does *not* do any deadlock checking, so passing
799  INVALID_HANDLE_VALUE here will just hang. */
800  ret = DeleteTimerQueueTimer(d->q, d->t, NULL);
801  ok(!ret, "DeleteTimerQueueTimer\n");
802  ok(GetLastError() == ERROR_IO_PENDING, "DeleteTimerQueueTimer\n");
803  }
804 }
805 
806 static void CALLBACK timer_queue_cb3(PVOID p, BOOLEAN timedOut)
807 {
808  struct timer_queue_data1 *d = p;
809  ok(timedOut, "Timer callbacks should always time out\n");
810  if (d->t && ++d->num_calls == d->max_calls)
811  {
812  /* Basically kill the timer since it won't have time to run
813  again. */
814  BOOL ret = ChangeTimerQueueTimer(d->q, d->t, 10000, 0);
815  ok(ret, "ChangeTimerQueueTimer\n");
816  }
817 }
818 
819 static void CALLBACK timer_queue_cb4(PVOID p, BOOLEAN timedOut)
820 {
821  struct timer_queue_data1 *d = p;
822  ok(timedOut, "Timer callbacks should always time out\n");
823  if (d->t)
824  {
825  /* This tests whether a timer gets flagged for deletion before
826  or after the callback runs. If we start this timer with a
827  period of zero (run once), then ChangeTimerQueueTimer will
828  fail if the timer is already flagged. Hence we really run
829  only once. Otherwise we will run multiple times. */
830  BOOL ret = ChangeTimerQueueTimer(d->q, d->t, 50, 50);
831  ok(ret, "ChangeTimerQueueTimer\n");
832  ++d->num_calls;
833  }
834 }
835 
836 static void CALLBACK timer_queue_cb5(PVOID p, BOOLEAN timedOut)
837 {
838  DWORD_PTR delay = (DWORD_PTR) p;
839  ok(timedOut, "Timer callbacks should always time out\n");
840  if (delay)
841  Sleep(delay);
842 }
843 
844 static void CALLBACK timer_queue_cb6(PVOID p, BOOLEAN timedOut)
845 {
846  struct timer_queue_data1 *d = p;
847  ok(timedOut, "Timer callbacks should always time out\n");
848  /* This tests an original implementation bug where a deleted timer may get
849  to run, but it is tricky to set up. */
850  if (d->q && d->num_calls++ == 0)
851  {
852  /* First run: delete ourselves, then insert and remove a timer
853  that goes in front of us in the sorted timeout list. Once
854  removed, we will still timeout at the faster timer's due time,
855  but this should be a no-op if we are bug-free. There should
856  not be a second run. We can test the value of num_calls later. */
857  BOOL ret;
858  HANDLE t;
859 
860  /* The delete will pend while we are in this callback. */
861  SetLastError(0xdeadbeef);
862  ret = DeleteTimerQueueTimer(d->q, d->t, NULL);
863  ok(!ret, "DeleteTimerQueueTimer\n");
864  ok(GetLastError() == ERROR_IO_PENDING, "DeleteTimerQueueTimer\n");
865 
866  ret = CreateTimerQueueTimer(&t, d->q, timer_queue_cb1, NULL, 100, 0, 0);
867  ok(ret, "CreateTimerQueueTimer\n");
868  ok(t != NULL, "CreateTimerQueueTimer\n");
869 
871  ok(ret, "DeleteTimerQueueTimer\n");
872 
873  /* Now we stay alive by hanging around in the callback. */
874  Sleep(500);
875  }
876 }
877 
878 static void test_timer_queue(void)
879 {
880  HANDLE q, t0, t1, t2, t3, t4, t5;
881  int n0, n1, n2, n3, n4, n5;
882  struct timer_queue_data1 d1, d2, d3, d4;
883  HANDLE e, et1, et2;
884  BOOL ret, ret0;
885 
886  /* Test asynchronous deletion of the queue. */
887  q = CreateTimerQueue();
888  ok(q != NULL, "CreateTimerQueue\n");
889 
890  SetLastError(0xdeadbeef);
892  ok(ret /* vista */ || GetLastError() == ERROR_IO_PENDING,
893  "DeleteTimerQueueEx, GetLastError: expected ERROR_IO_PENDING, got %d\n",
894  GetLastError());
895 
896  /* Test synchronous deletion of the queue and running timers. */
897  q = CreateTimerQueue();
898  ok(q != NULL, "CreateTimerQueue\n");
899 
900  /* Not called. */
901  t0 = NULL;
902  n0 = 0;
903  ret = CreateTimerQueueTimer(&t0, q, timer_queue_cb1, &n0, 0, 300, 0);
904  ok(ret, "CreateTimerQueueTimer\n");
905  ok(t0 != NULL, "CreateTimerQueueTimer\n");
906  ret0 = DeleteTimerQueueTimer(q, t0, NULL);
907  ok((!ret0 && GetLastError() == ERROR_IO_PENDING) ||
908  broken(ret0), /* Win 2000 & XP & 2003 */
909  "DeleteTimerQueueTimer ret=%d le=%u\n", ret0, GetLastError());
910 
911  /* Called once. */
912  t1 = NULL;
913  n1 = 0;
914  ret = CreateTimerQueueTimer(&t1, q, timer_queue_cb1, &n1, 0, 0, 0);
915  ok(ret, "CreateTimerQueueTimer\n");
916  ok(t1 != NULL, "CreateTimerQueueTimer\n");
917 
918  /* A slow one. */
919  t2 = NULL;
920  n2 = 0;
921  ret = CreateTimerQueueTimer(&t2, q, timer_queue_cb1, &n2, 0, 100, 0);
922  ok(ret, "CreateTimerQueueTimer\n");
923  ok(t2 != NULL, "CreateTimerQueueTimer\n");
924 
925  /* A fast one. */
926  t3 = NULL;
927  n3 = 0;
928  ret = CreateTimerQueueTimer(&t3, q, timer_queue_cb1, &n3, 0, 10, 0);
929  ok(ret, "CreateTimerQueueTimer\n");
930  ok(t3 != NULL, "CreateTimerQueueTimer\n");
931 
932  /* Start really late (it won't start). */
933  t4 = NULL;
934  n4 = 0;
935  ret = CreateTimerQueueTimer(&t4, q, timer_queue_cb1, &n4, 10000, 10, 0);
936  ok(ret, "CreateTimerQueueTimer\n");
937  ok(t4 != NULL, "CreateTimerQueueTimer\n");
938 
939  /* Start soon, but delay so long it won't run again. */
940  t5 = NULL;
941  n5 = 0;
942  ret = CreateTimerQueueTimer(&t5, q, timer_queue_cb1, &n5, 0, 10000, 0);
943  ok(ret, "CreateTimerQueueTimer\n");
944  ok(t5 != NULL, "CreateTimerQueueTimer\n");
945 
946  /* Give them a chance to do some work. */
947  Sleep(500);
948 
949  /* Test deleting a once-only timer. */
951  ok(ret, "DeleteTimerQueueTimer\n");
952 
953  /* A periodic timer. */
955  ok(ret, "DeleteTimerQueueTimer\n");
956 
958  ok(ret, "DeleteTimerQueueEx\n");
959  todo_wine
960  ok(n0 == 1 || broken(ret0 && n0 == 0), "Timer callback 0 expected 1 got %d\n", n0);
961  ok(n1 == 1, "Timer callback 1 expected 1 got %d\n", n1);
962  ok(n2 < n3, "Timer callback 2 & 3 expected %d < %d\n", n2, n3);
963  ok(n4 == 0, "Timer callback 4 expected 0 got %d\n", n4);
964  ok(n5 == 1, "Timer callback 5 expected 1 got %d\n", n5);
965 
966  /* Test synchronous deletion of the timer/queue with event trigger. */
968  et1 = CreateEventW(NULL, TRUE, FALSE, NULL);
969  et2 = CreateEventW(NULL, TRUE, FALSE, NULL);
970  if (!e || !et1 || !et2)
971  {
972  skip("Failed to create timer queue descruction event\n");
973  return;
974  }
975 
976  q = CreateTimerQueue();
977  ok(q != NULL, "CreateTimerQueue\n");
978 
979  /* Run once and finish quickly (should be done when we delete it). */
980  t1 = NULL;
981  ret = CreateTimerQueueTimer(&t1, q, timer_queue_cb5, NULL, 0, 0, 0);
982  ok(ret, "CreateTimerQueueTimer\n");
983  ok(t1 != NULL, "CreateTimerQueueTimer\n");
984 
985  /* Run once and finish slowly (shouldn't be done when we delete it). */
986  t2 = NULL;
987  ret = CreateTimerQueueTimer(&t2, q, timer_queue_cb5, (PVOID) 1000, 0, 0, 0);
988  ok(ret, "CreateTimerQueueTimer\n");
989  ok(t2 != NULL, "CreateTimerQueueTimer\n");
990 
991  /* Run once and finish quickly (should be done when we delete it). */
992  t3 = NULL;
993  ret = CreateTimerQueueTimer(&t3, q, timer_queue_cb5, NULL, 0, 0, 0);
994  ok(ret, "CreateTimerQueueTimer\n");
995  ok(t3 != NULL, "CreateTimerQueueTimer\n");
996 
997  /* Run once and finish slowly (shouldn't be done when we delete it). */
998  t4 = NULL;
999  ret = CreateTimerQueueTimer(&t4, q, timer_queue_cb5, (PVOID) 1000, 0, 0, 0);
1000  ok(ret, "CreateTimerQueueTimer\n");
1001  ok(t4 != NULL, "CreateTimerQueueTimer\n");
1002 
1003  /* Give them a chance to start. */
1004  Sleep(400);
1005 
1006  /* DeleteTimerQueueTimer always returns PENDING with a NULL event,
1007  even if the timer is finished. */
1008  SetLastError(0xdeadbeef);
1009  ret = DeleteTimerQueueTimer(q, t1, NULL);
1010  ok(ret /* vista */ || GetLastError() == ERROR_IO_PENDING,
1011  "DeleteTimerQueueTimer, GetLastError: expected ERROR_IO_PENDING, got %d\n",
1012  GetLastError());
1013 
1014  SetLastError(0xdeadbeef);
1015  ret = DeleteTimerQueueTimer(q, t2, NULL);
1016  ok(!ret, "DeleteTimerQueueTimer call was expected to fail\n");
1018  "DeleteTimerQueueTimer, GetLastError: expected ERROR_IO_PENDING, got %d\n",
1019  GetLastError());
1020 
1021  SetLastError(0xdeadbeef);
1022  ret = DeleteTimerQueueTimer(q, t3, et1);
1023  ok(ret, "DeleteTimerQueueTimer call was expected to fail\n");
1024  ok(GetLastError() == 0xdeadbeef,
1025  "DeleteTimerQueueTimer, GetLastError: expected 0xdeadbeef, got %d\n",
1026  GetLastError());
1027  ok(WaitForSingleObject(et1, 250) == WAIT_OBJECT_0,
1028  "Timer destruction event not triggered\n");
1029 
1030  SetLastError(0xdeadbeef);
1031  ret = DeleteTimerQueueTimer(q, t4, et2);
1032  ok(!ret, "DeleteTimerQueueTimer call was expected to fail\n");
1034  "DeleteTimerQueueTimer, GetLastError: expected ERROR_IO_PENDING, got %d\n",
1035  GetLastError());
1036  ok(WaitForSingleObject(et2, 1000) == WAIT_OBJECT_0,
1037  "Timer destruction event not triggered\n");
1038 
1039  SetLastError(0xdeadbeef);
1040  ret = DeleteTimerQueueEx(q, e);
1041  ok(ret /* vista */ || GetLastError() == ERROR_IO_PENDING,
1042  "DeleteTimerQueueEx, GetLastError: expected ERROR_IO_PENDING, got %d\n",
1043  GetLastError());
1045  "Queue destruction event not triggered\n");
1046  CloseHandle(e);
1047 
1048  /* Test deleting/changing a timer in execution. */
1049  q = CreateTimerQueue();
1050  ok(q != NULL, "CreateTimerQueue\n");
1051 
1052  /* Test changing a once-only timer before it fires (this is allowed,
1053  whereas after it fires you cannot). */
1054  n1 = 0;
1055  ret = CreateTimerQueueTimer(&t1, q, timer_queue_cb1, &n1, 10000, 0, 0);
1056  ok(ret, "CreateTimerQueueTimer\n");
1057  ok(t1 != NULL, "CreateTimerQueueTimer\n");
1058  ret = ChangeTimerQueueTimer(q, t1, 0, 0);
1059  ok(ret, "ChangeTimerQueueTimer\n");
1060 
1061  d2.t = t2 = NULL;
1062  d2.num_calls = 0;
1063  d2.max_calls = 3;
1064  d2.q = q;
1065  ret = CreateTimerQueueTimer(&t2, q, timer_queue_cb2, &d2, 10, 10, 0);
1066  d2.t = t2;
1067  ok(ret, "CreateTimerQueueTimer\n");
1068  ok(t2 != NULL, "CreateTimerQueueTimer\n");
1069 
1070  d3.t = t3 = NULL;
1071  d3.num_calls = 0;
1072  d3.max_calls = 4;
1073  d3.q = q;
1074  ret = CreateTimerQueueTimer(&t3, q, timer_queue_cb3, &d3, 10, 10, 0);
1075  d3.t = t3;
1076  ok(ret, "CreateTimerQueueTimer\n");
1077  ok(t3 != NULL, "CreateTimerQueueTimer\n");
1078 
1079  d4.t = t4 = NULL;
1080  d4.num_calls = 0;
1081  d4.q = q;
1082  ret = CreateTimerQueueTimer(&t4, q, timer_queue_cb4, &d4, 10, 0, 0);
1083  d4.t = t4;
1084  ok(ret, "CreateTimerQueueTimer\n");
1085  ok(t4 != NULL, "CreateTimerQueueTimer\n");
1086 
1087  Sleep(500);
1088 
1090  ok(ret, "DeleteTimerQueueEx\n");
1091  ok(n1 == 1, "ChangeTimerQueueTimer\n");
1092  ok(d2.num_calls == d2.max_calls, "DeleteTimerQueueTimer\n");
1093  ok(d3.num_calls == d3.max_calls, "ChangeTimerQueueTimer\n");
1094  ok(d4.num_calls == 1, "Timer flagged for deletion incorrectly\n");
1095 
1096  /* Test an obscure bug that was in the original implementation. */
1097  q = CreateTimerQueue();
1098  ok(q != NULL, "CreateTimerQueue\n");
1099 
1100  /* All the work is done in the callback. */
1101  d1.t = t1 = NULL;
1102  d1.num_calls = 0;
1103  d1.q = q;
1105  d1.t = t1;
1106  ok(ret, "CreateTimerQueueTimer\n");
1107  ok(t1 != NULL, "CreateTimerQueueTimer\n");
1108 
1109  Sleep(750);
1110 
1111  SetLastError(0xdeadbeef);
1113  ok(ret /* vista */ || GetLastError() == ERROR_IO_PENDING,
1114  "DeleteTimerQueueEx, GetLastError: expected ERROR_IO_PENDING, got %d\n",
1115  GetLastError());
1116  ok(d1.num_calls == 1, "DeleteTimerQueueTimer\n");
1117 
1118  /* Test functions on the default timer queue. */
1119  t1 = NULL;
1120  n1 = 0;
1121  ret = CreateTimerQueueTimer(&t1, NULL, timer_queue_cb1, &n1, 1000, 1000, 0);
1122  ok(ret, "CreateTimerQueueTimer, default queue\n");
1123  ok(t1 != NULL, "CreateTimerQueueTimer, default queue\n");
1124 
1125  ret = ChangeTimerQueueTimer(NULL, t1, 2000, 2000);
1126  ok(ret, "ChangeTimerQueueTimer, default queue\n");
1127 
1129  ok(ret, "DeleteTimerQueueTimer, default queue\n");
1130 
1131  /* Try mixing default and non-default queues. Apparently this works. */
1132  q = CreateTimerQueue();
1133  ok(q != NULL, "CreateTimerQueue\n");
1134 
1135  t1 = NULL;
1136  n1 = 0;
1137  ret = CreateTimerQueueTimer(&t1, q, timer_queue_cb1, &n1, 1000, 1000, 0);
1138  ok(ret, "CreateTimerQueueTimer\n");
1139  ok(t1 != NULL, "CreateTimerQueueTimer\n");
1140 
1141  t2 = NULL;
1142  n2 = 0;
1143  ret = CreateTimerQueueTimer(&t2, NULL, timer_queue_cb1, &n2, 1000, 1000, 0);
1144  ok(ret, "CreateTimerQueueTimer\n");
1145  ok(t2 != NULL, "CreateTimerQueueTimer\n");
1146 
1147  ret = ChangeTimerQueueTimer(NULL, t1, 2000, 2000);
1148  ok(ret, "ChangeTimerQueueTimer\n");
1149 
1150  ret = ChangeTimerQueueTimer(q, t2, 2000, 2000);
1151  ok(ret, "ChangeTimerQueueTimer\n");
1152 
1154  ok(ret, "DeleteTimerQueueTimer\n");
1155 
1157  ok(ret, "DeleteTimerQueueTimer\n");
1158 
1159  /* Try to delete the default queue? In any case: not allowed. */
1160  SetLastError(0xdeadbeef);
1162  ok(!ret, "DeleteTimerQueueEx call was expected to fail\n");
1164  "DeleteTimerQueueEx, GetLastError: expected ERROR_INVALID_HANDLE, got %d\n",
1165  GetLastError());
1166 
1167  SetLastError(0xdeadbeef);
1169  ok(ret /* vista */ || GetLastError() == ERROR_IO_PENDING,
1170  "DeleteTimerQueueEx, GetLastError: expected ERROR_IO_PENDING, got %d\n",
1171  GetLastError());
1172 }
1173 
1175 {
1176  DWORD tmp = HandleToULong(handle);
1177  tmp |= modify;
1178  return ULongToHandle(tmp);
1179 }
1180 
1181 static void test_WaitForSingleObject(void)
1182 {
1183  HANDLE signaled, nonsignaled, invalid;
1185  NTSTATUS status;
1186  DWORD ret;
1187 
1188  signaled = CreateEventW(NULL, TRUE, TRUE, NULL);
1189  nonsignaled = CreateEventW(NULL, TRUE, FALSE, NULL);
1190  invalid = (HANDLE) 0xdeadbee0;
1191 
1192  /* invalid handle with different values for lower 2 bits */
1193  SetLastError(0xdeadbeef);
1195  ok(ret == WAIT_FAILED, "expected WAIT_FAILED, got %d\n", ret);
1196  ok(GetLastError() == ERROR_INVALID_HANDLE, "expected ERROR_INVALID_HANDLE, got %d\n", GetLastError());
1197 
1198  SetLastError(0xdeadbeef);
1200  ok(ret == WAIT_FAILED, "expected WAIT_FAILED, got %d\n", ret);
1201  ok(GetLastError() == ERROR_INVALID_HANDLE, "expected ERROR_INVALID_HANDLE, got %d\n", GetLastError());
1202 
1203  SetLastError(0xdeadbeef);
1205  ok(ret == WAIT_FAILED, "expected WAIT_FAILED, got %d\n", ret);
1206  ok(GetLastError() == ERROR_INVALID_HANDLE, "expected ERROR_INVALID_HANDLE, got %d\n", GetLastError());
1207 
1208  SetLastError(0xdeadbeef);
1210  ok(ret == WAIT_FAILED, "expected WAIT_FAILED, got %d\n", ret);
1211  ok(GetLastError() == ERROR_INVALID_HANDLE, "expected ERROR_INVALID_HANDLE, got %d\n", GetLastError());
1212 
1213  /* valid handle with different values for lower 2 bits */
1214  SetLastError(0xdeadbeef);
1215  ret = WaitForSingleObject(nonsignaled, 0);
1216  ok(ret == WAIT_TIMEOUT, "expected WAIT_TIMEOUT, got %d\n", ret);
1217  ok(GetLastError() == 0xdeadbeef, "expected 0xdeadbeef, got %d\n", GetLastError());
1218 
1219  SetLastError(0xdeadbeef);
1220  ret = WaitForSingleObject(modify_handle(nonsignaled, 1), 0);
1221  ok(ret == WAIT_TIMEOUT, "expected WAIT_TIMEOUT, got %d\n", ret);
1222  ok(GetLastError() == 0xdeadbeef, "expected 0xdeadbeef, got %d\n", GetLastError());
1223 
1224  SetLastError(0xdeadbeef);
1225  ret = WaitForSingleObject(modify_handle(nonsignaled, 2), 0);
1226  ok(ret == WAIT_TIMEOUT, "expected WAIT_TIMEOUT, got %d\n", ret);
1227  ok(GetLastError() == 0xdeadbeef, "expected 0xdeadbeef, got %d\n", GetLastError());
1228 
1229  SetLastError(0xdeadbeef);
1230  ret = WaitForSingleObject(modify_handle(nonsignaled, 3), 0);
1231  ok(ret == WAIT_TIMEOUT, "expected WAIT_TIMEOUT, got %d\n", ret);
1232  ok(GetLastError() == 0xdeadbeef, "expected 0xdeadbeef, got %d\n", GetLastError());
1233 
1234  /* valid handle with different values for lower 2 bits */
1235  SetLastError(0xdeadbeef);
1236  ret = WaitForSingleObject(signaled, 0);
1237  ok(ret == WAIT_OBJECT_0, "expected WAIT_OBJECT_0, got %d\n", ret);
1238  ok(GetLastError() == 0xdeadbeef, "expected 0xdeadbeef, got %d\n", GetLastError());
1239 
1240  SetLastError(0xdeadbeef);
1241  ret = WaitForSingleObject(modify_handle(signaled, 1), 0);
1242  ok(ret == WAIT_OBJECT_0, "expected WAIT_OBJECT_0, got %d\n", ret);
1243  ok(GetLastError() == 0xdeadbeef, "expected 0xdeadbeef, got %d\n", GetLastError());
1244 
1245  SetLastError(0xdeadbeef);
1246  ret = WaitForSingleObject(modify_handle(signaled, 2), 0);
1247  ok(ret == WAIT_OBJECT_0, "expected WAIT_OBJECT_0, got %d\n", ret);
1248  ok(GetLastError() == 0xdeadbeef, "expected 0xdeadbeef, got %d\n", GetLastError());
1249 
1250  SetLastError(0xdeadbeef);
1251  ret = WaitForSingleObject(modify_handle(signaled, 3), 0);
1252  ok(ret == WAIT_OBJECT_0, "expected WAIT_OBJECT_0, got %d\n", ret);
1253  ok(GetLastError() == 0xdeadbeef, "expected 0xdeadbeef, got %d\n", GetLastError());
1254 
1255  /* pseudo handles are allowed in WaitForSingleObject and NtWaitForSingleObject */
1257  ok(ret == WAIT_TIMEOUT, "expected WAIT_TIMEOUT, got %u\n", ret);
1258 
1260  ok(ret == WAIT_TIMEOUT, "expected WAIT_TIMEOUT, got %u\n", ret);
1261 
1262  timeout.QuadPart = -1000000;
1263  status = pNtWaitForSingleObject(GetCurrentProcess(), FALSE, &timeout);
1264  ok(status == STATUS_TIMEOUT, "expected STATUS_TIMEOUT, got %08x\n", status);
1265 
1266  timeout.QuadPart = -1000000;
1267  status = pNtWaitForSingleObject(GetCurrentThread(), FALSE, &timeout);
1268  ok(status == STATUS_TIMEOUT, "expected STATUS_TIMEOUT, got %08x\n", status);
1269 
1270  CloseHandle(signaled);
1271  CloseHandle(nonsignaled);
1272 }
1273 
1275 {
1277  NTSTATUS status;
1278  DWORD r;
1279  int i;
1280  HANDLE maxevents[MAXIMUM_WAIT_OBJECTS];
1281 
1282  /* create the maximum number of events and make sure
1283  * we can wait on that many */
1284  for (i=0; i<MAXIMUM_WAIT_OBJECTS; i++)
1285  {
1286  maxevents[i] = CreateEventW(NULL, i==0, TRUE, NULL);
1287  ok( maxevents[i] != 0, "should create enough events\n");
1288  }
1289 
1290  /* a manual-reset event remains signaled, an auto-reset event is cleared */
1292  ok( r == WAIT_OBJECT_0, "should signal lowest handle first, got %d\n", r);
1294  ok( r == WAIT_OBJECT_0, "should signal handle #0 first, got %d\n", r);
1295  ok(ResetEvent(maxevents[0]), "ResetEvent\n");
1296  for (i=1; i<MAXIMUM_WAIT_OBJECTS; i++)
1297  {
1298  /* the lowest index is checked first and remaining events are untouched */
1300  ok( r == WAIT_OBJECT_0+i, "should signal handle #%d first, got %d\n", i, r);
1301  }
1302 
1303  /* run same test with Nt* call */
1304  for (i=0; i<MAXIMUM_WAIT_OBJECTS; i++)
1305  SetEvent(maxevents[i]);
1306 
1307  /* a manual-reset event remains signaled, an auto-reset event is cleared */
1308  status = pNtWaitForMultipleObjects(MAXIMUM_WAIT_OBJECTS, maxevents, TRUE, FALSE, NULL);
1309  ok(status == STATUS_WAIT_0, "should signal lowest handle first, got %08x\n", status);
1310  status = pNtWaitForMultipleObjects(MAXIMUM_WAIT_OBJECTS, maxevents, TRUE, FALSE, NULL);
1311  ok(status == STATUS_WAIT_0, "should signal handle #0 first, got %08x\n", status);
1312  ok(ResetEvent(maxevents[0]), "ResetEvent\n");
1313  for (i=1; i<MAXIMUM_WAIT_OBJECTS; i++)
1314  {
1315  /* the lowest index is checked first and remaining events are untouched */
1316  status = pNtWaitForMultipleObjects(MAXIMUM_WAIT_OBJECTS, maxevents, TRUE, FALSE, NULL);
1317  ok(status == STATUS_WAIT_0 + i, "should signal handle #%d first, got %08x\n", i, status);
1318  }
1319 
1320  for (i=0; i<MAXIMUM_WAIT_OBJECTS; i++)
1321  if (maxevents[i]) CloseHandle(maxevents[i]);
1322 
1323  /* in contrast to WaitForSingleObject, pseudo handles are not allowed in
1324  * WaitForMultipleObjects and NtWaitForMultipleObjects */
1325  maxevents[0] = GetCurrentProcess();
1326  SetLastError(0xdeadbeef);
1327  r = WaitForMultipleObjects(1, maxevents, FALSE, 100);
1328  todo_wine ok(r == WAIT_FAILED, "expected WAIT_FAILED, got %u\n", r);
1330  "expected ERROR_INVALID_HANDLE, got %u\n", GetLastError());
1331 
1332  maxevents[0] = GetCurrentThread();
1333  SetLastError(0xdeadbeef);
1334  r = WaitForMultipleObjects(1, maxevents, FALSE, 100);
1335  todo_wine ok(r == WAIT_FAILED, "expected WAIT_FAILED, got %u\n", r);
1337  "expected ERROR_INVALID_HANDLE, got %u\n", GetLastError());
1338 
1339  timeout.QuadPart = -1000000;
1340  maxevents[0] = GetCurrentProcess();
1341  status = pNtWaitForMultipleObjects(1, maxevents, TRUE, FALSE, &timeout);
1342  todo_wine ok(status == STATUS_INVALID_HANDLE, "expected STATUS_INVALID_HANDLE, got %08x\n", status);
1343 
1344  timeout.QuadPart = -1000000;
1345  maxevents[0] = GetCurrentThread();
1346  status = pNtWaitForMultipleObjects(1, maxevents, TRUE, FALSE, &timeout);
1347  todo_wine ok(status == STATUS_INVALID_HANDLE, "expected STATUS_INVALID_HANDLE, got %08x\n", status);
1348 }
1349 
1351 static void *g_initctxt;
1352 
1353 static BOOL CALLBACK initonce_callback(INIT_ONCE *initonce, void *parameter, void **ctxt)
1354 {
1356  /* zero bit set means here that initialization is taking place - initialization locked */
1357  ok(g_initctxt == *ctxt, "got wrong context value %p, expected %p\n", *ctxt, g_initctxt);
1358  ok(initonce->Ptr == (void*)0x1, "got %p\n", initonce->Ptr);
1359  ok(parameter == (void*)0xdeadbeef, "got wrong parameter\n");
1360  return g_initcallback_ret;
1361 }
1362 
1363 static void test_initonce(void)
1364 {
1365  INIT_ONCE initonce;
1366  BOOL ret, pending;
1367 
1368  if (!pInitOnceInitialize || !pInitOnceExecuteOnce)
1369  {
1370  win_skip("one-time initialization API not supported\n");
1371  return;
1372  }
1373 
1374  /* blocking initialization with callback */
1375  initonce.Ptr = (void*)0xdeadbeef;
1376  pInitOnceInitialize(&initonce);
1377  ok(initonce.Ptr == NULL, "got %p\n", initonce.Ptr);
1378 
1379  /* initialisation completed successfully */
1381  g_initctxt = NULL;
1382  ret = pInitOnceExecuteOnce(&initonce, initonce_callback, (void*)0xdeadbeef, &g_initctxt);
1383  ok(ret, "wrong ret %d err %u\n", ret, GetLastError());
1384  ok(initonce.Ptr == (void*)0x2, "got %p\n", initonce.Ptr);
1385  ok(g_initctxt == NULL, "got %p\n", g_initctxt);
1387 
1388  /* so it's been called already so won't be called again */
1389  g_initctxt = NULL;
1391  ret = pInitOnceExecuteOnce(&initonce, initonce_callback, (void*)0xdeadbeef, &g_initctxt);
1392  ok(ret, "wrong ret %d err %u\n", ret, GetLastError());
1393  ok(initonce.Ptr == (void*)0x2, "got %p\n", initonce.Ptr);
1394  ok(g_initctxt == NULL, "got %p\n", g_initctxt);
1396 
1397  pInitOnceInitialize(&initonce);
1399  /* 2 lower order bits should never be used, you'll get a crash in result */
1400  g_initctxt = (void*)0xFFFFFFF0;
1401  ret = pInitOnceExecuteOnce(&initonce, initonce_callback, (void*)0xdeadbeef, &g_initctxt);
1402  ok(ret, "wrong ret %d err %u\n", ret, GetLastError());
1403  ok(initonce.Ptr == (void*)0xFFFFFFF2, "got %p\n", initonce.Ptr);
1404  ok(g_initctxt == (void*)0xFFFFFFF0, "got %p\n", g_initctxt);
1406 
1407  /* callback failed */
1410  g_initctxt = NULL;
1411  pInitOnceInitialize(&initonce);
1412  SetLastError( 0xdeadbeef );
1413  ret = pInitOnceExecuteOnce(&initonce, initonce_callback, (void*)0xdeadbeef, &g_initctxt);
1414  ok(!ret && GetLastError() == 0xdeadbeef, "got wrong ret value %d err %u\n", ret, GetLastError());
1415  ok(initonce.Ptr == NULL, "got %p\n", initonce.Ptr);
1416  ok(g_initctxt == NULL, "got %p\n", g_initctxt);
1418 
1419  /* blocking initialization without a callback */
1420  pInitOnceInitialize(&initonce);
1421  g_initctxt = NULL;
1422  pending = FALSE;
1423  ret = pInitOnceBeginInitialize(&initonce, 0, &pending, &g_initctxt);
1424  ok(ret, "wrong ret %d err %u\n", ret, GetLastError());
1425  ok(pending, "got %d\n", pending);
1426  ok(initonce.Ptr == (void*)1, "got %p\n", initonce.Ptr);
1427  ok(g_initctxt == NULL, "got %p\n", g_initctxt);
1428  /* another attempt to begin initialization with block a single thread */
1429 
1430  g_initctxt = NULL;
1431  pending = 0xf;
1432  SetLastError( 0xdeadbeef );
1433  ret = pInitOnceBeginInitialize(&initonce, INIT_ONCE_CHECK_ONLY, &pending, &g_initctxt);
1434  ok(!ret && GetLastError() == ERROR_GEN_FAILURE, "wrong ret %d err %u\n", ret, GetLastError());
1435  ok(pending == 0xf, "got %d\n", pending);
1436  ok(initonce.Ptr == (void*)1, "got %p\n", initonce.Ptr);
1437  ok(g_initctxt == NULL, "got %p\n", g_initctxt);
1438 
1439  g_initctxt = (void*)0xdeadbee0;
1440  SetLastError( 0xdeadbeef );
1441  ret = pInitOnceComplete(&initonce, INIT_ONCE_INIT_FAILED, g_initctxt);
1442  ok(!ret && GetLastError() == ERROR_INVALID_PARAMETER, "wrong ret %d err %u\n", ret, GetLastError());
1443  ok(initonce.Ptr == (void*)1, "got %p\n", initonce.Ptr);
1444 
1445  /* once failed already */
1446  g_initctxt = (void*)0xdeadbee0;
1447  ret = pInitOnceComplete(&initonce, 0, g_initctxt);
1448  ok(ret, "wrong ret %d err %u\n", ret, GetLastError());
1449  ok(initonce.Ptr == (void*)0xdeadbee2, "got %p\n", initonce.Ptr);
1450 
1451  pInitOnceInitialize(&initonce);
1452  SetLastError( 0xdeadbeef );
1453  ret = pInitOnceComplete(&initonce, INIT_ONCE_INIT_FAILED, NULL);
1454  ok(!ret && GetLastError() == ERROR_GEN_FAILURE, "wrong ret %d err %u\n", ret, GetLastError());
1455  ok(initonce.Ptr == NULL, "got %p\n", initonce.Ptr);
1456 
1457  SetLastError( 0xdeadbeef );
1458  ret = pInitOnceComplete(&initonce, INIT_ONCE_INIT_FAILED | INIT_ONCE_ASYNC, NULL);
1459  ok(!ret && GetLastError() == ERROR_INVALID_PARAMETER, "wrong ret %d err %u\n", ret, GetLastError());
1460  ok(initonce.Ptr == NULL, "got %p\n", initonce.Ptr);
1461 
1462  ret = pInitOnceBeginInitialize(&initonce, 0, &pending, &g_initctxt);
1463  ok(ret, "wrong ret %d err %u\n", ret, GetLastError());
1464  ok(pending, "got %d\n", pending);
1465  ok(initonce.Ptr == (void*)1, "got %p\n", initonce.Ptr);
1466 
1467  SetLastError( 0xdeadbeef );
1468  ret = pInitOnceBeginInitialize(&initonce, INIT_ONCE_ASYNC, &pending, &g_initctxt);
1469  ok(!ret && GetLastError() == ERROR_INVALID_PARAMETER, "wrong ret %d err %u\n", ret, GetLastError());
1470 
1471  SetLastError( 0xdeadbeef );
1472  ret = pInitOnceComplete(&initonce, INIT_ONCE_INIT_FAILED | INIT_ONCE_ASYNC, NULL);
1473  ok(!ret && GetLastError() == ERROR_INVALID_PARAMETER, "wrong ret %d err %u\n", ret, GetLastError());
1474  ok(initonce.Ptr == (void*)1, "got %p\n", initonce.Ptr);
1475 
1476  SetLastError( 0xdeadbeef );
1477  ret = pInitOnceComplete(&initonce, 0, (void *)0xdeadbeef);
1478  ok(!ret && GetLastError() == ERROR_INVALID_PARAMETER, "wrong ret %d err %u\n", ret, GetLastError());
1479  ok(initonce.Ptr == (void*)1, "got %p\n", initonce.Ptr);
1480 
1481  ret = pInitOnceComplete(&initonce, INIT_ONCE_INIT_FAILED, NULL);
1482  ok(ret, "wrong ret %d err %u\n", ret, GetLastError());
1483  ok(initonce.Ptr == NULL, "got %p\n", initonce.Ptr);
1484 
1485  pInitOnceInitialize(&initonce);
1486  ret = pInitOnceBeginInitialize(&initonce, INIT_ONCE_ASYNC, &pending, &g_initctxt);
1487  ok(ret, "wrong ret %d err %u\n", ret, GetLastError());
1488  ok(pending, "got %d\n", pending);
1489  ok(initonce.Ptr == (void*)3, "got %p\n", initonce.Ptr);
1490 
1491  SetLastError( 0xdeadbeef );
1492  ret = pInitOnceBeginInitialize(&initonce, 0, &pending, &g_initctxt);
1493  ok(!ret && GetLastError() == ERROR_INVALID_PARAMETER, "wrong ret %d err %u\n", ret, GetLastError());
1494 
1495  ret = pInitOnceBeginInitialize(&initonce, INIT_ONCE_ASYNC, &pending, &g_initctxt);
1496  ok(ret, "wrong ret %d err %u\n", ret, GetLastError());
1497  ok(pending, "got %d\n", pending);
1498  ok(initonce.Ptr == (void*)3, "got %p\n", initonce.Ptr);
1499 
1500  SetLastError( 0xdeadbeef );
1501  ret = pInitOnceComplete(&initonce, INIT_ONCE_INIT_FAILED, NULL);
1502  ok(!ret && GetLastError() == ERROR_INVALID_PARAMETER, "wrong ret %d err %u\n", ret, GetLastError());
1503  ok(initonce.Ptr == (void*)3, "got %p\n", initonce.Ptr);
1504 
1505  SetLastError( 0xdeadbeef );
1506  ret = pInitOnceComplete(&initonce, INIT_ONCE_INIT_FAILED | INIT_ONCE_ASYNC, NULL);
1507  ok(!ret && GetLastError() == ERROR_INVALID_PARAMETER, "wrong ret %d err %u\n", ret, GetLastError());
1508  ok(initonce.Ptr == (void*)3, "got %p\n", initonce.Ptr);
1509 
1510  SetLastError( 0xdeadbeef );
1511  ret = pInitOnceComplete(&initonce, INIT_ONCE_ASYNC, (void *)0xdeadbeef);
1512  ok(!ret && GetLastError() == ERROR_INVALID_PARAMETER, "wrong ret %d err %u\n", ret, GetLastError());
1513  ok(initonce.Ptr == (void*)3, "got %p\n", initonce.Ptr);
1514 
1515  ret = pInitOnceComplete(&initonce, INIT_ONCE_ASYNC, (void *)0xdeadbee0);
1516  ok(ret, "wrong ret %d err %u\n", ret, GetLastError());
1517  ok(initonce.Ptr == (void*)0xdeadbee2, "got %p\n", initonce.Ptr);
1518 
1519  SetLastError( 0xdeadbeef );
1520  ret = pInitOnceComplete(&initonce, INIT_ONCE_INIT_FAILED | INIT_ONCE_ASYNC, NULL);
1521  ok(!ret && GetLastError() == ERROR_INVALID_PARAMETER, "wrong ret %d err %u\n", ret, GetLastError());
1522  ok(initonce.Ptr == (void*)0xdeadbee2, "got %p\n", initonce.Ptr);
1523 
1524  pInitOnceInitialize(&initonce);
1525  ret = pInitOnceBeginInitialize(&initonce, 0, &pending, &g_initctxt);
1526  ok(ret, "wrong ret %d err %u\n", ret, GetLastError());
1527  ok(pending, "got %d\n", pending);
1528  ok(initonce.Ptr == (void*)1, "got %p\n", initonce.Ptr);
1529 
1530  /* test INIT_ONCE_CHECK_ONLY */
1531 
1532  pInitOnceInitialize(&initonce);
1533  SetLastError( 0xdeadbeef );
1534  ret = pInitOnceBeginInitialize(&initonce, INIT_ONCE_CHECK_ONLY, &pending, &g_initctxt);
1535  ok(!ret && GetLastError() == ERROR_GEN_FAILURE, "wrong ret %d err %u\n", ret, GetLastError());
1536  SetLastError( 0xdeadbeef );
1537  ret = pInitOnceBeginInitialize(&initonce, INIT_ONCE_CHECK_ONLY|INIT_ONCE_ASYNC, &pending, &g_initctxt);
1538  ok(!ret && GetLastError() == ERROR_INVALID_PARAMETER, "wrong ret %d err %u\n", ret, GetLastError());
1539 
1540  ret = pInitOnceBeginInitialize(&initonce, 0, &pending, &g_initctxt);
1541  ok(ret, "wrong ret %d err %u\n", ret, GetLastError());
1542  ok(pending, "got %d\n", pending);
1543  ok(initonce.Ptr == (void*)1, "got %p\n", initonce.Ptr);
1544 
1545  SetLastError( 0xdeadbeef );
1546  ret = pInitOnceBeginInitialize(&initonce, INIT_ONCE_CHECK_ONLY, &pending, &g_initctxt);
1547  ok(!ret && GetLastError() == ERROR_GEN_FAILURE, "wrong ret %d err %u\n", ret, GetLastError());
1548  SetLastError( 0xdeadbeef );
1549  ret = pInitOnceBeginInitialize(&initonce, INIT_ONCE_CHECK_ONLY|INIT_ONCE_ASYNC, &pending, &g_initctxt);
1550  ok(!ret && GetLastError() == ERROR_INVALID_PARAMETER, "wrong ret %d err %u\n", ret, GetLastError());
1551 
1552  ret = pInitOnceComplete(&initonce, 0, (void *)0xdeadbee0);
1553  ok(ret, "wrong ret %d err %u\n", ret, GetLastError());
1554  ok(initonce.Ptr == (void*)0xdeadbee2, "got %p\n", initonce.Ptr);
1555 
1556  ret = pInitOnceBeginInitialize(&initonce, INIT_ONCE_CHECK_ONLY, &pending, &g_initctxt);
1557  ok(ret, "got wrong ret value %d err %u\n", ret, GetLastError());
1558  ok(!pending, "got %d\n", pending);
1559  ok(initonce.Ptr == (void*)0xdeadbee2, "got %p\n", initonce.Ptr);
1560  ok(g_initctxt == (void*)0xdeadbee0, "got %p\n", initonce.Ptr);
1561 
1562  SetLastError( 0xdeadbeef );
1563  ret = pInitOnceBeginInitialize(&initonce, INIT_ONCE_CHECK_ONLY|INIT_ONCE_ASYNC, &pending, &g_initctxt);
1564  ok(!ret && GetLastError() == ERROR_INVALID_PARAMETER, "wrong ret %d err %u\n", ret, GetLastError());
1565 
1566  pInitOnceInitialize(&initonce);
1567  ret = pInitOnceBeginInitialize(&initonce, INIT_ONCE_ASYNC, &pending, &g_initctxt);
1568  ok(ret, "wrong ret %d err %u\n", ret, GetLastError());
1569  ok(pending, "got %d\n", pending);
1570  ok(initonce.Ptr == (void*)3, "got %p\n", initonce.Ptr);
1571 
1572  SetLastError( 0xdeadbeef );
1573  ret = pInitOnceBeginInitialize(&initonce, INIT_ONCE_CHECK_ONLY, &pending, &g_initctxt);
1574  ok(!ret && GetLastError() == ERROR_GEN_FAILURE, "wrong ret %d err %u\n", ret, GetLastError());
1575  SetLastError( 0xdeadbeef );
1576  ret = pInitOnceBeginInitialize(&initonce, INIT_ONCE_CHECK_ONLY|INIT_ONCE_ASYNC, &pending, &g_initctxt);
1577  ok(!ret && GetLastError() == ERROR_INVALID_PARAMETER, "wrong ret %d err %u\n", ret, GetLastError());
1578 
1579  ret = pInitOnceComplete(&initonce, INIT_ONCE_ASYNC, (void *)0xdeadbee0);
1580  ok(ret, "wrong ret %d err %u\n", ret, GetLastError());
1581  ok(initonce.Ptr == (void*)0xdeadbee2, "got %p\n", initonce.Ptr);
1582 
1583  ret = pInitOnceBeginInitialize(&initonce, INIT_ONCE_CHECK_ONLY, &pending, &g_initctxt);
1584  ok(ret, "got wrong ret value %d err %u\n", ret, GetLastError());
1585  ok(!pending, "got %d\n", pending);
1586  ok(initonce.Ptr == (void*)0xdeadbee2, "got %p\n", initonce.Ptr);
1587  ok(g_initctxt == (void*)0xdeadbee0, "got %p\n", initonce.Ptr);
1588 
1589  SetLastError( 0xdeadbeef );
1590  ret = pInitOnceBeginInitialize(&initonce, INIT_ONCE_CHECK_ONLY|INIT_ONCE_ASYNC, &pending, &g_initctxt);
1591  ok(!ret && GetLastError() == ERROR_INVALID_PARAMETER, "wrong ret %d err %u\n", ret, GetLastError());
1592 }
1593 
1594 static CONDITION_VARIABLE buffernotempty = CONDITION_VARIABLE_INIT;
1595 static CONDITION_VARIABLE buffernotfull = CONDITION_VARIABLE_INIT;
1600 
1601 #define BUFFER_SIZE 5
1602 
1604  DWORD sleepinterval = 5;
1605 
1606  while (1) {
1607  Sleep(sleepinterval);
1608  if (sleepinterval > 1)
1609  sleepinterval -= 1;
1610 
1612  while ((bufferlen == BUFFER_SIZE) && !condvar_stop) {
1614  if (!pSleepConditionVariableCS(&buffernotfull, &buffercrit, sleepinterval)) {
1615  if (GetLastError() != ERROR_TIMEOUT)
1617  }
1618  }
1619  if (condvar_stop) {
1621  break;
1622  }
1623  bufferlen++;
1624  totalproduced++;
1626  pWakeConditionVariable(&buffernotempty);
1627  }
1628  return 0;
1629 }
1630 
1632  DWORD *cnt = (DWORD*)x;
1633  DWORD sleepinterval = 1;
1634 
1635  while (1) {
1637  while ((bufferlen == 0) && !condvar_stop) {
1639  if (!pSleepConditionVariableCS (&buffernotempty, &buffercrit, sleepinterval)) {
1640  if (GetLastError() != ERROR_TIMEOUT)
1642  }
1643  }
1644  if (condvar_stop && (bufferlen == 0)) {
1646  break;
1647  }
1648  bufferlen--;
1649  totalconsumed++;
1650  (*cnt)++;
1652  pWakeConditionVariable(&buffernotfull);
1653  Sleep(sleepinterval);
1654  if (sleepinterval < 5) sleepinterval += 1;
1655  }
1656  return 0;
1657 }
1658 
1660 {
1661  HANDLE hp1,hp2,hp3,hc1,hc2,hc3;
1662  DWORD dummy;
1663  DWORD cnt1,cnt2,cnt3;
1664 
1665  if (!pInitializeConditionVariable) {
1666  /* function is not yet in XP, only in newer Windows */
1667  win_skip("no condition variable support.\n");
1668  return;
1669  }
1670 
1671  /* Implement a producer / consumer scheme with non-full / non-empty triggers */
1672 
1673  /* If we have static initialized condition variables, InitializeConditionVariable
1674  * is not strictly necessary.
1675  * pInitializeConditionVariable(&buffernotfull);
1676  */
1677  pInitializeConditionVariable(&buffernotempty);
1679 
1680  /* Larger Test: consumer/producer example */
1681 
1682  bufferlen = totalproduced = totalconsumed = cnt1 = cnt2 = cnt3 = 0;
1683 
1684  hp1 = CreateThread(NULL, 0, condvar_producer, NULL, 0, &dummy);
1685  hp2 = CreateThread(NULL, 0, condvar_producer, NULL, 0, &dummy);
1686  hp3 = CreateThread(NULL, 0, condvar_producer, NULL, 0, &dummy);
1687  hc1 = CreateThread(NULL, 0, condvar_consumer, (PVOID)&cnt1, 0, &dummy);
1688  hc2 = CreateThread(NULL, 0, condvar_consumer, (PVOID)&cnt2, 0, &dummy);
1689  hc3 = CreateThread(NULL, 0, condvar_consumer, (PVOID)&cnt3, 0, &dummy);
1690 
1691  /* Limit run to 0.5 seconds. */
1692  Sleep(500);
1693 
1694  /* tear down start */
1695  condvar_stop = TRUE;
1696 
1697  /* final wake up call */
1698  pWakeAllConditionVariable (&buffernotfull);
1699  pWakeAllConditionVariable (&buffernotempty);
1700 
1701  /* (mostly an implementation detail)
1702  * ok(buffernotfull.Ptr == NULL, "buffernotfull.Ptr is %p\n", buffernotfull.Ptr);
1703  */
1704 
1705  WaitForSingleObject(hp1, 1000);
1706  WaitForSingleObject(hp2, 1000);
1707  WaitForSingleObject(hp3, 1000);
1708  WaitForSingleObject(hc1, 1000);
1709  WaitForSingleObject(hc2, 1000);
1710  WaitForSingleObject(hc3, 1000);
1711 
1713  "consumed %d != produced %d\n", totalconsumed, totalproduced);
1714  ok (!condvar_sleeperr, "error occurred during SleepConditionVariableCS\n");
1715 
1716  /* Checking cnt1 - cnt2 for non-0 would be not good, the case where
1717  * one consumer does not get anything to do is possible. */
1718  trace("produced %d, c1 %d, c2 %d, c3 %d\n", totalproduced, cnt1, cnt2, cnt3);
1719  /* The sleeps of the producer or consumer should not go above 100* produced count,
1720  * otherwise the implementation does not sleep correctly. But yet again, this is
1721  * not hard defined. */
1722  trace("producer sleep %d, consumer sleep %d\n", condvar_producer_sleepcnt, condvar_consumer_sleepcnt);
1723 }
1724 
1725 /* Sample test for some sequence of events happening, sequenced using "condvar_seq" */
1726 static DWORD condvar_seq = 0;
1727 static CONDITION_VARIABLE condvar_base = CONDITION_VARIABLE_INIT;
1729 static SRWLOCK condvar_srwlock;
1730 
1731 /* Sequence of wake/sleep to check boundary conditions:
1732  * 0: init
1733  * 1: producer emits a WakeConditionVariable without consumer waiting.
1734  * 2: consumer sleeps without a wake expecting timeout
1735  * 3: producer emits a WakeAllConditionVariable without consumer waiting.
1736  * 4: consumer sleeps without a wake expecting timeout
1737  * 5: a wake is handed to a SleepConditionVariableCS
1738  * 6: a wakeall is handed to a SleepConditionVariableCS
1739  * 7: sleep after above should timeout
1740  * 8: wake with crit section locked into the sleep timeout
1741  *
1742  * the following tests will only be executed if InitializeSRWLock is available
1743  *
1744  * 9: producer (exclusive) wakes up consumer (exclusive)
1745  * 10: producer (exclusive) wakes up consumer (shared)
1746  * 11: producer (shared) wakes up consumer (exclusive)
1747  * 12: producer (shared) wakes up consumer (shared)
1748  * 13: end
1749  */
1751  while (condvar_seq < 1) Sleep(1);
1752 
1753  pWakeConditionVariable (&condvar_base);
1754  condvar_seq = 2;
1755 
1756  while (condvar_seq < 3) Sleep(1);
1757  pWakeAllConditionVariable (&condvar_base);
1758  condvar_seq = 4;
1759 
1760  while (condvar_seq < 5) Sleep(1);
1762  pWakeConditionVariable (&condvar_base);
1764  while (condvar_seq < 6) Sleep(1);
1766  pWakeAllConditionVariable (&condvar_base);
1768 
1769  while (condvar_seq < 8) Sleep(1);
1771  pWakeConditionVariable (&condvar_base);
1772  Sleep(50);
1774 
1775  /* skip over remaining tests if InitializeSRWLock is not available */
1776  if (!pInitializeSRWLock)
1777  return 0;
1778 
1779  while (condvar_seq < 9) Sleep(1);
1780  pAcquireSRWLockExclusive(&condvar_srwlock);
1781  pWakeConditionVariable(&condvar_base);
1782  pReleaseSRWLockExclusive(&condvar_srwlock);
1783 
1784  while (condvar_seq < 10) Sleep(1);
1785  pAcquireSRWLockExclusive(&condvar_srwlock);
1786  pWakeConditionVariable(&condvar_base);
1787  pReleaseSRWLockExclusive(&condvar_srwlock);
1788 
1789  while (condvar_seq < 11) Sleep(1);
1790  pAcquireSRWLockShared(&condvar_srwlock);
1791  pWakeConditionVariable(&condvar_base);
1792  pReleaseSRWLockShared(&condvar_srwlock);
1793 
1794  while (condvar_seq < 12) Sleep(1);
1795  Sleep(50); /* ensure that consumer waits for cond variable */
1796  pAcquireSRWLockShared(&condvar_srwlock);
1797  pWakeConditionVariable(&condvar_base);
1798  pReleaseSRWLockShared(&condvar_srwlock);
1799 
1800  return 0;
1801 }
1802 
1804  BOOL ret;
1805 
1806  while (condvar_seq < 2) Sleep(1);
1807 
1808  /* wake was emitted, but we were not sleeping */
1810  ret = pSleepConditionVariableCS(&condvar_base, &condvar_crit, 10);
1812  ok (!ret, "SleepConditionVariableCS should return FALSE on out of band wake\n");
1813  ok (GetLastError() == ERROR_TIMEOUT, "SleepConditionVariableCS should return ERROR_TIMEOUT on out of band wake, not %d\n", GetLastError());
1814 
1815  condvar_seq = 3;
1816  while (condvar_seq < 4) Sleep(1);
1817 
1818  /* wake all was emitted, but we were not sleeping */
1820  ret = pSleepConditionVariableCS(&condvar_base, &condvar_crit, 10);
1822  ok (!ret, "SleepConditionVariableCS should return FALSE on out of band wake\n");
1823  ok (GetLastError() == ERROR_TIMEOUT, "SleepConditionVariableCS should return ERROR_TIMEOUT on out of band wake, not %d\n", GetLastError());
1824 
1826  condvar_seq = 5;
1827  ret = pSleepConditionVariableCS(&condvar_base, &condvar_crit, 200);
1829  ok (ret, "SleepConditionVariableCS should return TRUE on good wake\n");
1830 
1832  condvar_seq = 6;
1833  ret = pSleepConditionVariableCS(&condvar_base, &condvar_crit, 200);
1835  ok (ret, "SleepConditionVariableCS should return TRUE on good wakeall\n");
1836  condvar_seq = 7;
1837 
1839  ret = pSleepConditionVariableCS(&condvar_base, &condvar_crit, 10);
1841  ok (!ret, "SleepConditionVariableCS should return FALSE on out of band wake\n");
1842  ok (GetLastError() == ERROR_TIMEOUT, "SleepConditionVariableCS should return ERROR_TIMEOUT on out of band wake, not %d\n", GetLastError());
1843 
1845  condvar_seq = 8;
1846  ret = pSleepConditionVariableCS(&condvar_base, &condvar_crit, 20);
1848  ok (ret, "SleepConditionVariableCS should still return TRUE on crit unlock delay\n");
1849 
1850  /* skip over remaining tests if InitializeSRWLock is not available */
1851  if (!pInitializeSRWLock)
1852  {
1853  win_skip("no srw lock support.\n");
1854  condvar_seq = 13; /* end */
1855  return 0;
1856  }
1857 
1858  pAcquireSRWLockExclusive(&condvar_srwlock);
1859  condvar_seq = 9;
1860  ret = pSleepConditionVariableSRW(&condvar_base, &condvar_srwlock, 200, 0);
1861  pReleaseSRWLockExclusive(&condvar_srwlock);
1862  ok (ret, "pSleepConditionVariableSRW should return TRUE on good wake\n");
1863 
1864  pAcquireSRWLockShared(&condvar_srwlock);
1865  condvar_seq = 10;
1866  ret = pSleepConditionVariableSRW(&condvar_base, &condvar_srwlock, 200, CONDITION_VARIABLE_LOCKMODE_SHARED);
1867  pReleaseSRWLockShared(&condvar_srwlock);
1868  ok (ret, "pSleepConditionVariableSRW should return TRUE on good wake\n");
1869 
1870  pAcquireSRWLockExclusive(&condvar_srwlock);
1871  condvar_seq = 11;
1872  ret = pSleepConditionVariableSRW(&condvar_base, &condvar_srwlock, 200, 0);
1873  pReleaseSRWLockExclusive(&condvar_srwlock);
1874  ok (ret, "pSleepConditionVariableSRW should return TRUE on good wake\n");
1875 
1876  pAcquireSRWLockShared(&condvar_srwlock);
1877  condvar_seq = 12;
1878  ret = pSleepConditionVariableSRW(&condvar_base, &condvar_srwlock, 200, CONDITION_VARIABLE_LOCKMODE_SHARED);
1879  pReleaseSRWLockShared(&condvar_srwlock);
1880  ok (ret, "pSleepConditionVariableSRW should return TRUE on good wake\n");
1881 
1882  condvar_seq = 13;
1883  return 0;
1884 }
1885 
1886 static void test_condvars_base(void) {
1887  HANDLE hp, hc;
1888  DWORD dummy;
1889  BOOL ret;
1890 
1891 
1892  if (!pInitializeConditionVariable) {
1893  /* function is not yet in XP, only in newer Windows */
1894  win_skip("no condition variable support.\n");
1895  return;
1896  }
1897 
1899 
1900  if (pInitializeSRWLock)
1901  pInitializeSRWLock(&condvar_srwlock);
1902 
1904  ret = pSleepConditionVariableCS(&condvar_base, &condvar_crit, 10);
1906 
1907  ok (!ret, "SleepConditionVariableCS should return FALSE on untriggered condvar\n");
1908  ok (GetLastError() == ERROR_TIMEOUT, "SleepConditionVariableCS should return ERROR_TIMEOUT on untriggered condvar, not %d\n", GetLastError());
1909 
1910  if (pInitializeSRWLock)
1911  {
1912  pAcquireSRWLockExclusive(&condvar_srwlock);
1913  ret = pSleepConditionVariableSRW(&condvar_base, &condvar_srwlock, 10, 0);
1914  pReleaseSRWLockExclusive(&condvar_srwlock);
1915 
1916  ok(!ret, "SleepConditionVariableSRW should return FALSE on untriggered condvar\n");
1917  ok(GetLastError() == ERROR_TIMEOUT, "SleepConditionVariableSRW should return ERROR_TIMEOUT on untriggered condvar, not %d\n", GetLastError());
1918 
1919  pAcquireSRWLockShared(&condvar_srwlock);
1920  ret = pSleepConditionVariableSRW(&condvar_base, &condvar_srwlock, 10, CONDITION_VARIABLE_LOCKMODE_SHARED);
1921  pReleaseSRWLockShared(&condvar_srwlock);
1922 
1923  ok(!ret, "SleepConditionVariableSRW should return FALSE on untriggered condvar\n");
1924  ok(GetLastError() == ERROR_TIMEOUT, "SleepConditionVariableSRW should return ERROR_TIMEOUT on untriggered condvar, not %d\n", GetLastError());
1925  }
1926 
1927 
1930 
1931  condvar_seq = 1; /* go */
1932 
1933  while (condvar_seq < 9)
1934  Sleep (5);
1935  WaitForSingleObject(hp, 100);
1936  WaitForSingleObject(hc, 100);
1937 }
1938 
1939 static LONG srwlock_seq = 0;
1940 static SRWLOCK srwlock_base;
1941 static struct
1942 {
1952 
1953 /* Sequence of acquire/release to check boundary conditions:
1954  * 0: init
1955  *
1956  * 1: thread2 acquires an exclusive lock and tries to acquire a second exclusive lock
1957  * 2: thread1 expects a deadlock and releases the waiting lock
1958  * thread2 releases the lock again
1959  *
1960  * 3: thread2 acquires an exclusive lock and tries to acquire a shared lock
1961  * 4: thread1 expects a deadlock and releases the waiting lock
1962  * thread2 releases the lock again
1963  *
1964  * 5: thread2 acquires a shared lock and tries to acquire an exclusive lock
1965  * 6: thread1 expects a deadlock and releases the waiting lock
1966  * thread2 releases the lock again
1967  *
1968  * 7: thread2 acquires and releases two nested shared locks
1969  *
1970  * 8: thread1 acquires an exclusive lock
1971  * 9: thread2 tries to acquire the exclusive lock, too
1972  * thread1 releases the exclusive lock again
1973  * 10: thread2 enters the exclusive lock and leaves it immediately again
1974  *
1975  * 11: thread1 acquires a shared lock
1976  * 12: thread2 acquires and releases a shared lock
1977  * thread1 releases the lock again
1978  *
1979  * 13: thread1 acquires a shared lock
1980  * 14: thread2 tries to acquire an exclusive lock
1981  * 15: thread3 tries to acquire a shared lock
1982  * 16: thread1 releases the shared lock
1983  * 17: thread2 wakes up and releases the exclusive lock
1984  * 18: thread3 wakes up and releases the shared lock
1985  *
1986  * the following tests will only be executed if TryAcquireSRWLock* is available
1987  *
1988  * 19: thread1 calls TryAcquireSRWLockExclusive which should return TRUE
1989  * thread1 checks the result of recursive calls to TryAcquireSRWLock*
1990  * thread1 releases the exclusive lock
1991  *
1992  * thread1 calls TryAcquireSRWLockShared which should return TRUE
1993  * thread1 checks the result of recursive calls to TryAcquireSRWLock*
1994  * thread1 releases the shared lock
1995  *
1996  * thread1 acquires an exclusive lock
1997  * 20: thread2 calls TryAcquireSRWLockShared which should return FALSE
1998  * thread2 calls TryAcquireSRWLockExclusive which should return FALSE
1999  * 21: thread1 releases the exclusive lock
2000  *
2001  * thread1 acquires an shared lock
2002  * 22: thread2 calls TryAcquireSRWLockShared which should return TRUE
2003  * thread2 calls TryAcquireSRWLockExclusive which should return FALSE
2004  * 23: thread1 releases the shared lock
2005  *
2006  * thread1 acquires a shared lock and tries to acquire an exclusive lock
2007  * 24: thread2 calls TryAcquireSRWLockShared which should return FALSE
2008  * thread2 calls TryAcquireSRWLockExclusive which should return FALSE
2009  * 25: thread1 releases the exclusive lock
2010  *
2011  * thread1 acquires two shared locks
2012  * 26: thread2 calls TryAcquireSRWLockShared which should return TRUE
2013  * thread2 calls TryAcquireSRWLockExclusive which should return FALSE
2014  * 27: thread1 releases one shared lock
2015  * 28: thread2 calls TryAcquireSRWLockShared which should return TRUE
2016  * thread2 calls TryAcquireSRWLockExclusive which should return FALSE
2017  * 29: thread1 releases the second shared lock
2018  * 30: thread2 calls TryAcquireSRWLockShared which should return TRUE
2019  * thread2 calls TryAcquireSRWLockExclusive which should return TRUE
2020  *
2021  * 31: end
2022  */
2023 
2025 {
2026  /* seq 2 */
2027  while (srwlock_seq < 2) Sleep(1);
2028  Sleep(100);
2029  if (InterlockedIncrement(&srwlock_seq) != 3)
2030  InterlockedIncrement(&srwlock_base_errors.samethread_excl_excl);
2031  pReleaseSRWLockExclusive(&srwlock_base);
2032 
2033  /* seq 4 */
2034  while (srwlock_seq < 4) Sleep(1);
2035  Sleep(100);
2036  if (InterlockedIncrement(&srwlock_seq) != 5)
2037  InterlockedIncrement(&srwlock_base_errors.samethread_excl_shared);
2038  pReleaseSRWLockExclusive(&srwlock_base);
2039 
2040  /* seq 6 */
2041  while (srwlock_seq < 6) Sleep(1);
2042  Sleep(100);
2043  if (InterlockedIncrement(&srwlock_seq) != 7)
2044  InterlockedIncrement(&srwlock_base_errors.samethread_shared_excl);
2045  pReleaseSRWLockShared(&srwlock_base);
2046 
2047  /* seq 8 */
2048  while (srwlock_seq < 8) Sleep(1);
2049  pAcquireSRWLockExclusive(&srwlock_base);
2050  if (InterlockedIncrement(&srwlock_seq) != 9)
2051  InterlockedIncrement(&srwlock_base_errors.wrong_execution_order);
2052  Sleep(100);
2053  if (InterlockedIncrement(&srwlock_seq) != 10)
2054  InterlockedIncrement(&srwlock_base_errors.multithread_excl_excl);
2055  pReleaseSRWLockExclusive(&srwlock_base);
2056 
2057  /* seq 11 */
2058  while (srwlock_seq < 11) Sleep(1);
2059  pAcquireSRWLockShared(&srwlock_base);
2060  if (InterlockedIncrement(&srwlock_seq) != 12)
2061  InterlockedIncrement(&srwlock_base_errors.wrong_execution_order);
2062 
2063  /* seq 13 */
2064  while (srwlock_seq < 13) Sleep(1);
2065  pReleaseSRWLockShared(&srwlock_base);
2066  pAcquireSRWLockShared(&srwlock_base);
2067  if (InterlockedIncrement(&srwlock_seq) != 14)
2068  InterlockedIncrement(&srwlock_base_errors.wrong_execution_order);
2069 
2070  /* seq 16 */
2071  while (srwlock_seq < 16) Sleep(1);
2072  Sleep(50); /* ensure that both the exclusive and shared access thread are queued */
2073  if (InterlockedIncrement(&srwlock_seq) != 17)
2074  InterlockedIncrement(&srwlock_base_errors.wrong_execution_order);
2075  pReleaseSRWLockShared(&srwlock_base);
2076 
2077  /* skip over remaining tests if TryAcquireSRWLock* is not available */
2078  if (!pTryAcquireSRWLockExclusive)
2079  return 0;
2080 
2081  /* seq 19 */
2082  while (srwlock_seq < 19) Sleep(1);
2083  if (pTryAcquireSRWLockExclusive(&srwlock_base))
2084  {
2085  if (pTryAcquireSRWLockShared(&srwlock_base))
2086  InterlockedIncrement(&srwlock_base_errors.trylock_shared);
2087  if (pTryAcquireSRWLockExclusive(&srwlock_base))
2089  pReleaseSRWLockExclusive(&srwlock_base);
2090  }
2091  else
2093 
2094  if (pTryAcquireSRWLockShared(&srwlock_base))
2095  {
2096  if (pTryAcquireSRWLockShared(&srwlock_base))
2097  pReleaseSRWLockShared(&srwlock_base);
2098  else
2099  InterlockedIncrement(&srwlock_base_errors.trylock_shared);
2100  if (pTryAcquireSRWLockExclusive(&srwlock_base))
2102  pReleaseSRWLockShared(&srwlock_base);
2103  }
2104  else
2105  InterlockedIncrement(&srwlock_base_errors.trylock_shared);
2106 
2107  pAcquireSRWLockExclusive(&srwlock_base);
2108  if (InterlockedIncrement(&srwlock_seq) != 20)
2109  InterlockedIncrement(&srwlock_base_errors.wrong_execution_order);
2110 
2111  /* seq 21 */
2112  while (srwlock_seq < 21) Sleep(1);
2113  pReleaseSRWLockExclusive(&srwlock_base);
2114  pAcquireSRWLockShared(&srwlock_base);
2115  if (InterlockedIncrement(&srwlock_seq) != 22)
2116  InterlockedIncrement(&srwlock_base_errors.wrong_execution_order);
2117 
2118  /* seq 23 */
2119  while (srwlock_seq < 23) Sleep(1);
2120  pReleaseSRWLockShared(&srwlock_base);
2121  pAcquireSRWLockShared(&srwlock_base);
2122  if (InterlockedIncrement(&srwlock_seq) != 24)
2123  InterlockedIncrement(&srwlock_base_errors.wrong_execution_order);
2124 
2125  /* seq 25 */
2126  pAcquireSRWLockExclusive(&srwlock_base);
2127  if (srwlock_seq != 25)
2128  InterlockedIncrement(&srwlock_base_errors.wrong_execution_order);
2129  pReleaseSRWLockExclusive(&srwlock_base);
2130 
2131  pAcquireSRWLockShared(&srwlock_base);
2132  pAcquireSRWLockShared(&srwlock_base);
2133  if (InterlockedIncrement(&srwlock_seq) != 26)
2134  InterlockedIncrement(&srwlock_base_errors.wrong_execution_order);
2135 
2136  /* seq 27 */
2137  while (srwlock_seq < 27) Sleep(1);
2138  pReleaseSRWLockShared(&srwlock_base);
2139  if (InterlockedIncrement(&srwlock_seq) != 28)
2140  InterlockedIncrement(&srwlock_base_errors.wrong_execution_order);
2141 
2142  /* seq 29 */
2143  while (srwlock_seq < 29) Sleep(1);
2144  pReleaseSRWLockShared(&srwlock_base);
2145  if (InterlockedIncrement(&srwlock_seq) != 30)
2146  InterlockedIncrement(&srwlock_base_errors.wrong_execution_order);
2147 
2148  return 0;
2149 }
2150 
2152 {
2153  /* seq 1 */
2154  while (srwlock_seq < 1) Sleep(1);
2155  pAcquireSRWLockExclusive(&srwlock_base);
2156  if (InterlockedIncrement(&srwlock_seq) != 2)
2157  InterlockedIncrement(&srwlock_base_errors.wrong_execution_order);
2158 
2159  /* seq 3 */
2160  pAcquireSRWLockExclusive(&srwlock_base);
2161  if (srwlock_seq != 3)
2162  InterlockedIncrement(&srwlock_base_errors.samethread_excl_excl);
2163  pReleaseSRWLockExclusive(&srwlock_base);
2164  pAcquireSRWLockExclusive(&srwlock_base);
2165  if (InterlockedIncrement(&srwlock_seq) != 4)
2166  InterlockedIncrement(&srwlock_base_errors.wrong_execution_order);
2167 
2168  /* seq 5 */
2169  pAcquireSRWLockShared(&srwlock_base);
2170  if (srwlock_seq != 5)
2171  InterlockedIncrement(&srwlock_base_errors.samethread_excl_shared);
2172  pReleaseSRWLockShared(&srwlock_base);
2173  pAcquireSRWLockShared(&srwlock_base);
2174  if (InterlockedIncrement(&srwlock_seq) != 6)
2175  InterlockedIncrement(&srwlock_base_errors.wrong_execution_order);
2176 
2177  /* seq 7 */
2178  pAcquireSRWLockExclusive(&srwlock_base);
2179  if (srwlock_seq != 7)
2180  InterlockedIncrement(&srwlock_base_errors.samethread_shared_excl);
2181  pReleaseSRWLockExclusive(&srwlock_base);
2182  pAcquireSRWLockShared(&srwlock_base);
2183  pAcquireSRWLockShared(&srwlock_base);
2184  pReleaseSRWLockShared(&srwlock_base);
2185  pReleaseSRWLockShared(&srwlock_base);
2186  if (InterlockedIncrement(&srwlock_seq) != 8)
2187  InterlockedIncrement(&srwlock_base_errors.wrong_execution_order);
2188 
2189  /* seq 9, 10 */
2190  while (srwlock_seq < 9) Sleep(1);
2191  pAcquireSRWLockExclusive(&srwlock_base);
2192  if (srwlock_seq != 10)
2193  InterlockedIncrement(&srwlock_base_errors.multithread_excl_excl);
2194  pReleaseSRWLockExclusive(&srwlock_base);
2195  if (InterlockedIncrement(&srwlock_seq) != 11)
2196  InterlockedIncrement(&srwlock_base_errors.wrong_execution_order);
2197 
2198  /* seq 12 */
2199  while (srwlock_seq < 12) Sleep(1);
2200  pAcquireSRWLockShared(&srwlock_base);
2201  pReleaseSRWLockShared(&srwlock_base);
2202  if (InterlockedIncrement(&srwlock_seq) != 13)
2203  InterlockedIncrement(&srwlock_base_errors.wrong_execution_order);
2204 
2205  /* seq 14 */
2206  while (srwlock_seq < 14) Sleep(1);
2207  if (InterlockedIncrement(&srwlock_seq) != 15)
2208  InterlockedIncrement(&srwlock_base_errors.wrong_execution_order);
2209 
2210  /* seq 17 */
2211  pAcquireSRWLockExclusive(&srwlock_base);
2212  if (srwlock_seq != 17)
2213  InterlockedIncrement(&srwlock_base_errors.excl_not_preferred);
2214  if (InterlockedIncrement(&srwlock_seq) != 18)
2215  InterlockedIncrement(&srwlock_base_errors.wrong_execution_order);
2216  pReleaseSRWLockExclusive(&srwlock_base);
2217 
2218  /* skip over remaining tests if TryAcquireSRWLock* is not available */
2219  if (!pTryAcquireSRWLockExclusive)
2220  return 0;
2221 
2222  /* seq 20 */
2223  while (srwlock_seq < 20) Sleep(1);
2224  if (pTryAcquireSRWLockShared(&srwlock_base))
2225  InterlockedIncrement(&srwlock_base_errors.trylock_shared);
2226  if (pTryAcquireSRWLockExclusive(&srwlock_base))
2228  if (InterlockedIncrement(&srwlock_seq) != 21)
2229  InterlockedIncrement(&srwlock_base_errors.wrong_execution_order);
2230 
2231  /* seq 22 */
2232  while (srwlock_seq < 22) Sleep(1);
2233  if (pTryAcquireSRWLockShared(&srwlock_base))
2234  pReleaseSRWLockShared(&srwlock_base);
2235  else
2236  InterlockedIncrement(&srwlock_base_errors.trylock_shared);
2237  if (pTryAcquireSRWLockExclusive(&srwlock_base))
2239  if (InterlockedIncrement(&srwlock_seq) != 23)
2240  InterlockedIncrement(&srwlock_base_errors.wrong_execution_order);
2241 
2242  /* seq 24 */
2243  while (srwlock_seq < 24) Sleep(1);
2244  Sleep(50); /* ensure that exclusive access request is queued */
2245  if (pTryAcquireSRWLockShared(&srwlock_base))
2246  {
2247  pReleaseSRWLockShared(&srwlock_base);
2248  InterlockedIncrement(&srwlock_base_errors.excl_not_preferred);
2249  }
2250  if (pTryAcquireSRWLockExclusive(&srwlock_base))
2252  if (InterlockedIncrement(&srwlock_seq) != 25)
2253  InterlockedIncrement(&srwlock_base_errors.wrong_execution_order);
2254  pReleaseSRWLockShared(&srwlock_base);
2255 
2256  /* seq 26 */
2257  while (srwlock_seq < 26) Sleep(1);
2258  if (pTryAcquireSRWLockShared(&srwlock_base))
2259  pReleaseSRWLockShared(&srwlock_base);
2260  else
2261  InterlockedIncrement(&srwlock_base_errors.trylock_shared);
2262  if (pTryAcquireSRWLockExclusive(&srwlock_base))
2264  if (InterlockedIncrement(&srwlock_seq) != 27)
2265  InterlockedIncrement(&srwlock_base_errors.wrong_execution_order);
2266 
2267  /* seq 28 */
2268  while (srwlock_seq < 28) Sleep(1);
2269  if (pTryAcquireSRWLockShared(&srwlock_base))
2270  pReleaseSRWLockShared(&srwlock_base);
2271  else
2272  InterlockedIncrement(&srwlock_base_errors.trylock_shared);
2273  if (pTryAcquireSRWLockExclusive(&srwlock_base))
2275  if (InterlockedIncrement(&srwlock_seq) != 29)
2276  InterlockedIncrement(&srwlock_base_errors.wrong_execution_order);
2277 
2278  /* seq 30 */
2279  while (srwlock_seq < 30) Sleep(1);
2280  if (pTryAcquireSRWLockShared(&srwlock_base))
2281  pReleaseSRWLockShared(&srwlock_base);
2282  else
2283  InterlockedIncrement(&srwlock_base_errors.trylock_shared);
2284  if (pTryAcquireSRWLockExclusive(&srwlock_base))
2285  pReleaseSRWLockExclusive(&srwlock_base);
2286  else
2288  if (InterlockedIncrement(&srwlock_seq) != 31)
2289  InterlockedIncrement(&srwlock_base_errors.wrong_execution_order);
2290 
2291  return 0;
2292 }
2293 
2295 {
2296  /* seq 15 */
2297  while (srwlock_seq < 15) Sleep(1);
2298  Sleep(50); /* some delay, so that thread2 can try to acquire a second exclusive lock */
2299  if (InterlockedIncrement(&srwlock_seq) != 16)
2300  InterlockedIncrement(&srwlock_base_errors.wrong_execution_order);
2301 
2302  /* seq 18 */
2303  pAcquireSRWLockShared(&srwlock_base);
2304  if (srwlock_seq != 18)
2305  InterlockedIncrement(&srwlock_base_errors.excl_not_preferred);
2306  pReleaseSRWLockShared(&srwlock_base);
2307  if (InterlockedIncrement(&srwlock_seq) != 19)
2308  InterlockedIncrement(&srwlock_base_errors.wrong_execution_order);
2309 
2310  /* skip over remaining tests if TryAcquireSRWLock* is not available */
2311  if (!pTryAcquireSRWLockExclusive)
2312  {
2313  /* function is only in Windows 7 and newer */
2314  win_skip("no srw trylock support.\n");
2315  srwlock_seq = 31; /* end */
2316  return 0;
2317  }
2318 
2319  return 0;
2320 }
2321 
2322 static void test_srwlock_base(void)
2323 {
2324  HANDLE h1, h2, h3;
2325  DWORD dummy;
2326 
2327  if (!pInitializeSRWLock)
2328  {
2329  /* function is not yet in XP, only in newer Windows */
2330  win_skip("no srw lock support.\n");
2331  return;
2332  }
2333 
2334  pInitializeSRWLock(&srwlock_base);
2336 
2340 
2341  srwlock_seq = 1; /* go */
2342  while (srwlock_seq < 31)
2343  Sleep(5);
2344 
2345  WaitForSingleObject(h1, 100);
2346  WaitForSingleObject(h2, 100);
2347  WaitForSingleObject(h3, 100);
2348 
2349  ok(!srwlock_base_errors.wrong_execution_order,
2350  "thread commands were executed in the wrong order (occurred %d times).\n",
2351  srwlock_base_errors.wrong_execution_order);
2352 
2353  ok(!srwlock_base_errors.samethread_excl_excl,
2354  "AcquireSRWLockExclusive didn't block when called multiple times from the same thread (occurred %d times).\n",
2355  srwlock_base_errors.samethread_excl_excl);
2356 
2357  ok(!srwlock_base_errors.samethread_excl_shared,
2358  "AcquireSRWLockShared didn't block when the same thread holds an exclusive lock (occurred %d times).\n",
2359  srwlock_base_errors.samethread_excl_shared);
2360 
2361  ok(!srwlock_base_errors.samethread_shared_excl,
2362  "AcquireSRWLockExclusive didn't block when the same thread holds a shared lock (occurred %d times).\n",
2363  srwlock_base_errors.samethread_shared_excl);
2364 
2365  ok(!srwlock_base_errors.multithread_excl_excl,
2366  "AcquireSRWLockExclusive didn't block when a second thread holds the exclusive lock (occurred %d times).\n",
2367  srwlock_base_errors.multithread_excl_excl);
2368 
2369  ok(!srwlock_base_errors.excl_not_preferred,
2370  "thread waiting for exclusive access to the SHMLock was not preferred (occurred %d times).\n",
2371  srwlock_base_errors.excl_not_preferred);
2372 
2373  ok(!srwlock_base_errors.trylock_excl,
2374  "TryAcquireSRWLockExclusive didn't behave as expected (occurred %d times).\n",
2375  srwlock_base_errors.trylock_excl);
2376 
2377  ok(!srwlock_base_errors.trylock_shared,
2378  "TryAcquireSRWLockShared didn't behave as expected (occurred %d times).\n",
2379  srwlock_base_errors.trylock_shared);
2380 
2381 }
2382 
2383 static SRWLOCK srwlock_example;
2387 
2389  DWORD *cnt = x;
2390  LONG old;
2391 
2392  while (!srwlock_stop)
2393  {
2394 
2395  /* periodically request exclusive access */
2396  if (InterlockedIncrement(&srwlock_cnt) % 13 == 0)
2397  {
2398  pAcquireSRWLockExclusive(&srwlock_example);
2401 
2403  Sleep(1);
2404 
2407  pReleaseSRWLockExclusive(&srwlock_example);
2408  }
2409 
2410  /* request shared access */
2411  pAcquireSRWLockShared(&srwlock_example);
2414 
2415  (*cnt)++;
2416  Sleep(1);
2417 
2418  if (old != srwlock_protected_value)
2421  pReleaseSRWLockShared(&srwlock_example);
2422  }
2423 
2424  return 0;
2425 }
2426 
2427 static void test_srwlock_example(void)
2428 {
2429  HANDLE h1, h2, h3;
2430  DWORD dummy;
2431  DWORD cnt1, cnt2, cnt3;
2432 
2433  if (!pInitializeSRWLock) {
2434  /* function is not yet in XP, only in newer Windows */
2435  win_skip("no srw lock support.\n");
2436  return;
2437  }
2438 
2439  pInitializeSRWLock(&srwlock_example);
2440 
2441  cnt1 = cnt2 = cnt3 = 0;
2442 
2443  h1 = CreateThread(NULL, 0, srwlock_example_thread, &cnt1, 0, &dummy);
2444  h2 = CreateThread(NULL, 0, srwlock_example_thread, &cnt2, 0, &dummy);
2445  h3 = CreateThread(NULL, 0, srwlock_example_thread, &cnt3, 0, &dummy);
2446 
2447  /* limit run to 1 second. */
2448  Sleep(1000);
2449 
2450  /* tear down start */
2451  srwlock_stop = TRUE;
2452 
2453  WaitForSingleObject(h1, 1000);
2454  WaitForSingleObject(h2, 1000);
2455  WaitForSingleObject(h3, 1000);
2456 
2457  ok(!srwlock_inside, "threads didn't terminate properly, srwlock_inside is %d.\n", srwlock_inside);
2458  ok(!srwlock_example_errors, "errors occurred while running SRWLock example test (number of errors: %d)\n",
2460 
2461  trace("number of shared accesses per thread are c1 %d, c2 %d, c3 %d\n", cnt1, cnt2, cnt3);
2462  trace("number of total exclusive accesses is %d\n", srwlock_protected_value);
2463 }
2464 
2466 {
2467  HANDLE *semaphores = param;
2469  NTSTATUS status;
2470  DWORD result;
2471 
2472  ReleaseSemaphore(semaphores[0], 1, NULL);
2473  result = WaitForMultipleObjectsEx(1, &semaphores[1], TRUE, 1000, TRUE);
2474  ok(result == WAIT_IO_COMPLETION, "expected WAIT_IO_COMPLETION, got %u\n", result);
2475  result = WaitForMultipleObjectsEx(1, &semaphores[1], TRUE, 200, TRUE);
2476  ok(result == WAIT_OBJECT_0, "expected WAIT_OBJECT_0, got %u\n", result);
2477 
2478  ReleaseSemaphore(semaphores[0], 1, NULL);
2479  timeout.QuadPart = -10000000;
2480  status = pNtWaitForMultipleObjects(1, &semaphores[1], FALSE, TRUE, &timeout);
2481  ok(status == STATUS_USER_APC, "expected STATUS_USER_APC, got %08x\n", status);
2482  timeout.QuadPart = -2000000;
2483  status = pNtWaitForMultipleObjects(1, &semaphores[1], FALSE, TRUE, &timeout);
2484  ok(status == STATUS_WAIT_0, "expected STATUS_WAIT_0, got %08x\n", status);
2485 
2486  ReleaseSemaphore(semaphores[0], 1, NULL);
2487  timeout.QuadPart = -10000000;
2488  status = pNtWaitForMultipleObjects(1, &semaphores[1], FALSE, TRUE, &timeout);
2489  ok(status == STATUS_USER_APC, "expected STATUS_USER_APC, got %08x\n", status);
2490  result = WaitForSingleObject(semaphores[0], 0);
2491  ok(result == WAIT_TIMEOUT, "expected WAIT_TIMEOUT, got %u\n", result);
2492 
2493  return 0;
2494 }
2495 
2497 {
2498  HANDLE *semaphores = (void *)userdata;
2499  ReleaseSemaphore(semaphores[1], 1, NULL);
2500 }
2501 
2503 {
2504  HANDLE *semaphores = (void *)userdata;
2505  DWORD result;
2506 
2507  result = WaitForSingleObject(semaphores[0], 1000);
2508  ok(result == WAIT_OBJECT_0, "expected WAIT_OBJECT_0, got %u\n", result);
2509 }
2510 
2511 static void test_alertable_wait(void)
2512 {
2513  HANDLE thread, semaphores[2];
2514  DWORD result;
2515 
2516  semaphores[0] = CreateSemaphoreW(NULL, 0, 2, NULL);
2517  ok(semaphores[0] != NULL, "CreateSemaphore failed with %u\n", GetLastError());
2518  semaphores[1] = CreateSemaphoreW(NULL, 0, 1, NULL);
2519  ok(semaphores[1] != NULL, "CreateSemaphore failed with %u\n", GetLastError());
2520  thread = CreateThread(NULL, 0, alertable_wait_thread, semaphores, 0, NULL);
2521  ok(thread != NULL, "CreateThread failed with %u\n", GetLastError());
2522 
2523  result = WaitForSingleObject(semaphores[0], 1000);
2524  ok(result == WAIT_OBJECT_0, "expected WAIT_OBJECT_0, got %u\n", result);
2525  Sleep(100); /* ensure the thread is blocking in WaitForMultipleObjectsEx */
2527  ok(result != 0, "QueueUserAPC failed with %u\n", GetLastError());
2528 
2529  result = WaitForSingleObject(semaphores[0], 1000);
2530  ok(result == WAIT_OBJECT_0, "expected WAIT_OBJECT_0, got %u\n", result);
2531  Sleep(100); /* ensure the thread is blocking in NtWaitForMultipleObjects */
2533  ok(result != 0, "QueueUserAPC failed with %u\n", GetLastError());
2534 
2535  result = WaitForSingleObject(semaphores[0], 1000);
2536  ok(result == WAIT_OBJECT_0, "expected WAIT_OBJECT_0, got %u\n", result);
2537  Sleep(100); /* ensure the thread is blocking in NtWaitForMultipleObjects */
2539  ok(result != 0, "QueueUserAPC failed with %u\n", GetLastError());
2541  ok(result != 0, "QueueUserAPC failed with %u\n", GetLastError());
2542  ReleaseSemaphore(semaphores[0], 2, NULL);
2543 
2545  ok(result == WAIT_OBJECT_0, "expected WAIT_OBJECT_0, got %u\n", result);
2547  CloseHandle(semaphores[0]);
2548  CloseHandle(semaphores[1]);
2549 }
2550 
2552 {
2556 };
2557 
2559 {
2560  struct apc_deadlock_info *info = param;
2561  PROCESS_INFORMATION *pi = info->pi;
2562  NTSTATUS status;
2563  SIZE_T size;
2564  void *base;
2565 
2566  while (info->running)
2567  {
2568  base = NULL;
2569  size = 0x1000;
2570  status = pNtAllocateVirtualMemory(pi->hProcess, &base, 0, &size,
2573  ok(!status, "expected STATUS_SUCCESS, got %08x\n", status);
2574  ok(base != NULL, "expected base != NULL, got %p\n", base);
2575  SetEvent(info->event);
2576 
2577  size = 0;
2578  status = pNtFreeVirtualMemory(pi->hProcess, &base, &size, MEM_RELEASE);
2580  ok(!status, "expected STATUS_SUCCESS, got %08x\n", status);
2581  SetEvent(info->event);
2582  }
2583 
2584  return 0;
2585 }
2586 
2587 static void test_apc_deadlock(void)
2588 {
2589  struct apc_deadlock_info info;
2591  STARTUPINFOA si = { sizeof(si) };
2592  char cmdline[MAX_PATH];
2593  HANDLE event, thread;
2594  DWORD result;
2595  BOOL success;
2596  char **argv;
2597  int i;
2598 
2600  sprintf(cmdline, "\"%s\" sync apc_deadlock", argv[0]);
2601  success = CreateProcessA(argv[0], cmdline, NULL, NULL, FALSE, 0, NULL, NULL, &si, &pi);
2602  ok(success, "CreateProcess failed with %u\n", GetLastError());
2603 
2604  event = CreateEventA(NULL, FALSE, FALSE, NULL);
2605  ok(event != NULL, "CreateEvent failed with %u\n", GetLastError());
2606 
2607  info.pi = &pi;
2608  info.event = event;
2609  info.running = TRUE;
2610 
2612  ok(thread != NULL, "CreateThread failed with %u\n", GetLastError());
2613  result = WaitForSingleObject(event, 1000);
2614  ok(result == WAIT_OBJECT_0, "expected WAIT_OBJECT_0, got %u\n", result);
2615 
2617  for (i = 0; i < 1000; i++)
2618  {
2619  result = SuspendThread(pi.hThread);
2620  ok(result == 0, "expected 0, got %u\n", result);
2621 
2622  WaitForSingleObject(event, 0); /* reset event */
2623  result = WaitForSingleObject(event, 1000);
2624  ok(result == WAIT_OBJECT_0, "expected WAIT_OBJECT_0, got %u\n", result);
2625 
2626  result = ResumeThread(pi.hThread);
2627  ok(result == 1, "expected 1, got %u\n", result);
2628  Sleep(1);
2629  }
2630 
2631  info.running = FALSE;
2633  ok(result == WAIT_OBJECT_0, "expected WAIT_OBJECT_0, got %u\n", result);
2635  CloseHandle(event);
2636 
2637  TerminateProcess(pi.hProcess, 0);
2638  CloseHandle(pi.hThread);
2639  CloseHandle(pi.hProcess);
2640 }
2641 
2643 {
2644  char **argv;
2645  int argc;
2646  HMODULE hdll = GetModuleHandleA("kernel32.dll");
2647  HMODULE hntdll = GetModuleHandleA("ntdll.dll");
2648 #ifdef __REACTOS__
2649  HMODULE hdll_vista = GetModuleHandleA("kernel32_vista.dll");
2650 #endif
2651 
2652  pInitOnceInitialize = (void *)GetProcAddress(hdll, "InitOnceInitialize");
2653  pInitOnceExecuteOnce = (void *)GetProcAddress(hdll, "InitOnceExecuteOnce");
2654  pInitOnceBeginInitialize = (void *)GetProcAddress(hdll, "InitOnceBeginInitialize");
2655  pInitOnceComplete = (void *)GetProcAddress(hdll, "InitOnceComplete");
2656  pInitializeConditionVariable = (void *)GetProcAddress(hdll, "InitializeConditionVariable");
2657  pSleepConditionVariableCS = (void *)GetProcAddress(hdll, "SleepConditionVariableCS");
2658  pSleepConditionVariableSRW = (void *)GetProcAddress(hdll, "SleepConditionVariableSRW");
2659  pWakeAllConditionVariable = (void *)GetProcAddress(hdll, "WakeAllConditionVariable");
2660  pWakeConditionVariable = (void *)GetProcAddress(hdll, "WakeConditionVariable");
2661  pInitializeSRWLock = (void *)GetProcAddress(hdll, "InitializeSRWLock");
2662  pAcquireSRWLockExclusive = (void *)GetProcAddress(hdll, "AcquireSRWLockExclusive");
2663  pAcquireSRWLockShared = (void *)GetProcAddress(hdll, "AcquireSRWLockShared");
2664  pReleaseSRWLockExclusive = (void *)GetProcAddress(hdll, "ReleaseSRWLockExclusive");
2665  pReleaseSRWLockShared = (void *)GetProcAddress(hdll, "ReleaseSRWLockShared");
2666  pTryAcquireSRWLockExclusive = (void *)GetProcAddress(hdll, "TryAcquireSRWLockExclusive");
2667  pTryAcquireSRWLockShared = (void *)GetProcAddress(hdll, "TryAcquireSRWLockShared");
2668  pNtAllocateVirtualMemory = (void *)GetProcAddress(hntdll, "NtAllocateVirtualMemory");
2669  pNtFreeVirtualMemory = (void *)GetProcAddress(hntdll, "NtFreeVirtualMemory");
2670  pNtWaitForSingleObject = (void *)GetProcAddress(hntdll, "NtWaitForSingleObject");
2671  pNtWaitForMultipleObjects = (void *)GetProcAddress(hntdll, "NtWaitForMultipleObjects");
2672  pRtlInterlockedPushListSList = (void *)GetProcAddress(hntdll, "RtlInterlockedPushListSList");
2673  pRtlInterlockedPushListSListEx = (void *)GetProcAddress(hntdll, "RtlInterlockedPushListSListEx");
2674 
2675 #ifdef __REACTOS__
2676  if (!pInitializeConditionVariable)
2677  {
2678  pInitializeConditionVariable = (void *)GetProcAddress(hdll_vista, "InitializeConditionVariable");
2679  pSleepConditionVariableCS = (void *)GetProcAddress(hdll_vista, "SleepConditionVariableCS");
2680  pSleepConditionVariableSRW = (void *)GetProcAddress(hdll_vista, "SleepConditionVariableSRW");
2681  pWakeAllConditionVariable = (void *)GetProcAddress(hdll_vista, "WakeAllConditionVariable");
2682  pWakeConditionVariable = (void *)GetProcAddress(hdll_vista, "WakeConditionVariable");
2683  }
2684 
2685  if (!pInitializeSRWLock)
2686  {
2687  pInitializeSRWLock = (void *)GetProcAddress(hdll_vista, "InitializeSRWLock");
2688  pAcquireSRWLockExclusive = (void *)GetProcAddress(hdll_vista, "AcquireSRWLockExclusive");
2689  pAcquireSRWLockShared = (void *)GetProcAddress(hdll_vista, "AcquireSRWLockShared");
2690  pReleaseSRWLockExclusive = (void *)GetProcAddress(hdll_vista, "ReleaseSRWLockExclusive");
2691  pReleaseSRWLockShared = (void *)GetProcAddress(hdll_vista, "ReleaseSRWLockShared");
2692  pTryAcquireSRWLockExclusive = (void *)GetProcAddress(hdll_vista, "TryAcquireSRWLockExclusive");
2693  pTryAcquireSRWLockShared = (void *)GetProcAddress(hdll_vista, "TryAcquireSRWLockShared");
2694  }
2695 #endif
2696 
2698  if (argc >= 3)
2699  {
2700  if (!strcmp(argv[2], "apc_deadlock"))
2701  {
2702  for (;;) SleepEx(INFINITE, TRUE);
2703  }
2704  return;
2705  }
2706 
2709  test_mutex();
2710  test_slist();
2711  test_event();
2712  test_semaphore();
2715  test_timer_queue();
2718  test_initonce();
2725 }
LONG excl_not_preferred
Definition: sync.c:1948
static void CALLBACK timer_queue_cb3(PVOID p, BOOLEAN timedOut)
Definition: sync.c:806
#define ERROR_INVALID_PARAMETER
Definition: compat.h:91
static CRITICAL_SECTION condvar_crit
Definition: sync.c:1728
GLenum func
Definition: glext.h:6028
static const WCHAR invalid[]
Definition: assoc.c:39
static const LARGE_INTEGER *static const HANDLE const LARGE_INTEGER *static PSLIST_ENTRY PSLIST_ENTRY ULONG count
Definition: sync.c:65
BOOL WINAPI WriteFile(IN HANDLE hFile, IN LPCVOID lpBuffer, IN DWORD nNumberOfBytesToWrite OPTIONAL, OUT LPDWORD lpNumberOfBytesWritten, IN LPOVERLAPPED lpOverlapped OPTIONAL)
Definition: rw.c:24
static void test_semaphore(void)
Definition: sync.c:582
static int argc
Definition: ServiceArgs.c:12
#define ULongToHandle(h)
Definition: basetsd.h:81
static void test_event(void)
Definition: sync.c:469
namespace GUID const ADDRINFOEXW ADDRINFOEXW struct timeval OVERLAPPED LPLOOKUPSERVICE_COMPLETION_ROUTINE HANDLE * handle
Definition: sock.c:82
#define TRUE
Definition: types.h:120
#define CloseHandle
Definition: compat.h:407
VOID WINAPI DECLSPEC_HOTPATCH Sleep(IN DWORD dwMilliseconds)
Definition: synch.c:790
static LONG srwlock_cnt
Definition: sync.c:2385
static void * g_initctxt
Definition: sync.c:1351
static void test_slist(void)
Definition: sync.c:298
static DWORD WINAPI alertable_wait_thread(void *param)
Definition: sync.c:2465
static LONG srwlock_example_errors
Definition: sync.c:2385
#define DWORD_PTR
Definition: treelist.c:76
#define ACCESS_SYSTEM_SECURITY
Definition: nt_native.h:77
#define ERROR_PRIVILEGE_NOT_HELD
Definition: winerror.h:796
BOOL WINAPI InitializeAcl(PACL pAcl, DWORD nAclLength, DWORD dwAclRevision)
Definition: security.c:885
HANDLE WINAPI DECLSPEC_HOTPATCH CreateSemaphoreW(IN LPSECURITY_ATTRIBUTES lpSemaphoreAttributes OPTIONAL, IN LONG lInitialCount, IN LONG lMaximumCount, IN LPCWSTR lpName OPTIONAL)
Definition: synch.c:444
static BOOL(WINAPI *pQueryMemoryResourceNotification)(HANDLE
Definition: cproxy.c:247
static CONDITION_VARIABLE condvar_base
Definition: sync.c:1727
#define __fastcall
Definition: sync.c:38
HANDLE WINAPI DECLSPEC_HOTPATCH CreateSemaphoreA(IN LPSECURITY_ATTRIBUTES lpSemaphoreAttributes OPTIONAL, IN LONG lInitialCount, IN LONG lMaximumCount, IN LPCSTR lpName OPTIONAL)
Definition: synch.c:430
#define ERROR_TIMEOUT
Definition: winerror.h:941
static BOOL srwlock_stop
Definition: sync.c:2386
static SRWLOCK condvar_srwlock
Definition: sync.c:1729
GLdouble GLdouble GLdouble r
Definition: gl.h:2055
static LONG condvar_consumer_sleepcnt
Definition: sync.c:1599
#define MAXIMUM_WAIT_OBJECTS
Definition: winbase.h:385
BOOL WINAPI InitializeSecurityDescriptor(PSECURITY_DESCRIPTOR pSecurityDescriptor, DWORD dwRevision)
Definition: security.c:808
_In_ CLIPOBJ _In_ BRUSHOBJ _In_ LONG x1
Definition: winddi.h:3706
#define ERROR_INVALID_HANDLE
Definition: compat.h:88
static void CALLBACK timer_queue_cb1(PVOID p, BOOLEAN timedOut)
Definition: sync.c:775
LONG NTSTATUS
Definition: precomp.h:26
#define CALLBACK
Definition: compat.h:27
static LONG srwlock_inside
Definition: sync.c:2385
static LONG srwlock_seq
Definition: sync.c:1939
GLdouble GLdouble t
Definition: gl.h:2047
static void test_alertable_wait(void)
Definition: sync.c:2511
#define INVALID_HANDLE_VALUE
Definition: compat.h:400
static HANDLE(WINAPI *pCreateMemoryResourceNotification)(MEMORY_RESOURCE_NOTIFICATION_TYPE)
BOOL WINAPI DECLSPEC_HOTPATCH SetEvent(IN HANDLE hEvent)
Definition: synch.c:733
#define INIT_ONCE_ASYNC
Definition: winbase.h:3776
DWORD WINAPI GetLastError(VOID)
Definition: except.c:1059
#define HandleToULong(h)
Definition: basetsd.h:95
GLuint buffer
Definition: glext.h:5915
GLint GLint GLint GLint GLint x
Definition: gl.h:1548
HANDLE WINAPI OpenWaitableTimerW(IN DWORD dwDesiredAccess, IN BOOL bInheritHandle, IN LPCWSTR lpTimerName)
Definition: synch.c:358
static NTSTATUS(WINAPI *pNtAllocateVirtualMemory)(HANDLE
static BOOL condvar_stop
Definition: sync.c:1597
static LONG bufferlen
Definition: sync.c:1598
Definition: dhcpd.h:245
static const LARGE_INTEGER *static const HANDLE const LARGE_INTEGER *static PSLIST_ENTRY PSLIST_ENTRY last
Definition: sync.c:65
TCHAR * cmdline
Definition: stretchblt.cpp:32
void WINAPI EnterCriticalSection(LPCRITICAL_SECTION)
static void test_signalandwait(void)
Definition: sync.c:108
#define argv
Definition: mplay32.c:18
HANDLE WINAPI DECLSPEC_HOTPATCH OpenMutexA(IN DWORD dwDesiredAccess, IN BOOL bInheritHandle, IN LPCSTR lpName)
Definition: synch.c:592
const char * filename
Definition: ioapi.h:135
#define ERROR_IO_PENDING
Definition: dderror.h:15
DWORD WINAPI WaitForMultipleObjects(IN DWORD nCount, IN CONST HANDLE *lpHandles, IN BOOL bWaitAll, IN DWORD dwMilliseconds)
Definition: synch.c:151
#define MEM_COMMIT
Definition: nt_native.h:1313
#define QueryDepthSList(SListHead)
Definition: rtlfuncs.h:3402
LONG samethread_shared_excl
Definition: sync.c:1946
static LONG totalconsumed
Definition: sync.c:1598
GLbitfield GLuint64 timeout
Definition: glext.h:7164
HANDLE WINAPI OpenWaitableTimerA(IN DWORD dwDesiredAccess, IN BOOL bInheritHandle, IN LPCSTR lpTimerName)
Definition: synch.c:370
#define STATUS_INVALID_HANDLE
Definition: ntstatus.h:231
static PBOOL
Definition: sync.c:41
PSLIST_ENTRY WINAPI InterlockedPopEntrySList(PSLIST_HEADER ListHead)
Definition: interlocked.c:55
static void test_iocp_callback(void)
Definition: sync.c:683
HANDLE WINAPI DECLSPEC_HOTPATCH CreateEventW(IN LPSECURITY_ATTRIBUTES lpEventAttributes OPTIONAL, IN BOOL bManualReset, IN BOOL bInitialState, IN LPCWSTR lpName OPTIONAL)
Definition: synch.c:651
HANDLE q
Definition: sync.c:787
HANDLE WINAPI DECLSPEC_HOTPATCH OpenEventW(IN DWORD dwDesiredAccess, IN BOOL bInheritHandle, IN LPCWSTR lpName)
Definition: synch.c:682
uint32_t ULONG_PTR
Definition: typedefs.h:64
static void test_WaitForMultipleObjects(void)
Definition: sync.c:1274
static const struct metadata_item item3[]
Definition: metadata.c:2814
#define SECURITY_DESCRIPTOR_REVISION
Definition: setypes.h:58
#define sprintf(buf, format,...)
Definition: sprintf.c:55
#define STATUS_TIMEOUT
Definition: ntstatus.h:81
static BOOL CALLBACK initonce_callback(INIT_ONCE *initonce, void *parameter, void **ctxt)
Definition: sync.c:1353
static ULONG
Definition: sync.c:49
DWORD WINAPI WaitForSingleObject(IN HANDLE hHandle, IN DWORD dwMilliseconds)
Definition: synch.c:82
static const LARGE_INTEGER *static const HANDLE const LARGE_INTEGER *static PSLIST_ENTRY(__fastcall *pRtlInterlockedPushListSList)(PSLIST_HEADER list
HANDLE FileHandle
Definition: stats.c:38
DWORD WINAPI QueueUserAPC(IN PAPCFUNC pfnAPC, IN HANDLE hThread, IN ULONG_PTR dwData)
Definition: thread.c:947
GLsizei GLenum const GLvoid GLsizei GLenum GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLint GLint GLint GLshort GLshort GLshort GLubyte GLubyte GLubyte GLuint GLuint GLuint GLushort GLushort GLushort GLbyte GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLfloat GLint GLint GLint GLint GLshort GLshort GLshort GLshort GLubyte GLubyte GLubyte GLubyte GLuint GLuint GLuint GLuint GLushort GLushort GLushort GLushort GLboolean const GLdouble const GLfloat const GLint const GLshort const GLbyte const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLdouble const GLfloat const GLfloat const GLint const GLint const GLshort const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort GLenum GLenum GLenum GLfloat GLenum GLint GLenum GLenum GLenum GLfloat GLenum GLenum GLint GLenum GLfloat GLenum GLint GLint GLushort GLenum GLenum GLfloat GLenum GLenum GLint GLfloat const GLubyte GLenum GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLint GLint GLsizei GLsizei GLint GLenum GLenum const GLvoid GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLenum const GLdouble GLenum GLenum const GLfloat GLenum GLenum const GLint GLsizei GLuint GLfloat GLuint GLbitfield GLfloat GLint GLuint GLboolean GLenum GLfloat GLenum GLbitfield GLenum GLfloat GLfloat GLint GLint const GLfloat GLenum GLfloat GLfloat GLint GLint GLfloat GLfloat GLint GLint const GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat const GLdouble const GLfloat const GLdouble const GLfloat GLint i
Definition: glfuncs.h:248
static SRWLOCK srwlock_base
Definition: sync.c:1940
#define STATUS_WAIT_0
Definition: ntstatus.h:223
LPVOID NTAPI VirtualAlloc(IN LPVOID lpAddress, IN SIZE_T dwSize, IN DWORD flAllocationType, IN DWORD flProtect)
Definition: virtmem.c:74
static LPOVERLAPPED_COMPLETION_ROUTINE Function
Definition: sync.c:681
HANDLE WINAPI GetCurrentThread(VOID)
Definition: proc.c:1148
#define ERROR_ACCESS_DENIED
Definition: compat.h:87
static const LARGE_INTEGER *static const HANDLE const LARGE_INTEGER *static PSLIST_ENTRY first
Definition: sync.c:65
unsigned int BOOL
Definition: ntddk_ex.h:94
GLuint base
Definition: 3dtext.c:35
long LONG
Definition: pedump.c:60
HANDLE WINAPI DECLSPEC_HOTPATCH OpenEventA(IN DWORD dwDesiredAccess, IN BOOL bInheritHandle, IN LPCSTR lpName)
Definition: synch.c:669
#define e
Definition: ke_i.h:82
static PINIT_ONCE_FN
Definition: sync.c:43
static void CALLBACK timer_queue_cb4(PVOID p, BOOLEAN timedOut)
Definition: sync.c:819
#define INIT_ONCE_INIT_FAILED
Definition: winbase.h:3777
#define EVENT_ALL_ACCESS
Definition: isotest.c:82
static LONG srwlock_protected_value
Definition: sync.c:2384
#define GENERIC_WRITE
Definition: nt_native.h:90
#define MEM_RESERVE
Definition: nt_native.h:1314
HANDLE event
Definition: sync.c:2554
static DWORD WINAPI srwlock_base_thread2(LPVOID x)
Definition: sync.c:2151
static PSRWLOCK
Definition: sync.c:49
static void test_condvars_base(void)
Definition: sync.c:1886
HANDLE WINAPI DECLSPEC_HOTPATCH OpenMutexW(IN DWORD dwDesiredAccess, IN BOOL bInheritHandle, IN LPCWSTR lpName)
Definition: synch.c:605
DWORD WINAPI SignalObjectAndWait(IN HANDLE hObjectToSignal, IN HANDLE hObjectToWaitOn, IN DWORD dwMilliseconds, IN BOOL bAlertable)
Definition: synch.c:269
unsigned char BOOLEAN
static DWORD WINAPI condvar_consumer(LPVOID x)
Definition: sync.c:1631
HANDLE WINAPI DECLSPEC_HOTPATCH CreateThread(IN LPSECURITY_ATTRIBUTES lpThreadAttributes, IN DWORD dwStackSize, IN LPTHREAD_START_ROUTINE lpStartAddress, IN LPVOID lpParameter, IN DWORD dwCreationFlags, OUT LPDWORD lpThreadId)
Definition: thread.c:136
HANDLE WINAPI CreateTimerQueue(VOID)
Definition: timerqueue.c:117
VOID WINAPI InitializeCriticalSection(OUT LPCRITICAL_SECTION lpCriticalSection)
Definition: synch.c:751
smooth NULL
Definition: ftsmooth.c:416
LONG trylock_shared
Definition: sync.c:1950
static void CALLBACK alertable_wait_apc2(ULONG_PTR userdata)
Definition: sync.c:2502
HANDLE t
Definition: sync.c:787
BOOL WINAPI DeleteFileA(IN LPCSTR lpFileName)
Definition: delete.c:24
static void test_srwlock_example(void)
Definition: sync.c:2427
static VOID(WINAPI *pInitOnceInitialize)(PINIT_ONCE)
HANDLE WINAPI DECLSPEC_HOTPATCH CreateEventA(IN LPSECURITY_ATTRIBUTES lpEventAttributes OPTIONAL, IN BOOL bManualReset, IN BOOL bInitialState, IN LPCSTR lpName OPTIONAL)
Definition: synch.c:637
#define ERROR_NOT_OWNER
Definition: winerror.h:301
#define WAIT_IO_COMPLETION
Definition: winbase.h:392
#define ERROR_FILE_NOT_FOUND
Definition: disk.h:79
PFLT_MESSAGE_WAITER_QUEUE CONTAINING_RECORD(Csq, DEVICE_EXTENSION, IrpQueue)) -> WaiterQ.mLock) _IRQL_raises_(DISPATCH_LEVEL) VOID NTAPI FltpAcquireMessageWaiterLock(_In_ PIO_CSQ Csq, _Out_ PKIRQL Irql)
Definition: Messaging.c:560
static void test_initonce(void)
Definition: sync.c:1363
FORCEINLINE VOID InitializeSListHead(_Out_ PSLIST_HEADER SListHead)
Definition: rtlfuncs.h:3353
GLuint GLfloat * val
Definition: glext.h:7180
static DWORD WINAPI condvar_base_consumer(LPVOID x)
Definition: sync.c:1803
static int pints_t pn[]
Definition: server.c:129
static BOOL g_initcallback_called
Definition: sync.c:1350
#define call_func4(func, a, b, c, d)
Definition: sync.c:104
HANDLE semaphore
Definition: loader.c:2140
GLboolean GLboolean GLboolean b
Definition: glext.h:6204
#define WT_EXECUTELONGFUNCTION
Definition: winnt_old.h:1076
DWORD WINAPI SleepEx(IN DWORD dwMilliseconds, IN BOOL bAlertable)
Definition: synch.c:802
static void test_waitable_timer(void)
Definition: sync.c:628
#define WAIT_OBJECT_0
Definition: winbase.h:387
GLsizeiptr size
Definition: glext.h:5919
#define init_fastcall_thunk()
Definition: sync.c:103
static void test_WaitForSingleObject(void)
Definition: sync.c:1181
#define GetProcessHeap()
Definition: compat.h:404
#define trace
Definition: atltest.h:70
PVOID WINAPI HeapAlloc(HANDLE, DWORD, SIZE_T)
#define d
Definition: ke_i.h:81
HANDLE WINAPI CreateWaitableTimerA(IN LPSECURITY_ATTRIBUTES lpTimerAttributes OPTIONAL, IN BOOL bManualReset, IN LPCSTR lpTimerName OPTIONAL)
Definition: synch.c:346
int n3
Definition: dwarfget.c:148
static LPVOID *static BOOL LPVOID *static LPVOID
Definition: sync.c:45
static refpint_t pi[]
Definition: server.c:96
#define TIMER_ALL_ACCESS
Definition: extypes.h:116
static struct @1640 srwlock_base_errors
DWORD WINAPI WaitForMultipleObjectsEx(IN DWORD nCount, IN CONST HANDLE *lpHandles, IN BOOL bWaitAll, IN DWORD dwMilliseconds, IN BOOL bAlertable)
Definition: synch.c:169
HANDLE WINAPI GetCurrentProcess(VOID)
Definition: proc.c:1138
static const struct metadata_item item2[]
Definition: metadata.c:2807
BOOL WINAPI DECLSPEC_HOTPATCH CreateProcessA(LPCSTR lpApplicationName, LPSTR lpCommandLine, LPSECURITY_ATTRIBUTES lpProcessAttributes, LPSECURITY_ATTRIBUTES lpThreadAttributes, BOOL bInheritHandles, DWORD dwCreationFlags, LPVOID lpEnvironment, LPCSTR lpCurrentDirectory, LPSTARTUPINFOA lpStartupInfo, LPPROCESS_INFORMATION lpProcessInformation)
Definition: proc.c:4744
#define InterlockedFlushSList(SListHead)
Definition: rtlfuncs.h:3397
GLfloat param
Definition: glext.h:5796
#define MAX_PATH
Definition: compat.h:26
#define WINAPI
Definition: msvc.h:6
const char file[]
Definition: icontest.c:11
static PVOID
Definition: sync.c:43
const GLubyte * c
Definition: glext.h:8905
#define FILE_FLAG_DELETE_ON_CLOSE
Definition: disk.h:42
unsigned short WORD
Definition: ntddk_ex.h:93
BOOL WINAPI ChangeTimerQueueTimer(IN HANDLE TimerQueue, IN HANDLE Timer, IN ULONG DueTime, IN ULONG Period)
Definition: timerqueue.c:82
unsigned long DWORD
Definition: ntddk_ex.h:95
#define WAIT_FAILED
Definition: winbase.h:394
#define disable_success_count
Definition: test.h:170
#define success(from, fromstr, to, tostr)
#define SetLastError(x)
Definition: compat.h:418
int n1
Definition: dwarfget.c:148
GLdouble GLdouble GLdouble GLdouble q
Definition: gl.h:2063
PRTL_RUN_ONCE PINIT_ONCE
Definition: winbase.h:3772
int winetest_get_mainargs(char ***pargv)
#define WAIT_TIMEOUT
Definition: dderror.h:14
#define READ_CONTROL
Definition: nt_native.h:58
static CONDITION_VARIABLE buffernotfull
Definition: sync.c:1595
BOOL WINAPI DECLSPEC_HOTPATCH ReleaseMutex(IN HANDLE hMutex)
Definition: synch.c:618
static HANDLE thread
Definition: service.c:33
static const WCHAR sd[]
Definition: suminfo.c:287
static HANDLE modify_handle(HANDLE handle, DWORD modify)
Definition: sync.c:1174
void sync()
Definition: prep.c:9
int ret
static LPVOID *static DWORD
Definition: sync.c:44
#define FILE_ATTRIBUTE_NORMAL
Definition: compat.h:126
static LONG condvar_producer_sleepcnt
Definition: sync.c:1599
DWORD WINAPI SuspendThread(IN HANDLE hThread)
Definition: thread.c:641
static DWORD WINAPI condvar_base_producer(LPVOID x)
Definition: sync.c:1750
#define todo_wine
Definition: test.h:162
#define InterlockedDecrement
Definition: armddk.h:52
static DWORD WINAPI apc_deadlock_thread(void *param)
Definition: sync.c:2558
static void test_timer_queue(void)
Definition: sync.c:878
uint32_t entry
Definition: isohybrid.c:63
HMODULE WINAPI DECLSPEC_HOTPATCH GetModuleHandleA(LPCSTR lpModuleName)
Definition: loader.c:812
#define BUFFER_SIZE
Definition: sync.c:1601
#define GENERIC_READ
Definition: compat.h:124
PROCESS_INFORMATION * pi
Definition: sync.c:2553
NTKERNELAPI PSLIST_ENTRY FASTCALL InterlockedPushEntrySList(IN PSLIST_HEADER ListHead, IN PSLIST_ENTRY ListEntry)
Definition: interlocked.c:82
struct _cl_event * event
Definition: glext.h:7739
uint32_t DWORD_PTR
Definition: typedefs.h:64
_In_ HANDLE hFile
Definition: mswsock.h:90
GLsizei const GLfloat * value
Definition: glext.h:6069
static DWORD WINAPI srwlock_base_thread1(LPVOID x)
Definition: sync.c:2024
unsigned char BYTE
Definition: xxhash.c:193
#define broken(x)
Definition: _sntprintf.h:21
static PEXPLICIT_ACCESSW *static HMODULE hmod
Definition: security.c:141
void(CALLBACK * LPOVERLAPPED_COMPLETION_ROUTINE)(DWORD, DWORD, LPOVERLAPPED)
Definition: winbase.h:1417
GLenum GLsizei GLuint GLint * bytesWritten
Definition: glext.h:11123
LONG wrong_execution_order
Definition: sync.c:1943
#define INIT_ONCE_CHECK_ONLY
Definition: winbase.h:3775
#define STATUS_USER_APC
Definition: ntstatus.h:78
ULONG_PTR SIZE_T
Definition: typedefs.h:79
namespace GUID const ADDRINFOEXW ADDRINFOEXW struct timeval OVERLAPPED * overlapped
Definition: sock.c:82
#define CREATE_ALWAYS
Definition: disk.h:72
static BOOL g_initcallback_ret
Definition: sync.c:1350
#define InterlockedIncrement
Definition: armddk.h:53
static ATOM item
Definition: dde.c:856
int n2
Definition: dwarfget.c:148
_In_ HANDLE _In_ DWORD _In_ DWORD _Inout_opt_ LPOVERLAPPED lpOverlapped
Definition: mswsock.h:90
DWORD WINAPI GetTempPathA(IN DWORD nBufferLength, OUT LPSTR lpBuffer)
Definition: path.c:2053
unsigned short USHORT
Definition: pedump.c:61
static HANDLE sem
Definition: sync.c:674
unsigned char dummy
Definition: maze.c:118
static DWORD condvar_seq
Definition: sync.c:1726
BOOL WINAPI TerminateProcess(IN HANDLE hProcess, IN UINT uExitCode)
Definition: proc.c:1532
#define ok(value,...)
Definition: atltest.h:57
static void CALLBACK iocp_callback(DWORD dwErrorCode, DWORD dwNumberOfBytesTransferred, LPOVERLAPPED lpOverlapped)
Definition: sync.c:676
static void test_mutex(void)
Definition: sync.c:186
#define list
Definition: rosglue.h:35
BOOL WINAPI DeleteTimerQueueTimer(IN HANDLE TimerQueue, IN HANDLE Timer, IN HANDLE CompletionEvent)
Definition: timerqueue.c:240
int n4
Definition: dwarfget.c:148
static SRWLOCK srwlock_example
Definition: sync.c:2383
BOOL WINAPI SetSecurityDescriptorDacl(PSECURITY_DESCRIPTOR pSecurityDescriptor, BOOL bDaclPresent, PACL pDacl, BOOL bDaclDefaulted)
Definition: sec.c:262
static PVOID hdll
Definition: shimdbg.c:126
static void test_apc_deadlock(void)
Definition: sync.c:2587
static CONDITION_VARIABLE buffernotempty
Definition: sync.c:1594
BOOL WINAPI DECLSPEC_HOTPATCH ResetEvent(IN HANDLE hEvent)
Definition: synch.c:714
static HINSTANCE hntdll
Definition: process.c:66
BOOL WINAPI DECLSPEC_HOTPATCH ReleaseSemaphore(IN HANDLE hSemaphore, IN LONG lReleaseCount, IN LPLONG lpPreviousCount)
Definition: synch.c:542
_In_ CLIPOBJ _In_ BRUSHOBJ _In_ LONG _In_ LONG _In_ LONG x2
Definition: winddi.h:3706
int n5
Definition: dwarfget.c:148
LONG samethread_excl_shared
Definition: sync.c:1945
#define SLIST_ENTRY(type)
Definition: queue.h:102
#define skip(...)
Definition: atltest.h:64
#define ACL_REVISION
Definition: setypes.h:39
LONG samethread_excl_excl
Definition: sync.c:1944
#define MEM_RELEASE
Definition: nt_native.h:1316
static DWORD WINAPI condvar_producer(LPVOID x)
Definition: sync.c:1603
static void CALLBACK alertable_wait_apc(ULONG_PTR userdata)
Definition: sync.c:2496
static void CALLBACK timer_queue_cb5(PVOID p, BOOLEAN timedOut)
Definition: sync.c:836
DWORD WINAPI ResumeThread(IN HANDLE hThread)
Definition: thread.c:566
HANDLE WINAPI DECLSPEC_HOTPATCH OpenSemaphoreA(IN DWORD dwDesiredAccess, IN BOOL bInheritHandle, IN LPCSTR lpName)
Definition: synch.c:516
unsigned int ULONG
Definition: retypes.h:1
static void CALLBACK timer_queue_cb6(PVOID p, BOOLEAN timedOut)
Definition: sync.c:844
int strcmp(const char *String1, const char *String2)
Definition: utclib.c:469
HANDLE WINAPI DECLSPEC_HOTPATCH CreateMutexA(IN LPSECURITY_ATTRIBUTES lpMutexAttributes OPTIONAL, IN BOOL bInitialOwner, IN LPCSTR lpName OPTIONAL)
Definition: synch.c:563
#define GetProcAddress(x, y)
Definition: compat.h:419
LONG trylock_excl
Definition: sync.c:1949
static CRITICAL_SECTION buffercrit
Definition: sync.c:1596
START_TEST(sync)
Definition: sync.c:2642
LONG multithread_excl_excl
Definition: sync.c:1947
static const struct metadata_item item1[]
Definition: metadata.c:2802
BOOL WINAPI DeleteTimerQueueEx(IN HANDLE TimerQueue, IN HANDLE CompletionEvent)
Definition: timerqueue.c:205
#define PAGE_EXECUTE_READWRITE
Definition: nt_native.h:1308
#define ERROR_ALREADY_EXISTS
Definition: disk.h:80
BOOL WINAPI CreateTimerQueueTimer(OUT PHANDLE phNewTimer, IN HANDLE TimerQueue, IN WAITORTIMERCALLBACK Callback, IN PVOID Parameter, IN DWORD DueTime, IN DWORD Period, IN ULONG Flags)
Definition: timerqueue.c:138
#define ERROR_GEN_FAILURE
Definition: winerror.h:134
void WINAPI LeaveCriticalSection(LPCRITICAL_SECTION)
static BOOL condvar_sleeperr
Definition: sync.c:1597
#define CreateFileA(a, b, c, d, e, f, g)
Definition: compat.h:408
GLboolean GLboolean GLboolean GLboolean a
Definition: glext.h:6204
static LONG totalproduced
Definition: sync.c:1598
GLfloat GLfloat p
Definition: glext.h:8902
#define FILE_FLAG_OVERLAPPED
Definition: disk.h:46
#define INFINITE
Definition: serial.h:102
#define GENERIC_EXECUTE
Definition: nt_native.h:91
GLuint64EXT * result
Definition: glext.h:11304
#define memset(x, y, z)
Definition: compat.h:39
static DWORD WINAPI srwlock_base_thread3(LPVOID x)
Definition: sync.c:2294
static SERVICE_STATUS status
Definition: service.c:31
#define SEMAPHORE_ALL_ACCESS
Definition: winbase.h:160
static DWORD WINAPI srwlock_example_thread(LPVOID x)
Definition: sync.c:2388
#define win_skip
Definition: test.h:149
UINT WINAPI GetTempFileNameA(IN LPCSTR lpPathName, IN LPCSTR lpPrefixString, IN UINT uUnique, OUT LPSTR lpTempFileName)
Definition: filename.c:26
#define HeapFree(x, y, z)
Definition: compat.h:403
static void CALLBACK timer_queue_cb2(PVOID p, BOOLEAN timedOut)
Definition: sync.c:790
static PCRITICAL_SECTION
Definition: sync.c:48
static void test_srwlock_base(void)
Definition: sync.c:2322
static struct sockaddr_in sa
Definition: adnsresfilter.c:69
HANDLE WINAPI DECLSPEC_HOTPATCH OpenSemaphoreW(IN DWORD dwDesiredAccess, IN BOOL bInheritHandle, IN LPCWSTR lpName)
Definition: synch.c:529
static void test_condvars_consumer_producer(void)
Definition: sync.c:1659
static LPOVERLAPPED_COMPLETION_ROUTINE ULONG Flags
Definition: sync.c:681
#define FILE_FLAG_RANDOM_ACCESS
Definition: disk.h:44
#define PAGE_READWRITE
Definition: nt_native.h:1304
static BOOLEAN
Definition: sync.c:63
Definition: fci.c:126
char temp_path[MAX_PATH]
Definition: mspatcha.c:123
Definition: ps.c:97