Clean up the elevation code for MSI transactions.
Sean Hall committed
Nov 15, 2020 at 20:23 UTC
846f5a033d346c1bac51c56d4936cd3118ebea7a
5 files changed
+213
-261
src/engine/apply.cpp
+82
-150
@@ -198,6 +198,19 @@ static HRESULT ExecuteCompatiblePackageAction(
198
__in BURN_ENGINE_STATE* pEngineState,
199
__in BURN_EXECUTE_ACTION* pAction
200
);
201
+static HRESULT ExecuteMsiBeginTransaction(
202
+ __in BURN_ENGINE_STATE* pEngineState,
203
+ __in LPCWSTR wzName,
204
+ __in BURN_EXECUTE_CONTEXT* pContext
205
+ );
206
+static HRESULT ExecuteMsiCommitTransaction(
207
+ __in BURN_ENGINE_STATE* pEngineState,
208
+ __in BURN_EXECUTE_CONTEXT* pContext
209
+ );
210
+static HRESULT ExecuteMsiRollbackTransaction(
211
+ __in BURN_ENGINE_STATE* pEngineState,
212
+ __in BURN_EXECUTE_CONTEXT* pContext
213
+ );
214
static HRESULT CleanPackage(
215
__in HANDLE hElevatedPipe,
216
__in BURN_PACKAGE* pPackage
@@ -228,30 +241,6 @@ static HRESULT ExecutePackageComplete(
241
__out BOOL* pfSuspend
242
);
243
231
-static HRESULT DoMsiBeginTransaction(
232
- __in BURN_EXECUTE_CONTEXT *context
233
- , __in BURN_ENGINE_STATE* pEngineState
234
-);
235
-static HRESULT DoMsiCommitTransaction(
236
- __in BURN_EXECUTE_CONTEXT *context
237
- , __in BURN_ENGINE_STATE* pEngineState
238
-);
239
-static HRESULT DoMsiRollbackTransaction(
240
- __in BURN_EXECUTE_CONTEXT *context
241
- , __in BURN_ENGINE_STATE* pEngineState
242
-);
243
-static HRESULT ExecuteMsiBeginTransaction(
244
- __in BURN_EXECUTE_CONTEXT* pContext
245
- , __in BURN_ENGINE_STATE* pEngineState
246
-);
247
-static HRESULT ExecuteMsiCommitTransaction(
248
- __in BURN_EXECUTE_CONTEXT* pContext
249
- , __in BURN_ENGINE_STATE* pEngineState
250
-);
251
-static HRESULT ExecuteMsiRollbackTransaction(
252
- __in BURN_EXECUTE_CONTEXT* pContext
253
- , __in BURN_ENGINE_STATE* pEngineState
254
-);
244
245
// function definitions
246
@@ -773,7 +762,7 @@ extern "C" HRESULT ApplyExecute(
762
if (fInTransaction)
763
{
764
LogString(REPORT_STANDARD, "Committing MSI transaction\n");
776
- hr = DoMsiCommitTransaction(&context, pEngineState);
765
+ hr = ExecuteMsiCommitTransaction(pEngineState, &context);
766
ExitOnFailure(hr, "Failed committing an MSI transaction");
767
fInTransaction = FALSE;
768
}
@@ -789,7 +778,7 @@ extern "C" HRESULT ApplyExecute(
778
else
779
{
780
LogString(REPORT_STANDARD, "Starting a new MSI transaction\n");
792
- hr = DoMsiBeginTransaction(&context, pEngineState);
781
+ hr = ExecuteMsiBeginTransaction(pEngineState, pExecuteAction->rollbackBoundary.pRollbackBoundary->sczId, &context);
782
ExitOnFailure(hr, "Failed beginning an MSI transaction");
783
fInTransaction = TRUE;
784
}
@@ -855,7 +844,7 @@ extern "C" HRESULT ApplyExecute(
844
if (fInTransaction)
845
{
846
LogString(REPORT_STANDARD, "Committing an MSI transaction\n");
858
- hr = DoMsiCommitTransaction(&context, pEngineState);
847
+ hr = ExecuteMsiCommitTransaction(pEngineState, &context);
848
ExitOnFailure(hr, "Failed committing an MSI transaction");
849
fInTransaction = FALSE;
850
}
@@ -1658,127 +1647,6 @@ static void DoRollbackCache(
1647
}
1648
}
1649
1661
-/* MSI Transactions:
1662
- * All MSI/MSP/MSU packages wrapped in MsiBeginTranasaction-MsiEndTransaction pair are installed or uninstalled together.
1663
-*/
1664
-static HRESULT ExecuteMsiBeginTransaction(
1665
- __in BURN_EXECUTE_CONTEXT* pContext
1666
- , __in BURN_ENGINE_STATE* pEngineState
1667
-)
1668
-{
1669
- HRESULT hr = S_OK;
1670
- UINT uResult = ERROR_SUCCESS;
1671
-
1672
- // Per user/machine context
1673
- if (pEngineState->plan.fPerMachine)
1674
- {
1675
- hr = ElevationMsiBeginTransaction(pEngineState->companionConnection.hPipe, pEngineState->userExperience.hwndApply, pContext);
1676
- ExitOnFailure(hr, "Failed to begin an MSI transaction.");
1677
- }
1678
- else
1679
- {
1680
- MSIHANDLE hMsiTrns = NULL;
1681
- HANDLE hMsiTrnsEvent = NULL;
1682
- uResult = MsiBeginTransaction(L"WiX", 0, &hMsiTrns, &hMsiTrnsEvent);
1683
- ExitOnWin32Error(uResult, hr, "Failed beginning an MSI transaction");
1684
- }
1685
-
1686
-LExit:
1687
- return hr;
1688
-}
1689
-
1690
-static HRESULT ExecuteMsiCommitTransaction(
1691
- __in BURN_EXECUTE_CONTEXT* pContext
1692
- , __in BURN_ENGINE_STATE* pEngineState
1693
-)
1694
-{
1695
- HRESULT hr = S_OK;
1696
- UINT uResult = ERROR_SUCCESS;
1697
-
1698
- // Per user/machine context
1699
- if (pEngineState->plan.fPerMachine)
1700
- {
1701
- hr = ElevationMsiCommitTransaction(pEngineState->companionConnection.hPipe, pEngineState->userExperience.hwndApply, pContext);
1702
- ExitOnFailure(hr, "Failed to commit an MSI transaction.");
1703
- }
1704
- else
1705
- {
1706
- uResult = MsiEndTransaction(MSITRANSACTIONSTATE_COMMIT);
1707
- ExitOnWin32Error(uResult, hr, "Failed beginning an MSI transaction");
1708
- }
1709
-
1710
-LExit:
1711
- return hr;
1712
-}
1713
-
1714
-static HRESULT ExecuteMsiRollbackTransaction(
1715
- __in BURN_EXECUTE_CONTEXT* pContext
1716
- , __in BURN_ENGINE_STATE* pEngineState
1717
-)
1718
-{
1719
- HRESULT hr = S_OK;
1720
- UINT uResult = ERROR_SUCCESS;
1721
-
1722
- // Per user/machine context
1723
- if (pEngineState->plan.fPerMachine)
1724
- {
1725
- hr = ElevationMsiRollbackTransaction(pEngineState->companionConnection.hPipe, pEngineState->userExperience.hwndApply, pContext);
1726
- ExitOnFailure(hr, "Failed to rollback an MSI transaction.");
1727
- }
1728
- else
1729
- {
1730
- uResult = MsiEndTransaction(MSITRANSACTIONSTATE_ROLLBACK);
1731
- ExitOnWin32Error(uResult, hr, "Failed beginning an MSI transaction");
1732
- }
1733
-
1734
-LExit:
1735
- return hr;
1736
-}
1737
-
1738
-// Currently, supporting only elevated transactions.
1739
-static HRESULT DoMsiBeginTransaction(
1740
- __in BURN_EXECUTE_CONTEXT *pContext
1741
- , __in BURN_ENGINE_STATE* pEngineState
1742
-)
1743
-{
1744
- HRESULT hr = S_OK;
1745
-
1746
- hr = ExecuteMsiBeginTransaction(pContext, pEngineState);
1747
- ExitOnFailure(hr, "Failed to execute EXE package.");
1748
-
1749
-LExit:
1750
- return hr;
1751
-}
1752
-
1753
-static HRESULT DoMsiCommitTransaction(
1754
- __in BURN_EXECUTE_CONTEXT *pContext
1755
- , __in BURN_ENGINE_STATE* pEngineState
1756
-)
1757
-{
1758
- HRESULT hr = S_OK;
1759
-
1760
- hr = ExecuteMsiCommitTransaction(pContext, pEngineState);
1761
- ExitOnFailure(hr, "Failed to execute EXE package.");
1762
-
1763
-LExit:
1764
- return hr;
1765
-}
1766
-
1767
-static HRESULT DoMsiRollbackTransaction(
1768
- __in BURN_EXECUTE_CONTEXT *pContext
1769
- , __in BURN_ENGINE_STATE* pEngineState
1770
-)
1771
-{
1772
- HRESULT hr = S_OK;
1773
-
1774
- hr = ExecuteMsiRollbackTransaction(pContext, pEngineState);
1775
- ExitOnFailure(hr, "Failed to execute EXE package.");
1776
-
1777
-LExit:
1778
- return hr;
1779
-}
1780
-
1781
-
1650
static HRESULT DoExecuteAction(
1651
__in BURN_ENGINE_STATE* pEngineState,
1652
__in BURN_EXECUTE_ACTION* pExecuteAction,
@@ -1904,7 +1772,7 @@ static HRESULT DoRollbackActions(
1772
__in BOOL fInTransaction,
1773
__out BOOL* pfKeepRegistration,
1774
__out BOOTSTRAPPER_APPLY_RESTART* pRestart
1907
-)
1775
+ )
1776
{
1777
HRESULT hr = S_OK;
1778
DWORD iCheckpoint = 0;
@@ -1916,7 +1784,7 @@ static HRESULT DoRollbackActions(
1784
// Rollback MSI transaction
1785
if (fInTransaction)
1786
{
1919
- hr = DoMsiRollbackTransaction(pContext, pEngineState);
1787
+ hr = ExecuteMsiRollbackTransaction(pEngineState, pContext);
1788
ExitOnFailure(hr, "Failed rolling back transaction");
1789
}
1790
@@ -2364,6 +2232,70 @@ LExit:
2232
return hr;
2233
}
2234
2235
+static HRESULT ExecuteMsiBeginTransaction(
2236
+ __in BURN_ENGINE_STATE* pEngineState,
2237
+ __in LPCWSTR wzName,
2238
+ __in BURN_EXECUTE_CONTEXT* /*pContext*/
2239
+ )
2240
+{
2241
+ HRESULT hr = S_OK;
2242
+
2243
+ if (pEngineState->plan.fPerMachine)
2244
+ {
2245
+ hr = ElevationMsiBeginTransaction(pEngineState->companionConnection.hPipe, wzName);
2246
+ ExitOnFailure(hr, "Failed to begin an elevated MSI transaction.");
2247
+ }
2248
+ else
2249
+ {
2250
+ hr = MsiEngineBeginTransaction(wzName);
2251
+ }
2252
+
2253
+LExit:
2254
+ return hr;
2255
+}
2256
+
2257
+static HRESULT ExecuteMsiCommitTransaction(
2258
+ __in BURN_ENGINE_STATE* pEngineState,
2259
+ __in BURN_EXECUTE_CONTEXT* /*pContext*/
2260
+ )
2261
+{
2262
+ HRESULT hr = S_OK;
2263
+
2264
+ if (pEngineState->plan.fPerMachine)
2265
+ {
2266
+ hr = ElevationMsiCommitTransaction(pEngineState->companionConnection.hPipe);
2267
+ ExitOnFailure(hr, "Failed to commit an elevated MSI transaction.");
2268
+ }
2269
+ else
2270
+ {
2271
+ hr = MsiEngineCommitTransaction();
2272
+ }
2273
+
2274
+LExit:
2275
+ return hr;
2276
+}
2277
+
2278
+static HRESULT ExecuteMsiRollbackTransaction(
2279
+ __in BURN_ENGINE_STATE* pEngineState,
2280
+ __in BURN_EXECUTE_CONTEXT* /*pContext*/
2281
+ )
2282
+{
2283
+ HRESULT hr = S_OK;
2284
+
2285
+ if (pEngineState->plan.fPerMachine)
2286
+ {
2287
+ hr = ElevationMsiRollbackTransaction(pEngineState->companionConnection.hPipe);
2288
+ ExitOnFailure(hr, "Failed to rollback an elevated MSI transaction.");
2289
+ }
2290
+ else
2291
+ {
2292
+ hr = MsiEngineRollbackTransaction();
2293
+ }
2294
+
2295
+LExit:
2296
+ return hr;
2297
+}
2298
+
2299
static HRESULT CleanPackage(
2300
__in HANDLE hElevatedPipe,
2301
__in BURN_PACKAGE* pPackage
src/engine/elevation.cpp
+78
-100
@@ -28,17 +28,15 @@ typedef enum _BURN_ELEVATION_MESSAGE_TYPE
28
BURN_ELEVATION_MESSAGE_TYPE_LAUNCH_EMBEDDED_CHILD,
29
BURN_ELEVATION_MESSAGE_TYPE_CLEAN_PACKAGE,
30
BURN_ELEVATION_MESSAGE_TYPE_LAUNCH_APPROVED_EXE,
31
+ BURN_ELEVATION_MESSAGE_TYPE_BEGIN_MSI_TRANSACTION,
32
+ BURN_ELEVATION_MESSAGE_TYPE_COMMIT_MSI_TRANSACTION,
33
+ BURN_ELEVATION_MESSAGE_TYPE_ROLLBACK_MSI_TRANSACTION,
34
35
BURN_ELEVATION_MESSAGE_TYPE_EXECUTE_PROGRESS,
36
BURN_ELEVATION_MESSAGE_TYPE_EXECUTE_ERROR,
37
BURN_ELEVATION_MESSAGE_TYPE_EXECUTE_MSI_MESSAGE,
38
BURN_ELEVATION_MESSAGE_TYPE_EXECUTE_FILES_IN_USE,
39
BURN_ELEVATION_MESSAGE_TYPE_LAUNCH_APPROVED_EXE_PROCESSID,
37
-
38
- BURN_ELEVATION_TRANSACTION_BEGIN,
39
- BURN_ELEVATION_TRANSACTION_COMMIT,
40
- BURN_ELEVATION_TRANSACTION_ROLLBACK
41
-
40
} BURN_ELEVATION_MESSAGE_TYPE;
41
42
@@ -74,24 +72,11 @@ typedef struct _BURN_ELEVATION_CHILD_MESSAGE_CONTEXT
72
BURN_VARIABLES* pVariables;
73
BURN_REGISTRATION* pRegistration;
74
BURN_USER_EXPERIENCE* pUserExperience;
77
-
78
- MSIHANDLE hMsiTrns;
79
- HANDLE hMsiTrnsEvent;
75
} BURN_ELEVATION_CHILD_MESSAGE_CONTEXT;
76
77
78
// internal function declarations
79
85
-static HRESULT OnMsiBeginTransaction(
86
- __in BURN_ELEVATION_CHILD_MESSAGE_CONTEXT* pContext
87
-);
88
-static HRESULT OnMsiCommitTransaction(
89
- __in BURN_ELEVATION_CHILD_MESSAGE_CONTEXT* pContext
90
-);
91
-static HRESULT OnMsiRollbackTransaction(
92
- __in BURN_ELEVATION_CHILD_MESSAGE_CONTEXT* pContext
93
-);
94
-
80
static DWORD WINAPI ElevatedChildCacheThreadProc(
81
__in LPVOID lpThreadParameter
82
);
@@ -248,6 +233,13 @@ static HRESULT OnLaunchApprovedExe(
233
__in BYTE* pbData,
234
__in DWORD cbData
235
);
236
+static HRESULT OnMsiBeginTransaction(
237
+ __in BYTE* pbData,
238
+ __in DWORD cbData
239
+ );
240
+static HRESULT OnMsiCommitTransaction();
241
+static HRESULT OnMsiRollbackTransaction();
242
+
243
244
245
// function definitions
@@ -726,62 +718,56 @@ LExit:
718
719
extern "C" HRESULT ElevationMsiBeginTransaction(
720
__in HANDLE hPipe,
729
- __in_opt HWND hwndParent,
730
- __in LPVOID pvContext
731
-)
721
+ __in LPCWSTR wzName
722
+ )
723
{
733
- UNREFERENCED_PARAMETER(hwndParent);
724
HRESULT hr = S_OK;
735
- BURN_ELEVATION_MSI_MESSAGE_CONTEXT context = {};
725
+ BYTE* pbData = NULL;
726
+ SIZE_T cbData = 0;
727
DWORD dwResult = ERROR_SUCCESS;
728
738
- context.pvContext = pvContext;
729
+ // serialize message data
730
+ hr = BuffWriteString(&pbData, &cbData, wzName);
731
+ ExitOnFailure(hr, "Failed to write transaction name to message buffer.");
732
740
- hr = PipeSendMessage(hPipe, BURN_ELEVATION_TRANSACTION_BEGIN, NULL, 0, NULL, &context, &dwResult);
741
- ExitOnFailure(hr, "Failed to send BURN_ELEVATION_MESSAGE_TYPE_EXECUTE_MSI_PACKAGE message to per-machine process.");
742
- ExitOnWin32Error(dwResult, hr, "Failed beginning an elevated MSI transaction");
733
+ hr = PipeSendMessage(hPipe, BURN_ELEVATION_MESSAGE_TYPE_BEGIN_MSI_TRANSACTION, NULL, 0, NULL, NULL, &dwResult);
734
+ ExitOnFailure(hr, "Failed to send BURN_ELEVATION_MESSAGE_TYPE_BEGIN_MSI_TRANSACTION message to per-machine process.");
735
+
736
+ hr = static_cast<HRESULT>(dwResult);
737
738
LExit:
739
+ ReleaseBuffer(pbData);
740
+
741
return hr;
742
}
743
744
extern "C" HRESULT ElevationMsiCommitTransaction(
749
- __in HANDLE hPipe,
750
- __in_opt HWND hwndParent,
751
- __in LPVOID pvContext
752
-)
745
+ __in HANDLE hPipe
746
+ )
747
{
754
- UNREFERENCED_PARAMETER(hwndParent);
748
HRESULT hr = S_OK;
756
- BURN_ELEVATION_MSI_MESSAGE_CONTEXT context = {};
749
DWORD dwResult = ERROR_SUCCESS;
750
759
- context.pvContext = pvContext;
751
+ hr = PipeSendMessage(hPipe, BURN_ELEVATION_MESSAGE_TYPE_COMMIT_MSI_TRANSACTION, NULL, 0, NULL, NULL, &dwResult);
752
+ ExitOnFailure(hr, "Failed to send BURN_ELEVATION_MESSAGE_TYPE_COMMIT_MSI_TRANSACTION message to per-machine process.");
753
761
- hr = PipeSendMessage(hPipe, BURN_ELEVATION_TRANSACTION_COMMIT, NULL, 0, NULL, &context, &dwResult);
762
- ExitOnFailure(hr, "Failed to send BURN_ELEVATION_MESSAGE_TYPE_EXECUTE_MSI_PACKAGE message to per-machine process.");
763
- ExitOnWin32Error(dwResult, hr, "Failed committing an elevated MSI transaction");
754
+ hr = static_cast<HRESULT>(dwResult);
755
756
LExit:
757
return hr;
758
}
759
760
extern "C" HRESULT ElevationMsiRollbackTransaction(
770
- __in HANDLE hPipe,
771
- __in_opt HWND hwndParent,
772
- __in LPVOID pvContext
773
-)
761
+ __in HANDLE hPipe
762
+ )
763
{
775
- UNREFERENCED_PARAMETER(hwndParent);
764
HRESULT hr = S_OK;
777
- BURN_ELEVATION_MSI_MESSAGE_CONTEXT context = {};
765
DWORD dwResult = ERROR_SUCCESS;
766
780
- context.pvContext = pvContext;
767
+ hr = PipeSendMessage(hPipe, BURN_ELEVATION_MESSAGE_TYPE_ROLLBACK_MSI_TRANSACTION, NULL, 0, NULL, NULL, &dwResult);
768
+ ExitOnFailure(hr, "Failed to send BURN_ELEVATION_MESSAGE_TYPE_ROLLBACK_MSI_TRANSACTION message to per-machine process.");
769
782
- hr = PipeSendMessage(hPipe, BURN_ELEVATION_TRANSACTION_ROLLBACK, NULL, 0, NULL, &context, &dwResult);
783
- ExitOnFailure(hr, "Failed to send BURN_ELEVATION_MESSAGE_TYPE_EXECUTE_MSI_PACKAGE message to per-machine process.");
784
- ExitOnWin32Error(dwResult, hr, "Failed rolling back an elevated MSI transaction");
770
+ hr = static_cast<HRESULT>(dwResult);
771
772
LExit:
773
return hr;
@@ -1543,16 +1529,16 @@ static HRESULT ProcessElevatedChildMessage(
1529
1530
switch (pMsg->dwMessage)
1531
{
1546
- case BURN_ELEVATION_TRANSACTION_BEGIN:
1547
- hrResult = OnMsiBeginTransaction(pContext);
1532
+ case BURN_ELEVATION_MESSAGE_TYPE_BEGIN_MSI_TRANSACTION:
1533
+ hrResult = OnMsiBeginTransaction((BYTE*)pMsg->pvData, pMsg->cbData);
1534
break;
1535
1550
- case BURN_ELEVATION_TRANSACTION_COMMIT:
1551
- hrResult = OnMsiCommitTransaction(pContext);
1536
+ case BURN_ELEVATION_MESSAGE_TYPE_COMMIT_MSI_TRANSACTION:
1537
+ hrResult = OnMsiCommitTransaction();
1538
break;
1539
1554
- case BURN_ELEVATION_TRANSACTION_ROLLBACK:
1555
- hrResult = OnMsiRollbackTransaction(pContext);
1540
+ case BURN_ELEVATION_MESSAGE_TYPE_ROLLBACK_MSI_TRANSACTION:
1541
+ hrResult = OnMsiRollbackTransaction();
1542
break;
1543
1544
case BURN_ELEVATION_MESSAGE_TYPE_APPLY_INITIALIZE:
@@ -1690,53 +1676,6 @@ static HRESULT ProcessResult(
1676
return hr;
1677
}
1678
1693
-static HRESULT OnMsiBeginTransaction(
1694
- __in BURN_ELEVATION_CHILD_MESSAGE_CONTEXT* pContext
1695
-)
1696
-{
1697
- UINT uResult = ERROR_SUCCESS;
1698
- HRESULT hr = S_OK;
1699
-
1700
- pContext->hMsiTrns = NULL;
1701
- pContext->hMsiTrnsEvent = NULL;
1702
- uResult = MsiBeginTransaction(L"WiX", 0, &pContext->hMsiTrns, &pContext->hMsiTrnsEvent);
1703
- ExitOnWin32Error(uResult, hr, "Failed beginning an MSI transaction");
1704
-
1705
-LExit:
1706
- return hr;
1707
-}
1708
-
1709
-static HRESULT OnMsiCommitTransaction(
1710
- __in BURN_ELEVATION_CHILD_MESSAGE_CONTEXT* pContext
1711
-)
1712
-{
1713
- UINT uResult = ERROR_SUCCESS;
1714
- HRESULT hr = S_OK;
1715
-
1716
- uResult = MsiEndTransaction(MSITRANSACTIONSTATE_COMMIT);
1717
- ExitOnWin32Error(uResult, hr, "Failed committing an MSI transaction");
1718
-
1719
-LExit:
1720
- pContext->hMsiTrns = NULL;
1721
- pContext->hMsiTrnsEvent = NULL;
1722
- return hr;
1723
-}
1724
-
1725
-static HRESULT OnMsiRollbackTransaction(
1726
- __in BURN_ELEVATION_CHILD_MESSAGE_CONTEXT* pContext
1727
-) {
1728
- UINT uResult = ERROR_SUCCESS;
1729
- HRESULT hr = S_OK;
1730
-
1731
- uResult = MsiEndTransaction(MSITRANSACTIONSTATE_ROLLBACK);
1732
- ExitOnWin32Error(uResult, hr, "Failed rolling back an MSI transaction");
1733
-
1734
-LExit:
1735
- pContext->hMsiTrns = NULL;
1736
- pContext->hMsiTrnsEvent = NULL;
1737
- return hr;
1738
-}
1739
-
1679
static HRESULT OnApplyInitialize(
1680
__in BURN_VARIABLES* pVariables,
1681
__in BURN_REGISTRATION* pRegistration,
@@ -2845,3 +2784,42 @@ LExit:
2784
ApprovedExesUninitializeLaunch(pLaunchApprovedExe);
2785
return hr;
2786
}
2787
+
2788
+static HRESULT OnMsiBeginTransaction(
2789
+ __in BYTE* pbData,
2790
+ __in DWORD cbData
2791
+ )
2792
+{
2793
+ HRESULT hr = S_OK;
2794
+ SIZE_T iData = 0;
2795
+ LPWSTR sczName = NULL;
2796
+
2797
+ // Deserialize message data.
2798
+ hr = BuffReadString(pbData, cbData, &iData, &sczName);
2799
+ ExitOnFailure(hr, "Failed to read transaction name.");
2800
+
2801
+ hr = MsiEngineBeginTransaction(sczName);
2802
+
2803
+LExit:
2804
+ ReleaseStr(sczName);
2805
+
2806
+ return hr;
2807
+}
2808
+
2809
+static HRESULT OnMsiCommitTransaction()
2810
+{
2811
+ HRESULT hr = S_OK;
2812
+
2813
+ hr = MsiEngineCommitTransaction();
2814
+
2815
+ return hr;
2816
+}
2817
+
2818
+static HRESULT OnMsiRollbackTransaction()
2819
+{
2820
+ HRESULT hr = S_OK;
2821
+
2822
+ hr = MsiEngineRollbackTransaction();
2823
+
2824
+ return hr;
2825
+}
src/engine/elevation.h
+6
-11
@@ -159,19 +159,14 @@ HRESULT ElevationChildResumeAutomaticUpdates();
159
160
HRESULT ElevationMsiBeginTransaction(
161
__in HANDLE hPipe,
162
- __in_opt HWND hwndParent,
163
- __in LPVOID pvContext
164
-);
162
+ __in LPCWSTR wzName
163
+ );
164
HRESULT ElevationMsiCommitTransaction(
166
- __in HANDLE hPipe,
167
- __in_opt HWND hwndParent,
168
- __in LPVOID pvContext
169
-);
165
+ __in HANDLE hPipe
166
+ );
167
HRESULT ElevationMsiRollbackTransaction(
171
- __in HANDLE hPipe,
172
- __in_opt HWND hwndParent,
173
- __in LPVOID pvContext
174
-);
168
+ __in HANDLE hPipe
169
+ );
170
171
#ifdef __cplusplus
172
}
src/engine/msiengine.cpp
+42
@@ -1137,6 +1137,48 @@ LExit:
1137
return hr;
1138
}
1139
1140
+extern "C" HRESULT MsiEngineBeginTransaction(
1141
+ __in LPCWSTR wzName
1142
+ )
1143
+{
1144
+ HRESULT hr = S_OK;
1145
+ UINT uResult = ERROR_SUCCESS;
1146
+ MSIHANDLE hTransactionHandle = NULL;
1147
+ HANDLE hChangeOfOwnerEvent = NULL;
1148
+
1149
+ uResult = ::MsiBeginTransaction(wzName, 0, &hTransactionHandle, &hChangeOfOwnerEvent);
1150
+ ExitOnWin32Error(uResult, hr, "Failed to begin an MSI transaction");
1151
+
1152
+LExit:
1153
+ return hr;
1154
+}
1155
+
1156
+extern "C" HRESULT MsiEngineCommitTransaction()
1157
+{
1158
+ HRESULT hr = S_OK;
1159
+ UINT uResult = ERROR_SUCCESS;
1160
+
1161
+ uResult = ::MsiEndTransaction(MSITRANSACTIONSTATE_COMMIT);
1162
+ ExitOnWin32Error(uResult, hr, "Failed to commit the MSI transaction");
1163
+
1164
+LExit:
1165
+
1166
+ return hr;
1167
+}
1168
+
1169
+extern "C" HRESULT MsiEngineRollbackTransaction()
1170
+{
1171
+ HRESULT hr = S_OK;
1172
+ UINT uResult = ERROR_SUCCESS;
1173
+
1174
+ uResult = ::MsiEndTransaction(MSITRANSACTIONSTATE_ROLLBACK);
1175
+ ExitOnWin32Error(uResult, hr, "Failed to rollback the MSI transaction");
1176
+
1177
+LExit:
1178
+
1179
+ return hr;
1180
+}
1181
+
1182
extern "C" HRESULT MsiEngineExecutePackage(
1183
__in_opt HWND hwndParent,
1184
__in BURN_EXECUTE_ACTION* pExecuteAction,
src/engine/msiengine.h
+5
@@ -52,6 +52,11 @@ HRESULT MsiEngineAddCompatiblePackage(
52
__in const BURN_PACKAGE* pPackage,
53
__out_opt BURN_PACKAGE** ppCompatiblePackage
54
);
55
+HRESULT MsiEngineBeginTransaction(
56
+ __in LPCWSTR wzName
57
+ );
58
+HRESULT MsiEngineCommitTransaction();
59
+HRESULT MsiEngineRollbackTransaction();
60
HRESULT MsiEngineExecutePackage(
61
__in_opt HWND hwndParent,
62
__in BURN_EXECUTE_ACTION* pExecuteAction,