msi 2: Store the CustomActionData for deferred custom actions

James Hawkins truiken at gmail.com
Sun Sep 3 22:13:46 CDT 2006


Hi,

This fixes bug 5918.  To pass data between the installer and custom
actions, the installer needs to set the property named
'InsertCustomActionNameHere' to whatever value they want
CustomActionData to contain and MSI will handle the details of setting
CustomActionData (which is one of only three properties that a custom
action can read).  With deferred actions, this CustomActionData value
needs to be stored and used whenever we decided to run the custom
action, because more than likely the 'InsertCustomActionNameHere'
property will be erased before we run the deferred custom action.
This patch prepends [CustomActionData] to the name of the deferred
custom action when storing the action.  We then check for this
whenever we run an action, and if it's set, we use that value for the
CustomActionData property.
http://bugs.winehq.org/show_bug.cgi?id=5918

Changelog:
* Store the CustomActionData for deferred custom actions.

 dlls/msi/custom.c |   48 +++++++++++++++++++++++++++++++++++++++++++++---
 1 files changed, 45 insertions(+), 3 deletions(-)

-- 
James Hawkins
-------------- next part --------------
diff --git a/dlls/msi/custom.c b/dlls/msi/custom.c
index 4c824bf..dad67a2 100644
--- a/dlls/msi/custom.c
+++ b/dlls/msi/custom.c
@@ -117,6 +117,31 @@ static BOOL check_execution_scheduling_o
     return TRUE;
 }
 
+/* stores the CustomActionData before the action:
+ *     [CustomActionData]Action
+ */
+LPWSTR msi_get_deferred_action(LPCWSTR action, LPWSTR actiondata)
+{
+    LPWSTR deferred;
+    DWORD len;
+
+    static const WCHAR begin[] = {'[',0};
+    static const WCHAR end[] = {']',0};
+
+    if (!actiondata)
+        return strdupW(action);
+
+    len = lstrlenW(action) + lstrlenW(actiondata) + 3;
+    deferred = msi_alloc(len * sizeof(WCHAR));
+
+    lstrcpyW(deferred, begin);
+    lstrcatW(deferred, actiondata);
+    lstrcatW(deferred, end);
+    lstrcatW(deferred, action);
+
+    return deferred;
+}
+
 UINT ACTION_CustomAction(MSIPACKAGE *package,LPCWSTR action, BOOL execute)
 {
     UINT rc = ERROR_SUCCESS;
@@ -128,8 +153,18 @@ UINT ACTION_CustomAction(MSIPACKAGE *pac
      '=',' ','\'','%','s','\'',0};
     UINT type;
     LPCWSTR source, target;
+    LPWSTR ptr, deferred_data = NULL;
+    LPWSTR action_copy = strdupW(action);
     WCHAR *deformated=NULL;
 
+    /* deferred action: [CustomActionData]Action */
+    if ((ptr = strchrW(action_copy, ']')))
+    {
+        deferred_data = action_copy + 1;
+        *ptr = '\0';
+        action = ptr + 1;
+    }
+
     row = MSI_QueryGetRecord( package->db, ExecSeqQuery, action );
     if (!row)
         return ERROR_CALL_NOT_IMPLEMENTED;
@@ -160,18 +195,22 @@ UINT ACTION_CustomAction(MSIPACKAGE *pac
         }
         if (!execute)
         {
+            LPWSTR actiondata = msi_dup_property(package, action);
+            LPWSTR deferred = msi_get_deferred_action(action, actiondata);
+
             if (type & msidbCustomActionTypeCommit)
             {
                 TRACE("Deferring Commit Action!\n");
-                schedule_action(package, COMMIT_SCRIPT, action);
+                schedule_action(package, COMMIT_SCRIPT, deferred);
             }
             else
             {
                 TRACE("Deferring Action!\n");
-                schedule_action(package, INSTALL_SCRIPT, action);
+                schedule_action(package, INSTALL_SCRIPT, deferred);
             }
 
             rc = ERROR_SUCCESS;
+            msi_free(deferred);
             goto end;
         }
         else
@@ -182,7 +221,9 @@ UINT ACTION_CustomAction(MSIPACKAGE *pac
             'C','u','s','t','o','m','A','c','t','i','o','n','D','a','t','a',0};
             static const WCHAR szBlank[] = {0};
             LPWSTR actiondata = msi_dup_property( package, action );
-            if (actiondata)
+            if (deferred_data)
+                MSI_SetPropertyW(package,szActionData,deferred_data);
+            else if (actiondata)
                 MSI_SetPropertyW(package,szActionData,actiondata);
             else
                 MSI_SetPropertyW(package,szActionData,szBlank);
@@ -235,6 +276,7 @@ UINT ACTION_CustomAction(MSIPACKAGE *pac
     }
 
 end:
+    msi_free(action_copy);
     msiobj_release(&row->hdr);
     return rc;
 }
-- 
1.4.2



More information about the wine-patches mailing list