Misha Koshelev : kernel32: Added conformance test for nested thread wakeups in the server.

Alexandre Julliard julliard at wine.codeweavers.com
Mon Feb 5 15:25:34 CST 2007


Module: wine
Branch: master
Commit: d6d6ce299f3558a30cc5e09c8fe669f1be45a330
URL:    http://source.winehq.org/git/wine.git/?a=commit;h=d6d6ce299f3558a30cc5e09c8fe669f1be45a330

Author: Misha Koshelev <mk144210 at bcm.tmc.edu>
Date:   Sat Feb  3 13:26:29 2007 -0600

kernel32: Added conformance test for nested thread wakeups in the server.

---

 dlls/kernel32/tests/change.c |   46 ++++++++++++++++++++++++++++++++++++++++++
 1 files changed, 46 insertions(+), 0 deletions(-)

diff --git a/dlls/kernel32/tests/change.c b/dlls/kernel32/tests/change.c
index bf7cdc1..0774caf 100644
--- a/dlls/kernel32/tests/change.c
+++ b/dlls/kernel32/tests/change.c
@@ -317,6 +317,48 @@ static void test_ffcn(void)
     ok( r == TRUE, "failed to remove dir\n");
 }
 
+/* this test concentrates on the wait behavior when multiple threads are
+ * waiting on a change notification handle. */
+static void test_ffcnMultipleThreads()
+{
+    LONG r;
+    DWORD filter, threadId, status, exitcode;
+    HANDLE handles[2];
+    char path[MAX_PATH];
+
+    r = GetTempPathA(MAX_PATH, path);
+    ok(r, "GetTempPathA error: %d\n", GetLastError());
+
+    lstrcatA(path, "ffcnTestMultipleThreads");
+
+    RemoveDirectoryA(path);
+
+    r = CreateDirectoryA(path, NULL);
+    ok(r, "CreateDirectoryA error: %d\n", GetLastError());
+
+    filter = FILE_NOTIFY_CHANGE_FILE_NAME;
+    filter |= FILE_NOTIFY_CHANGE_DIR_NAME;
+
+    handles[0] = FindFirstChangeNotificationA(path, FALSE, filter);
+    ok(handles[0] != INVALID_HANDLE_VALUE, "FindFirstChangeNotification error: %d\n", GetLastError());
+
+    /* Test behavior if a waiting thread holds the last reference to a change
+     * directory object with an empty wine user APC queue for this thread (bug #7286) */
+
+    /* Create our notification thread */
+    handles[1] = CreateThread(NULL, 0, NotificationThread, (LPVOID)handles[0],
+                              0, &threadId);
+    ok(handles[1] != NULL, "CreateThread error: %d\n", GetLastError());
+
+    status = WaitForMultipleObjects(2, handles, FALSE, 5000);
+    ok(status == WAIT_OBJECT_0 || status == WAIT_OBJECT_0+1, "WaitForMultipleObjects status %d error %d\n", status, GetLastError());
+    ok(GetExitCodeThread(handles[1], &exitcode), "Could not retrieve thread exit code\n");
+
+    /* Clean up */
+    r = RemoveDirectoryA( path );
+    ok( r == TRUE, "failed to remove dir\n");
+}
+
 typedef BOOL (WINAPI *fnReadDirectoryChangesW)(HANDLE,LPVOID,DWORD,BOOL,DWORD,
                          LPDWORD,LPOVERLAPPED,LPOVERLAPPED_COMPLETION_ROUTINE);
 fnReadDirectoryChangesW pReadDirectoryChangesW;
@@ -708,6 +750,10 @@ START_TEST(change)
     pReadDirectoryChangesW = (fnReadDirectoryChangesW)
         GetProcAddress(hkernel32, "ReadDirectoryChangesW");
 
+    test_ffcnMultipleThreads();
+    /* The above function runs a test that must occur before FindCloseChangeNotification is run in the
+       current thread to preserve the emptiness of the wine user APC queue. To ensure this it should be
+       placed first. */
     test_FindFirstChangeNotification();
     test_ffcn();
     test_readdirectorychanges();




More information about the wine-cvs mailing list