msi: Don't fail if the service to start is already running.

Hans Leidekker hans at codeweavers.com
Mon Feb 1 02:55:08 CST 2010


See http://bugs.winehq.org/show_bug.cgi?id=15894
---
 dlls/msi/action.c        |    3 +-
 dlls/msi/tests/install.c |  100 ++++++++++++++++++++++++++++++++++++++++++++++
 2 files changed, 102 insertions(+), 1 deletions(-)

diff --git a/dlls/msi/action.c b/dlls/msi/action.c
index 0d765ea..462b9ff 100644
--- a/dlls/msi/action.c
+++ b/dlls/msi/action.c
@@ -4492,7 +4492,8 @@ static UINT ITERATE_StartService(MSIRECORD *rec, LPVOID param)
 
     vector = msi_service_args_to_vector(args, &numargs);
 
-    if (!StartServiceW(service, numargs, vector))
+    if (!StartServiceW(service, numargs, vector) &&
+        GetLastError() != ERROR_SERVICE_ALREADY_RUNNING)
     {
         ERR("Failed to start service %s (%u)\n", debugstr_w(name), GetLastError());
         goto done;
diff --git a/dlls/msi/tests/install.c b/dlls/msi/tests/install.c
index 3904185..5da3ed6 100644
--- a/dlls/msi/tests/install.c
+++ b/dlls/msi/tests/install.c
@@ -349,6 +349,29 @@ static const CHAR service_control_dat[] = "ServiceControl\tName\tEvent\tArgument
                                           "ServiceControl\tServiceControl\n"
                                           "ServiceControl\tTestService\t8\t\t0\tservice_comp";
 
+static const CHAR sss_service_control_dat[] = "ServiceControl\tName\tEvent\tArguments\tWait\tComponent_\n"
+                                              "s72\tl255\ti2\tL255\tI2\ts72\n"
+                                              "ServiceControl\tServiceControl\n"
+                                              "ServiceControl\tTermService\t1\t\t0\tservice_comp";
+
+static const CHAR sss_install_exec_seq_dat[] = "Action\tCondition\tSequence\n"
+                                               "s72\tS255\tI2\n"
+                                               "InstallExecuteSequence\tAction\n"
+                                               "CostFinalize\t\t1000\n"
+                                               "CostInitialize\t\t800\n"
+                                               "FileCost\t\t900\n"
+                                               "ResolveSource\t\t950\n"
+                                               "MoveFiles\t\t1700\n"
+                                               "InstallFiles\t\t4000\n"
+                                               "DuplicateFiles\t\t4500\n"
+                                               "WriteEnvironmentStrings\t\t4550\n"
+                                               "CreateShortcuts\t\t4600\n"
+                                               "StartServices\t\t5000\n"
+                                               "InstallFinalize\t\t6600\n"
+                                               "InstallInitialize\t\t1500\n"
+                                               "InstallValidate\t\t1400\n"
+                                               "LaunchConditions\t\t100\n";
+
 /* tables for test_continuouscabs */
 static const CHAR cc_component_dat[] = "Component\tComponentId\tDirectory_\tAttributes\tCondition\tKeyPath\n"
                                        "s72\tS38\ts72\ti2\tS255\tS72\n"
@@ -1812,6 +1835,19 @@ static const msi_table cf_tables[] =
     ADD_TABLE(property)
 };
 
+static const msi_table sss_tables[] =
+{
+    ADD_TABLE(component),
+    ADD_TABLE(directory),
+    ADD_TABLE(feature),
+    ADD_TABLE(feature_comp),
+    ADD_TABLE(file),
+    ADD_TABLE(sss_install_exec_seq),
+    ADD_TABLE(sss_service_control),
+    ADD_TABLE(media),
+    ADD_TABLE(property)
+};
+
 /* cabinet definitions */
 
 /* make the max size large so there is only one cab file */
@@ -7410,6 +7446,69 @@ static void test_create_folder(void)
     delete_test_files();
 }
 
+static void test_start_services(void)
+{
+    UINT r;
+    SC_HANDLE scm, service;
+    BOOL ret;
+    DWORD error = ERROR_SUCCESS;
+
+    scm = OpenSCManager(NULL, NULL, SC_MANAGER_ALL_ACCESS);
+    ok(scm != NULL, "Failed to open the SC Manager\n");
+
+    service = OpenService(scm, "TermService", SC_MANAGER_ALL_ACCESS);
+    ok(service != NULL, "Failed to open TermService\n");
+
+    ret = StartService(service, 0, NULL);
+    if (!ret && (error = GetLastError()) != ERROR_SERVICE_ALREADY_RUNNING)
+    {
+        skip("Terminal service not available, skipping test\n");
+        CloseServiceHandle(service);
+        CloseServiceHandle(scm);
+        return;
+    }
+
+    CloseServiceHandle(service);
+    CloseServiceHandle(scm);
+
+    create_test_files();
+    create_database(msifile, sss_tables, sizeof(sss_tables) / sizeof(msi_table));
+
+    MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
+
+    r = MsiInstallProductA(msifile, NULL);
+    ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
+
+    ok(delete_pf("msitest\\cabout\\new\\five.txt", TRUE), "File not installed\n");
+    ok(delete_pf("msitest\\cabout\\new", FALSE), "Directory not created\n");
+    ok(delete_pf("msitest\\cabout\\four.txt", TRUE), "File not installed\n");
+    ok(delete_pf("msitest\\cabout", FALSE), "Directory not created\n");
+    ok(delete_pf("msitest\\changed\\three.txt", TRUE), "File not installed\n");
+    ok(delete_pf("msitest\\changed", FALSE), "Directory not created\n");
+    ok(delete_pf("msitest\\first\\two.txt", TRUE), "File not installed\n");
+    ok(delete_pf("msitest\\first", FALSE), "Directory not created\n");
+    ok(delete_pf("msitest\\filename", TRUE), "File not installed\n");
+    ok(delete_pf("msitest\\one.txt", TRUE), "File not installed\n");
+    ok(delete_pf("msitest\\service.exe", TRUE), "File not installed\n");
+    ok(delete_pf("msitest", FALSE), "Directory not created\n");
+
+    delete_test_files();
+
+    if (error == ERROR_SUCCESS)
+    {
+        SERVICE_STATUS status;
+
+        scm = OpenSCManager(NULL, NULL, SC_MANAGER_ALL_ACCESS);
+        service = OpenService(scm, "TermService", SC_MANAGER_ALL_ACCESS);
+
+        ret = ControlService(service, SERVICE_CONTROL_STOP, &status);
+        ok(ret, "ControlService failed %u\n", GetLastError());
+
+        CloseServiceHandle(service);
+        CloseServiceHandle(scm);
+    }
+}
+
 START_TEST(install)
 {
     DWORD len;
@@ -7502,6 +7601,7 @@ START_TEST(install)
     test_allusers_prop();
     test_feature_override();
     test_create_folder();
+    test_start_services();
 
     DeleteFileA(log_file);
 
-- 
1.6.3.3




More information about the wine-patches mailing list