Paul Vriens : advapi32/service: Some 'refcount' tests.

Alexandre Julliard julliard at wine.codeweavers.com
Fri Jul 20 06:02:23 CDT 2007


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

Author: Paul Vriens <paul.vriens.wine at gmail.com>
Date:   Thu Jul 19 21:30:35 2007 +0200

advapi32/service: Some 'refcount' tests.

---

 dlls/advapi32/tests/service.c |   99 +++++++++++++++++++++++++++++++++++++++++
 1 files changed, 99 insertions(+), 0 deletions(-)

diff --git a/dlls/advapi32/tests/service.c b/dlls/advapi32/tests/service.c
index 0bdb0bf..5c9c663 100644
--- a/dlls/advapi32/tests/service.c
+++ b/dlls/advapi32/tests/service.c
@@ -517,6 +517,101 @@ static void test_sequence(void)
     CloseServiceHandle(scm_handle);
 }
 
+static void test_refcount(void)
+{
+    SC_HANDLE scm_handle, svc_handle1, svc_handle2, svc_handle3, svc_handle4, svc_handle5;
+    static const CHAR servicename         [] = "Winetest";
+    static const CHAR pathname            [] = "we_dont_care.exe";
+    BOOL ret;
+
+    /* Get a handle to the Service Control Manager */
+    SetLastError(0xdeadbeef);
+    scm_handle = OpenSCManagerA(NULL, NULL, GENERIC_ALL);
+    if (!scm_handle && (GetLastError() == ERROR_ACCESS_DENIED))
+    {
+        skip("Not enough rights to get a handle to the manager\n");
+        return;
+    }
+
+    /* Create a service */
+    svc_handle1 = CreateServiceA(scm_handle, servicename, NULL, GENERIC_ALL,
+                                 SERVICE_WIN32_OWN_PROCESS | SERVICE_INTERACTIVE_PROCESS,
+                                 SERVICE_DISABLED, 0, pathname, NULL, NULL, NULL, NULL, NULL);
+    ok(svc_handle1 != NULL, "Expected success\n");
+
+    /* Get a handle to this new service */
+    svc_handle2 = OpenServiceA(scm_handle, servicename, GENERIC_READ);
+    ok(svc_handle2 != NULL, "Expected success\n");
+
+    /* Get another handle to this new service */
+    svc_handle3 = OpenServiceA(scm_handle, servicename, GENERIC_READ);
+    ok(svc_handle3 != NULL, "Expected success\n");
+
+    /* Check if we can close the handle to the Service Control Manager */
+    ret = CloseServiceHandle(scm_handle);
+    ok(ret, "Expected success\n");
+
+    /* Get a new handle to the Service Control Manager */
+    scm_handle = OpenSCManagerA(NULL, NULL, GENERIC_ALL);
+    ok(scm_handle != NULL, "Expected success\n");
+
+    /* Get a handle to this new service */
+    svc_handle4 = OpenServiceA(scm_handle, servicename, GENERIC_ALL);
+    ok(svc_handle4 != NULL, "Expected success\n");
+
+    /* Delete the service */
+    ret = DeleteService(svc_handle4);
+    ok(ret, "Expected success\n");
+
+    /* We cannot create the same service again as it's still marked as 'being deleted'.
+     * The reason is that we still have 4 open handles to this service eventhough we
+     * closed the handle to the Service Control Manager in between.
+     */
+    SetLastError(0xdeadbeef);
+    svc_handle5 = CreateServiceA(scm_handle, servicename, NULL, GENERIC_ALL,
+                                 SERVICE_WIN32_OWN_PROCESS | SERVICE_INTERACTIVE_PROCESS,
+                                 SERVICE_DISABLED, 0, pathname, NULL, NULL, NULL, NULL, NULL);
+    todo_wine
+    {
+    ok(!svc_handle5, "Expected failure\n");
+    ok(GetLastError() == ERROR_SERVICE_MARKED_FOR_DELETE,
+       "Expected ERROR_SERVICE_MARKED_FOR_DELETE, got %d\n", GetLastError());
+    }
+
+    /* FIXME: Remove this when Wine is fixed */
+    if (svc_handle5)
+    {
+        DeleteService(svc_handle5);
+        CloseServiceHandle(svc_handle5);
+    }
+
+    /* Close all the handles to the service and try again */
+    ret = CloseServiceHandle(svc_handle4);
+    ok(ret, "Expected success\n");
+    ret = CloseServiceHandle(svc_handle3);
+    ok(ret, "Expected success\n");
+    ret = CloseServiceHandle(svc_handle2);
+    ok(ret, "Expected success\n");
+    ret = CloseServiceHandle(svc_handle1);
+    ok(ret, "Expected success\n");
+
+    /* We succeed now as all handles are closed (tested this also with a long SLeep() */
+    svc_handle5 = CreateServiceA(scm_handle, servicename, NULL, GENERIC_ALL,
+                                 SERVICE_WIN32_OWN_PROCESS | SERVICE_INTERACTIVE_PROCESS,
+                                 SERVICE_DISABLED, 0, pathname, NULL, NULL, NULL, NULL, NULL);
+    ok(svc_handle5 != NULL, "Expected success\n");
+
+    /* Delete the service */
+    ret = DeleteService(svc_handle5);
+    ok(ret, "Expected success\n");
+
+    /* Wait a while. Just in case one of the following tests does a CreateService again */
+    Sleep(1000);
+
+    CloseServiceHandle(svc_handle5);
+    CloseServiceHandle(scm_handle);
+}
+
 START_TEST(service)
 {
     SC_HANDLE scm_handle;
@@ -539,4 +634,8 @@ START_TEST(service)
     test_close();
     /* Test the creation, querying and deletion of a service */
     test_sequence();
+    /* The main reason for this test is to check if any refcounting is used
+     * and what the rules are
+     */
+    test_refcount();
 }




More information about the wine-cvs mailing list