[PATCH 2/2] msi: Add support for ARPNOMODIFY, APRNOREMOVE and ARPNOREPAIR.

Hans Leidekker hans at codeweavers.com
Thu Sep 27 08:00:31 CDT 2018


Signed-off-by: Hans Leidekker <hans at codeweavers.com>
---
 dlls/msi/action.c       | 66 ++++++++++++++++++++++++++++++++++++-------------
 dlls/msi/tests/action.c | 51 +++++++++++++++++++++++---------------
 2 files changed, 80 insertions(+), 37 deletions(-)

diff --git a/dlls/msi/action.c b/dlls/msi/action.c
index 0d6da3e2cc..f2a038bc41 100644
--- a/dlls/msi/action.c
+++ b/dlls/msi/action.c
@@ -5177,19 +5177,8 @@ static UINT ACTION_UnpublishFeatures(MSIPACKAGE *package)
 
 static UINT msi_publish_install_properties(MSIPACKAGE *package, HKEY hkey)
 {
-    SYSTEMTIME systime;
-    DWORD size, langid;
-    WCHAR date[9], *val, *buffer;
-    const WCHAR *prop, *key;
-
-    static const WCHAR date_fmt[] = {'%','i','%','0','2','i','%','0','2','i',0};
-    static const WCHAR modpath_fmt[] =
-        {'M','s','i','E','x','e','c','.','e','x','e',' ',
-         '/','I','[','P','r','o','d','u','c','t','C','o','d','e',']',0};
-    static const WCHAR szModifyPath[] =
-        {'M','o','d','i','f','y','P','a','t','h',0};
-    static const WCHAR szUninstallString[] =
-        {'U','n','i','n','s','t','a','l','l','S','t','r','i','n','g',0};
+    static const WCHAR date_fmt[] =
+        {'%','i','%','0','2','i','%','0','2','i',0};
     static const WCHAR szEstimatedSize[] =
         {'E','s','t','i','m','a','t','e','d','S','i','z','e',0};
     static const WCHAR szDisplayVersion[] =
@@ -5246,6 +5235,18 @@ static UINT msi_publish_install_properties(MSIPACKAGE *package, HKEY hkey)
         {'A','R','P','S','Y','S','T','E','M','C','O','M','P','O','N','E','N','T',0};
     static const WCHAR szSystemComponent[] =
         {'S','y','s','t','e','m','C','o','m','p','o','n','e','n','t',0};
+    static const WCHAR szARPNOMODIFY[] =
+        {'A','R','P','N','O','M','O','D','I','F','Y',0};
+    static const WCHAR szNoModify[] =
+        {'N','o','M','o','d','i','f','y',0};
+    static const WCHAR szARPNOREMOVE[] =
+        {'A','R','P','N','O','R','E','M','O','V','E',0};
+    static const WCHAR szNoRemove[] =
+        {'N','o','R','e','m','o','v','e',0};
+    static const WCHAR szARPNOREPAIR[] =
+        {'A','R','P','N','O','R','E','P','A','I','R',0};
+    static const WCHAR szNoRepair[] =
+        {'N','o','R','e','p','a','i','r',0};
 
     static const WCHAR *propval[] = {
         szARPAUTHORIZEDCDFPREFIX, szAuthorizedCDFPrefix,
@@ -5264,6 +5265,10 @@ static UINT msi_publish_install_properties(MSIPACKAGE *package, HKEY hkey)
         NULL
     };
     const WCHAR **p = propval;
+    SYSTEMTIME systime;
+    DWORD size, langid;
+    WCHAR date[9], *val, *buffer;
+    const WCHAR *prop, *key;
 
     while (*p)
     {
@@ -5279,10 +5284,37 @@ static UINT msi_publish_install_properties(MSIPACKAGE *package, HKEY hkey)
     {
         msi_reg_set_val_dword( hkey, szSystemComponent, 1 );
     }
-    size = deformat_string(package, modpath_fmt, &buffer) * sizeof(WCHAR);
-    RegSetValueExW(hkey, szModifyPath, 0, REG_EXPAND_SZ, (LPBYTE)buffer, size);
-    RegSetValueExW(hkey, szUninstallString, 0, REG_EXPAND_SZ, (LPBYTE)buffer, size);
-    msi_free(buffer);
+
+    if (msi_get_property_int( package->db, szARPNOREMOVE, 0 ))
+        msi_reg_set_val_dword( hkey, szNoRemove, 1 );
+    else
+    {
+        static const WCHAR fmt_install[] =
+            {'M','s','i','E','x','e','c','.','e','x','e',' ',
+             '/','I','[','P','r','o','d','u','c','t','C','o','d','e',']',0};
+        static const WCHAR fmt_uninstall[] =
+            {'M','s','i','E','x','e','c','.','e','x','e',' ',
+             '/','X','[','P','r','o','d','u','c','t','C','o','d','e',']',0};
+        static const WCHAR szModifyPath[] =
+            {'M','o','d','i','f','y','P','a','t','h',0};
+        static const WCHAR szUninstallString[] =
+            {'U','n','i','n','s','t','a','l','l','S','t','r','i','n','g',0};
+        const WCHAR *fmt = fmt_install;
+
+        if (msi_get_property_int( package->db, szARPNOREPAIR, 0 ))
+            msi_reg_set_val_dword( hkey, szNoRepair, 1 );
+
+        if (msi_get_property_int( package->db, szARPNOMODIFY, 0 ))
+        {
+            msi_reg_set_val_dword( hkey, szNoModify, 1 );
+            fmt = fmt_uninstall;
+        }
+
+        size = deformat_string(package, fmt, &buffer) * sizeof(WCHAR);
+        RegSetValueExW(hkey, szModifyPath, 0, REG_EXPAND_SZ, (LPBYTE)buffer, size);
+        RegSetValueExW(hkey, szUninstallString, 0, REG_EXPAND_SZ, (LPBYTE)buffer, size);
+        msi_free(buffer);
+    }
 
     /* FIXME: Write real Estimated Size when we have it */
     msi_reg_set_val_dword(hkey, szEstimatedSize, 0);
diff --git a/dlls/msi/tests/action.c b/dlls/msi/tests/action.c
index 084dbe4532..951b89cad2 100644
--- a/dlls/msi/tests/action.c
+++ b/dlls/msi/tests/action.c
@@ -182,6 +182,7 @@ static const char property_dat[] =
     "SERVDISP\tTestServiceDisp\n"
     "SERVDISP2\tTestServiceDisp2\n"
     "MSIFASTINSTALL\t1\n"
+    "ARPNOMODIFY\t1\n"
     "regdata17\t#1\n";
 
 static const char env_install_exec_seq_dat[] =
@@ -2677,15 +2678,16 @@ static void test_register_product(void)
     CHECK_DEL_REG_STR(hkey, "DisplayVersion", "1.1.1");
     CHECK_DEL_REG_STR(hkey, "InstallDate", date);
     CHECK_DEL_REG_STR(hkey, "InstallSource", temp);
-    CHECK_DEL_REG_ISTR(hkey, "ModifyPath", "MsiExec.exe /I{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
+    CHECK_DEL_REG_ISTR(hkey, "ModifyPath", "MsiExec.exe /X{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
     CHECK_DEL_REG_STR(hkey, "Publisher", "Wine");
-    CHECK_DEL_REG_STR(hkey, "UninstallString", "MsiExec.exe /I{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
+    CHECK_DEL_REG_STR(hkey, "UninstallString", "MsiExec.exe /X{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
     CHECK_DEL_REG_STR(hkey, "AuthorizedCDFPrefix", NULL);
     CHECK_DEL_REG_STR(hkey, "Comments", NULL);
     CHECK_DEL_REG_STR(hkey, "Contact", NULL);
     CHECK_DEL_REG_STR(hkey, "HelpLink", NULL);
     CHECK_DEL_REG_STR(hkey, "HelpTelephone", NULL);
     CHECK_DEL_REG_STR(hkey, "InstallLocation", NULL);
+    CHECK_DEL_REG_DWORD(hkey, "NoModify", 1);
     CHECK_DEL_REG_STR(hkey, "Readme", NULL);
     CHECK_DEL_REG_STR(hkey, "Size", NULL);
     CHECK_DEL_REG_STR(hkey, "URLInfoAbout", NULL);
@@ -2718,15 +2720,16 @@ static void test_register_product(void)
     CHECK_DEL_REG_STR(props, "DisplayVersion", "1.1.1");
     CHECK_DEL_REG_STR(props, "InstallDate", date);
     CHECK_DEL_REG_STR(props, "InstallSource", temp);
-    CHECK_DEL_REG_ISTR(props, "ModifyPath", "MsiExec.exe /I{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
+    CHECK_DEL_REG_ISTR(props, "ModifyPath", "MsiExec.exe /X{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
     CHECK_DEL_REG_STR(props, "Publisher", "Wine");
-    CHECK_DEL_REG_STR(props, "UninstallString", "MsiExec.exe /I{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
+    CHECK_DEL_REG_STR(props, "UninstallString", "MsiExec.exe /X{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
     CHECK_DEL_REG_STR(props, "AuthorizedCDFPrefix", NULL);
     CHECK_DEL_REG_STR(props, "Comments", NULL);
     CHECK_DEL_REG_STR(props, "Contact", NULL);
     CHECK_DEL_REG_STR(props, "HelpLink", NULL);
     CHECK_DEL_REG_STR(props, "HelpTelephone", NULL);
     CHECK_DEL_REG_STR(props, "InstallLocation", NULL);
+    CHECK_DEL_REG_DWORD(props, "NoModify", 1);
     CHECK_DEL_REG_STR(props, "Readme", NULL);
     CHECK_DEL_REG_STR(props, "Size", NULL);
     CHECK_DEL_REG_STR(props, "URLInfoAbout", NULL);
@@ -2782,15 +2785,16 @@ todo_wine
     CHECK_DEL_REG_STR(hkey, "DisplayVersion", "1.1.1");
     CHECK_DEL_REG_STR(hkey, "InstallDate", date);
     CHECK_DEL_REG_STR(hkey, "InstallSource", temp);
-    CHECK_DEL_REG_ISTR(hkey, "ModifyPath", "MsiExec.exe /I{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
+    CHECK_DEL_REG_ISTR(hkey, "ModifyPath", "MsiExec.exe /X{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
     CHECK_DEL_REG_STR(hkey, "Publisher", "Wine");
-    CHECK_DEL_REG_STR(hkey, "UninstallString", "MsiExec.exe /I{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
+    CHECK_DEL_REG_STR(hkey, "UninstallString", "MsiExec.exe /X{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
     CHECK_DEL_REG_STR(hkey, "AuthorizedCDFPrefix", NULL);
     CHECK_DEL_REG_STR(hkey, "Comments", NULL);
     CHECK_DEL_REG_STR(hkey, "Contact", NULL);
     CHECK_DEL_REG_STR(hkey, "HelpLink", NULL);
     CHECK_DEL_REG_STR(hkey, "HelpTelephone", NULL);
     CHECK_DEL_REG_STR(hkey, "InstallLocation", NULL);
+    CHECK_DEL_REG_DWORD(hkey, "NoModify", 1);
     CHECK_DEL_REG_STR(hkey, "Readme", NULL);
     CHECK_DEL_REG_STR(hkey, "Size", NULL);
     CHECK_DEL_REG_STR(hkey, "URLInfoAbout", NULL);
@@ -2823,15 +2827,16 @@ todo_wine
     CHECK_DEL_REG_STR(props, "DisplayVersion", "1.1.1");
     CHECK_DEL_REG_STR(props, "InstallDate", date);
     CHECK_DEL_REG_STR(props, "InstallSource", temp);
-    CHECK_DEL_REG_ISTR(props, "ModifyPath", "MsiExec.exe /I{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
+    CHECK_DEL_REG_ISTR(props, "ModifyPath", "MsiExec.exe /X{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
     CHECK_DEL_REG_STR(props, "Publisher", "Wine");
-    CHECK_DEL_REG_STR(props, "UninstallString", "MsiExec.exe /I{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
+    CHECK_DEL_REG_STR(props, "UninstallString", "MsiExec.exe /X{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
     CHECK_DEL_REG_STR(props, "AuthorizedCDFPrefix", NULL);
     CHECK_DEL_REG_STR(props, "Comments", NULL);
     CHECK_DEL_REG_STR(props, "Contact", NULL);
     CHECK_DEL_REG_STR(props, "HelpLink", NULL);
     CHECK_DEL_REG_STR(props, "HelpTelephone", NULL);
     CHECK_DEL_REG_STR(props, "InstallLocation", NULL);
+    CHECK_DEL_REG_DWORD(props, "NoModify", 1);
     CHECK_DEL_REG_STR(props, "Readme", NULL);
     CHECK_DEL_REG_STR(props, "Size", NULL);
     CHECK_DEL_REG_STR(props, "URLInfoAbout", NULL);
@@ -3693,15 +3698,16 @@ static void test_publish(void)
     CHECK_REG_STR(prodkey, "DisplayVersion", "1.1.1");
     CHECK_REG_STR(prodkey, "InstallDate", date);
     CHECK_REG_STR(prodkey, "InstallSource", temp);
-    CHECK_REG_ISTR(prodkey, "ModifyPath", "MsiExec.exe /I{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
+    CHECK_REG_ISTR(prodkey, "ModifyPath", "MsiExec.exe /X{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
     CHECK_REG_STR(prodkey, "Publisher", "Wine");
-    CHECK_REG_STR(prodkey, "UninstallString", "MsiExec.exe /I{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
+    CHECK_REG_STR(prodkey, "UninstallString", "MsiExec.exe /X{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
     CHECK_REG_STR(prodkey, "AuthorizedCDFPrefix", NULL);
     CHECK_REG_STR(prodkey, "Comments", NULL);
     CHECK_REG_STR(prodkey, "Contact", NULL);
     CHECK_REG_STR(prodkey, "HelpLink", NULL);
     CHECK_REG_STR(prodkey, "HelpTelephone", NULL);
     CHECK_REG_STR(prodkey, "InstallLocation", NULL);
+    CHECK_REG_DWORD(prodkey, "NoModify", 1);
     CHECK_REG_STR(prodkey, "Readme", NULL);
     CHECK_REG_STR(prodkey, "Size", NULL);
     CHECK_REG_STR(prodkey, "URLInfoAbout", NULL);
@@ -3797,15 +3803,16 @@ static void test_publish(void)
     CHECK_REG_STR(prodkey, "DisplayVersion", "1.1.1");
     CHECK_REG_STR(prodkey, "InstallDate", date);
     CHECK_REG_STR(prodkey, "InstallSource", temp);
-    CHECK_REG_ISTR(prodkey, "ModifyPath", "MsiExec.exe /I{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
+    CHECK_REG_ISTR(prodkey, "ModifyPath", "MsiExec.exe /X{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
     CHECK_REG_STR(prodkey, "Publisher", "Wine");
-    CHECK_REG_STR(prodkey, "UninstallString", "MsiExec.exe /I{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
+    CHECK_REG_STR(prodkey, "UninstallString", "MsiExec.exe /X{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
     CHECK_REG_STR(prodkey, "AuthorizedCDFPrefix", NULL);
     CHECK_REG_STR(prodkey, "Comments", NULL);
     CHECK_REG_STR(prodkey, "Contact", NULL);
     CHECK_REG_STR(prodkey, "HelpLink", NULL);
     CHECK_REG_STR(prodkey, "HelpTelephone", NULL);
     CHECK_REG_STR(prodkey, "InstallLocation", NULL);
+    CHECK_REG_DWORD(prodkey, "NoModify", 1);
     CHECK_REG_STR(prodkey, "Readme", NULL);
     CHECK_REG_STR(prodkey, "Size", NULL);
     CHECK_REG_STR(prodkey, "URLInfoAbout", NULL);
@@ -3878,15 +3885,16 @@ static void test_publish(void)
     CHECK_REG_STR(prodkey, "DisplayVersion", "1.1.1");
     CHECK_REG_STR(prodkey, "InstallDate", date);
     CHECK_REG_STR(prodkey, "InstallSource", temp);
-    CHECK_REG_ISTR(prodkey, "ModifyPath", "MsiExec.exe /I{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
+    CHECK_REG_ISTR(prodkey, "ModifyPath", "MsiExec.exe /X{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
     CHECK_REG_STR(prodkey, "Publisher", "Wine");
-    CHECK_REG_STR(prodkey, "UninstallString", "MsiExec.exe /I{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
+    CHECK_REG_STR(prodkey, "UninstallString", "MsiExec.exe /X{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
     CHECK_REG_STR(prodkey, "AuthorizedCDFPrefix", NULL);
     CHECK_REG_STR(prodkey, "Comments", NULL);
     CHECK_REG_STR(prodkey, "Contact", NULL);
     CHECK_REG_STR(prodkey, "HelpLink", NULL);
     CHECK_REG_STR(prodkey, "HelpTelephone", NULL);
     CHECK_REG_STR(prodkey, "InstallLocation", NULL);
+    CHECK_REG_DWORD(prodkey, "NoModify", 1);
     CHECK_REG_STR(prodkey, "Readme", NULL);
     CHECK_REG_STR(prodkey, "Size", NULL);
     CHECK_REG_STR(prodkey, "URLInfoAbout", NULL);
@@ -3936,15 +3944,16 @@ static void test_publish(void)
     CHECK_REG_STR(prodkey, "DisplayVersion", "1.1.1");
     CHECK_REG_STR(prodkey, "InstallDate", date);
     CHECK_REG_STR(prodkey, "InstallSource", temp);
-    CHECK_REG_ISTR(prodkey, "ModifyPath", "MsiExec.exe /I{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
+    CHECK_REG_ISTR(prodkey, "ModifyPath", "MsiExec.exe /X{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
     CHECK_REG_STR(prodkey, "Publisher", "Wine");
-    CHECK_REG_STR(prodkey, "UninstallString", "MsiExec.exe /I{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
+    CHECK_REG_STR(prodkey, "UninstallString", "MsiExec.exe /X{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
     CHECK_REG_STR(prodkey, "AuthorizedCDFPrefix", NULL);
     CHECK_REG_STR(prodkey, "Comments", NULL);
     CHECK_REG_STR(prodkey, "Contact", NULL);
     CHECK_REG_STR(prodkey, "HelpLink", NULL);
     CHECK_REG_STR(prodkey, "HelpTelephone", NULL);
     CHECK_REG_STR(prodkey, "InstallLocation", NULL);
+    CHECK_REG_DWORD(prodkey, "NoModify", 1);
     CHECK_REG_STR(prodkey, "Readme", NULL);
     CHECK_REG_STR(prodkey, "Size", NULL);
     CHECK_REG_STR(prodkey, "URLInfoAbout", NULL);
@@ -3994,15 +4003,16 @@ static void test_publish(void)
     CHECK_REG_STR(prodkey, "DisplayVersion", "1.1.1");
     CHECK_REG_STR(prodkey, "InstallDate", date);
     CHECK_REG_STR(prodkey, "InstallSource", temp);
-    CHECK_REG_ISTR(prodkey, "ModifyPath", "MsiExec.exe /I{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
+    CHECK_REG_ISTR(prodkey, "ModifyPath", "MsiExec.exe /X{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
     CHECK_REG_STR(prodkey, "Publisher", "Wine");
-    CHECK_REG_STR(prodkey, "UninstallString", "MsiExec.exe /I{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
+    CHECK_REG_STR(prodkey, "UninstallString", "MsiExec.exe /X{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
     CHECK_REG_STR(prodkey, "AuthorizedCDFPrefix", NULL);
     CHECK_REG_STR(prodkey, "Comments", NULL);
     CHECK_REG_STR(prodkey, "Contact", NULL);
     CHECK_REG_STR(prodkey, "HelpLink", NULL);
     CHECK_REG_STR(prodkey, "HelpTelephone", NULL);
     CHECK_REG_STR(prodkey, "InstallLocation", NULL);
+    CHECK_REG_DWORD(prodkey, "NoModify", 1);
     CHECK_REG_STR(prodkey, "Readme", NULL);
     CHECK_REG_STR(prodkey, "Size", NULL);
     CHECK_REG_STR(prodkey, "URLInfoAbout", NULL);
@@ -4075,15 +4085,16 @@ static void test_publish(void)
     CHECK_REG_STR(prodkey, "DisplayVersion", "1.1.1");
     CHECK_REG_STR(prodkey, "InstallDate", date);
     CHECK_REG_STR(prodkey, "InstallSource", temp);
-    CHECK_REG_ISTR(prodkey, "ModifyPath", "MsiExec.exe /I{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
+    CHECK_REG_ISTR(prodkey, "ModifyPath", "MsiExec.exe /X{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
     CHECK_REG_STR(prodkey, "Publisher", "Wine");
-    CHECK_REG_STR(prodkey, "UninstallString", "MsiExec.exe /I{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
+    CHECK_REG_STR(prodkey, "UninstallString", "MsiExec.exe /X{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
     CHECK_REG_STR(prodkey, "AuthorizedCDFPrefix", NULL);
     CHECK_REG_STR(prodkey, "Comments", NULL);
     CHECK_REG_STR(prodkey, "Contact", NULL);
     CHECK_REG_STR(prodkey, "HelpLink", NULL);
     CHECK_REG_STR(prodkey, "HelpTelephone", NULL);
     CHECK_REG_STR(prodkey, "InstallLocation", NULL);
+    CHECK_REG_DWORD(prodkey, "NoModify", 1);
     CHECK_REG_STR(prodkey, "Readme", NULL);
     CHECK_REG_STR(prodkey, "Size", NULL);
     CHECK_REG_STR(prodkey, "URLInfoAbout", NULL);
-- 
2.11.0




More information about the wine-devel mailing list