aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorNir Bar <nir.bar@panel-sw.co.il>2021-03-17 14:45:03 -0500
committerSean Hall <r.sean.hall@gmail.com>2021-03-17 14:49:24 -0500
commitb7582318f6cb6e166f5ca22128caea2a97551a1f (patch)
treef92071000dd33376e6b982b52ed2172278ef4035
parentaf68033509730ffe01602f839861a47287bb709f (diff)
downloadwix-b7582318f6cb6e166f5ca22128caea2a97551a1f.tar.gz
wix-b7582318f6cb6e166f5ca22128caea2a97551a1f.tar.bz2
wix-b7582318f6cb6e166f5ca22128caea2a97551a1f.zip
Use wiutil to start/end msi transactions
Release MSI transaction handles immediately contributes to #5386
-rw-r--r--src/engine/apply.cpp40
-rw-r--r--src/engine/elevation.cpp111
-rw-r--r--src/engine/elevation.h6
-rw-r--r--src/engine/msiengine.cpp32
-rw-r--r--src/engine/msiengine.h6
-rw-r--r--src/engine/package.cpp27
-rw-r--r--src/engine/package.h6
-rw-r--r--src/engine/plan.cpp1
-rw-r--r--src/engine/userexperience.cpp10
-rw-r--r--src/engine/userexperience.h5
10 files changed, 163 insertions, 81 deletions
diff --git a/src/engine/apply.cpp b/src/engine/apply.cpp
index 3fbab61a..77080c76 100644
--- a/src/engine/apply.cpp
+++ b/src/engine/apply.cpp
@@ -821,16 +821,16 @@ extern "C" HRESULT ApplyExecute(
821 break; 821 break;
822 } 822 }
823 823
824 // If inside a MSI transaction, roll it back.
825 if (pCheckpoint && pCheckpoint->pActiveRollbackBoundary && pCheckpoint->pActiveRollbackBoundary->fActiveTransaction)
826 {
827 hrRollback = ExecuteMsiRollbackTransaction(pEngineState, pCheckpoint->pActiveRollbackBoundary, &context);
828 IgnoreRollbackError(hrRollback, "Failed rolling back transaction");
829 }
830
831 // The action failed, roll back to previous rollback boundary.
832 if (pCheckpoint) 824 if (pCheckpoint)
833 { 825 {
826 // If inside a MSI transaction, roll it back.
827 if (pCheckpoint->pActiveRollbackBoundary && pCheckpoint->pActiveRollbackBoundary->fActiveTransaction)
828 {
829 hrRollback = ExecuteMsiRollbackTransaction(pEngineState, pCheckpoint->pActiveRollbackBoundary, &context);
830 IgnoreRollbackError(hrRollback, "Failed rolling back transaction");
831 }
832
833 // The action failed, roll back to previous rollback boundary.
834 hrRollback = DoRollbackActions(pEngineState, &context, pCheckpoint->dwId, pRestart); 834 hrRollback = DoRollbackActions(pEngineState, &context, pCheckpoint->dwId, pRestart);
835 IgnoreRollbackError(hrRollback, "Failed rollback actions"); 835 IgnoreRollbackError(hrRollback, "Failed rollback actions");
836 } 836 }
@@ -2316,12 +2316,12 @@ static HRESULT ExecuteMsiBeginTransaction(
2316 2316
2317 if (pEngineState->plan.fPerMachine) 2317 if (pEngineState->plan.fPerMachine)
2318 { 2318 {
2319 hr = ElevationMsiBeginTransaction(pEngineState->companionConnection.hPipe, pRollbackBoundary->sczId); 2319 hr = ElevationMsiBeginTransaction(pEngineState->companionConnection.hPipe, pRollbackBoundary);
2320 ExitOnFailure(hr, "Failed to begin an elevated MSI transaction."); 2320 ExitOnFailure(hr, "Failed to begin an elevated MSI transaction.");
2321 } 2321 }
2322 else 2322 else
2323 { 2323 {
2324 hr = MsiEngineBeginTransaction(pRollbackBoundary->sczId); 2324 hr = MsiEngineBeginTransaction(pRollbackBoundary);
2325 } 2325 }
2326 2326
2327 if (SUCCEEDED(hr)) 2327 if (SUCCEEDED(hr))
@@ -2347,25 +2347,25 @@ static HRESULT ExecuteMsiCommitTransaction(
2347 ) 2347 )
2348{ 2348{
2349 HRESULT hr = S_OK; 2349 HRESULT hr = S_OK;
2350 BOOL fBeginCalled = FALSE; 2350 BOOL fCommitBeginCalled = FALSE;
2351 2351
2352 if (!pRollbackBoundary->fActiveTransaction) 2352 if (!pRollbackBoundary->fActiveTransaction)
2353 { 2353 {
2354 ExitFunction1(hr = E_INVALIDSTATE); 2354 ExitFunction1(hr = E_INVALIDSTATE);
2355 } 2355 }
2356 2356
2357 fBeginCalled = TRUE; 2357 fCommitBeginCalled = TRUE;
2358 hr = UserExperienceOnCommitMsiTransactionBegin(&pEngineState->userExperience, pRollbackBoundary->sczId); 2358 hr = UserExperienceOnCommitMsiTransactionBegin(&pEngineState->userExperience, pRollbackBoundary->sczId);
2359 ExitOnRootFailure(hr, "BA aborted execute commit MSI transaction."); 2359 ExitOnRootFailure(hr, "BA aborted execute commit MSI transaction.");
2360 2360
2361 if (pEngineState->plan.fPerMachine) 2361 if (pEngineState->plan.fPerMachine)
2362 { 2362 {
2363 hr = ElevationMsiCommitTransaction(pEngineState->companionConnection.hPipe, pRollbackBoundary->sczId); 2363 hr = ElevationMsiCommitTransaction(pEngineState->companionConnection.hPipe, pRollbackBoundary);
2364 ExitOnFailure(hr, "Failed to commit an elevated MSI transaction."); 2364 ExitOnFailure(hr, "Failed to commit an elevated MSI transaction.");
2365 } 2365 }
2366 else 2366 else
2367 { 2367 {
2368 hr = MsiEngineCommitTransaction(pRollbackBoundary->sczId); 2368 hr = MsiEngineCommitTransaction(pRollbackBoundary);
2369 } 2369 }
2370 2370
2371 if (SUCCEEDED(hr)) 2371 if (SUCCEEDED(hr))
@@ -2376,7 +2376,7 @@ static HRESULT ExecuteMsiCommitTransaction(
2376 } 2376 }
2377 2377
2378LExit: 2378LExit:
2379 if (fBeginCalled) 2379 if (fCommitBeginCalled)
2380 { 2380 {
2381 UserExperienceOnCommitMsiTransactionComplete(&pEngineState->userExperience, pRollbackBoundary->sczId, hr); 2381 UserExperienceOnCommitMsiTransactionComplete(&pEngineState->userExperience, pRollbackBoundary->sczId, hr);
2382 } 2382 }
@@ -2391,24 +2391,24 @@ static HRESULT ExecuteMsiRollbackTransaction(
2391 ) 2391 )
2392{ 2392{
2393 HRESULT hr = S_OK; 2393 HRESULT hr = S_OK;
2394 BOOL fBeginCalled = FALSE; 2394 BOOL fRollbackBeginCalled = FALSE;
2395 2395
2396 if (!pRollbackBoundary->fActiveTransaction) 2396 if (!pRollbackBoundary->fActiveTransaction)
2397 { 2397 {
2398 ExitFunction(); 2398 ExitFunction();
2399 } 2399 }
2400 2400
2401 fBeginCalled = TRUE; 2401 fRollbackBeginCalled = TRUE;
2402 UserExperienceOnRollbackMsiTransactionBegin(&pEngineState->userExperience, pRollbackBoundary->sczId); 2402 UserExperienceOnRollbackMsiTransactionBegin(&pEngineState->userExperience, pRollbackBoundary->sczId);
2403 2403
2404 if (pEngineState->plan.fPerMachine) 2404 if (pEngineState->plan.fPerMachine)
2405 { 2405 {
2406 hr = ElevationMsiRollbackTransaction(pEngineState->companionConnection.hPipe, pRollbackBoundary->sczId); 2406 hr = ElevationMsiRollbackTransaction(pEngineState->companionConnection.hPipe, pRollbackBoundary);
2407 ExitOnFailure(hr, "Failed to rollback an elevated MSI transaction."); 2407 ExitOnFailure(hr, "Failed to rollback an elevated MSI transaction.");
2408 } 2408 }
2409 else 2409 else
2410 { 2410 {
2411 hr = MsiEngineRollbackTransaction(pRollbackBoundary->sczId); 2411 hr = MsiEngineRollbackTransaction(pRollbackBoundary);
2412 } 2412 }
2413 2413
2414LExit: 2414LExit:
@@ -2416,7 +2416,7 @@ LExit:
2416 2416
2417 ResetTransactionRegistrationState(pEngineState, FALSE); 2417 ResetTransactionRegistrationState(pEngineState, FALSE);
2418 2418
2419 if (fBeginCalled) 2419 if (fRollbackBeginCalled)
2420 { 2420 {
2421 UserExperienceOnRollbackMsiTransactionComplete(&pEngineState->userExperience, pRollbackBoundary->sczId, hr); 2421 UserExperienceOnRollbackMsiTransactionComplete(&pEngineState->userExperience, pRollbackBoundary->sczId, hr);
2422 } 2422 }
diff --git a/src/engine/elevation.cpp b/src/engine/elevation.cpp
index 7c5dae4b..1737bf5b 100644
--- a/src/engine/elevation.cpp
+++ b/src/engine/elevation.cpp
@@ -246,14 +246,17 @@ static HRESULT OnLaunchApprovedExe(
246 __in DWORD cbData 246 __in DWORD cbData
247 ); 247 );
248static HRESULT OnMsiBeginTransaction( 248static HRESULT OnMsiBeginTransaction(
249 __in BURN_PACKAGES* pPackages,
249 __in BYTE* pbData, 250 __in BYTE* pbData,
250 __in DWORD cbData 251 __in DWORD cbData
251 ); 252 );
252static HRESULT OnMsiCommitTransaction( 253static HRESULT OnMsiCommitTransaction(
254 __in BURN_PACKAGES* pPackages,
253 __in BYTE* pbData, 255 __in BYTE* pbData,
254 __in DWORD cbData 256 __in DWORD cbData
255 ); 257 );
256static HRESULT OnMsiRollbackTransaction( 258static HRESULT OnMsiRollbackTransaction(
259 __in BURN_PACKAGES* pPackages,
257 __in BYTE* pbData, 260 __in BYTE* pbData,
258 __in DWORD cbData 261 __in DWORD cbData
259 ); 262 );
@@ -763,7 +766,7 @@ LExit:
763 766
764extern "C" HRESULT ElevationMsiBeginTransaction( 767extern "C" HRESULT ElevationMsiBeginTransaction(
765 __in HANDLE hPipe, 768 __in HANDLE hPipe,
766 __in LPCWSTR wzName 769 __in BURN_ROLLBACK_BOUNDARY* pRollbackBoundary
767 ) 770 )
768{ 771{
769 HRESULT hr = S_OK; 772 HRESULT hr = S_OK;
@@ -772,9 +775,12 @@ extern "C" HRESULT ElevationMsiBeginTransaction(
772 DWORD dwResult = ERROR_SUCCESS; 775 DWORD dwResult = ERROR_SUCCESS;
773 776
774 // serialize message data 777 // serialize message data
775 hr = BuffWriteString(&pbData, &cbData, wzName); 778 hr = BuffWriteString(&pbData, &cbData, pRollbackBoundary->sczId);
776 ExitOnFailure(hr, "Failed to write transaction name to message buffer."); 779 ExitOnFailure(hr, "Failed to write transaction name to message buffer.");
777 780
781 hr = BuffWriteString(&pbData, &cbData, pRollbackBoundary->sczLogPath);
782 ExitOnFailure(hr, "Failed to write transaction log path to message buffer.");
783
778 hr = PipeSendMessage(hPipe, BURN_ELEVATION_MESSAGE_TYPE_BEGIN_MSI_TRANSACTION, pbData, cbData, NULL, NULL, &dwResult); 784 hr = PipeSendMessage(hPipe, BURN_ELEVATION_MESSAGE_TYPE_BEGIN_MSI_TRANSACTION, pbData, cbData, NULL, NULL, &dwResult);
779 ExitOnFailure(hr, "Failed to send BURN_ELEVATION_MESSAGE_TYPE_BEGIN_MSI_TRANSACTION message to per-machine process."); 785 ExitOnFailure(hr, "Failed to send BURN_ELEVATION_MESSAGE_TYPE_BEGIN_MSI_TRANSACTION message to per-machine process.");
780 786
@@ -788,7 +794,7 @@ LExit:
788 794
789extern "C" HRESULT ElevationMsiCommitTransaction( 795extern "C" HRESULT ElevationMsiCommitTransaction(
790 __in HANDLE hPipe, 796 __in HANDLE hPipe,
791 __in LPCWSTR wzName 797 __in BURN_ROLLBACK_BOUNDARY* pRollbackBoundary
792 ) 798 )
793{ 799{
794 HRESULT hr = S_OK; 800 HRESULT hr = S_OK;
@@ -797,9 +803,12 @@ extern "C" HRESULT ElevationMsiCommitTransaction(
797 DWORD dwResult = ERROR_SUCCESS; 803 DWORD dwResult = ERROR_SUCCESS;
798 804
799 // serialize message data 805 // serialize message data
800 hr = BuffWriteString(&pbData, &cbData, wzName); 806 hr = BuffWriteString(&pbData, &cbData, pRollbackBoundary->sczId);
801 ExitOnFailure(hr, "Failed to write transaction name to message buffer."); 807 ExitOnFailure(hr, "Failed to write transaction name to message buffer.");
802 808
809 hr = BuffWriteString(&pbData, &cbData, pRollbackBoundary->sczLogPath);
810 ExitOnFailure(hr, "Failed to write transaction log path to message buffer.");
811
803 hr = PipeSendMessage(hPipe, BURN_ELEVATION_MESSAGE_TYPE_COMMIT_MSI_TRANSACTION, pbData, cbData, NULL, NULL, &dwResult); 812 hr = PipeSendMessage(hPipe, BURN_ELEVATION_MESSAGE_TYPE_COMMIT_MSI_TRANSACTION, pbData, cbData, NULL, NULL, &dwResult);
804 ExitOnFailure(hr, "Failed to send BURN_ELEVATION_MESSAGE_TYPE_COMMIT_MSI_TRANSACTION message to per-machine process."); 813 ExitOnFailure(hr, "Failed to send BURN_ELEVATION_MESSAGE_TYPE_COMMIT_MSI_TRANSACTION message to per-machine process.");
805 814
@@ -811,7 +820,7 @@ LExit:
811 820
812extern "C" HRESULT ElevationMsiRollbackTransaction( 821extern "C" HRESULT ElevationMsiRollbackTransaction(
813 __in HANDLE hPipe, 822 __in HANDLE hPipe,
814 __in LPCWSTR wzName 823 __in BURN_ROLLBACK_BOUNDARY* pRollbackBoundary
815 ) 824 )
816{ 825{
817 HRESULT hr = S_OK; 826 HRESULT hr = S_OK;
@@ -820,9 +829,12 @@ extern "C" HRESULT ElevationMsiRollbackTransaction(
820 DWORD dwResult = ERROR_SUCCESS; 829 DWORD dwResult = ERROR_SUCCESS;
821 830
822 // serialize message data 831 // serialize message data
823 hr = BuffWriteString(&pbData, &cbData, wzName); 832 hr = BuffWriteString(&pbData, &cbData, pRollbackBoundary->sczId);
824 ExitOnFailure(hr, "Failed to write transaction name to message buffer."); 833 ExitOnFailure(hr, "Failed to write transaction name to message buffer.");
825 834
835 hr = BuffWriteString(&pbData, &cbData, pRollbackBoundary->sczLogPath);
836 ExitOnFailure(hr, "Failed to write transaction log path to message buffer.");
837
826 hr = PipeSendMessage(hPipe, BURN_ELEVATION_MESSAGE_TYPE_ROLLBACK_MSI_TRANSACTION, pbData, cbData, NULL, NULL, &dwResult); 838 hr = PipeSendMessage(hPipe, BURN_ELEVATION_MESSAGE_TYPE_ROLLBACK_MSI_TRANSACTION, pbData, cbData, NULL, NULL, &dwResult);
827 ExitOnFailure(hr, "Failed to send BURN_ELEVATION_MESSAGE_TYPE_ROLLBACK_MSI_TRANSACTION message to per-machine process."); 839 ExitOnFailure(hr, "Failed to send BURN_ELEVATION_MESSAGE_TYPE_ROLLBACK_MSI_TRANSACTION message to per-machine process.");
828 840
@@ -1610,15 +1622,15 @@ static HRESULT ProcessElevatedChildMessage(
1610 switch (pMsg->dwMessage) 1622 switch (pMsg->dwMessage)
1611 { 1623 {
1612 case BURN_ELEVATION_MESSAGE_TYPE_BEGIN_MSI_TRANSACTION: 1624 case BURN_ELEVATION_MESSAGE_TYPE_BEGIN_MSI_TRANSACTION:
1613 hrResult = OnMsiBeginTransaction((BYTE*)pMsg->pvData, pMsg->cbData); 1625 hrResult = OnMsiBeginTransaction(pContext->pPackages, (BYTE*)pMsg->pvData, pMsg->cbData);
1614 break; 1626 break;
1615 1627
1616 case BURN_ELEVATION_MESSAGE_TYPE_COMMIT_MSI_TRANSACTION: 1628 case BURN_ELEVATION_MESSAGE_TYPE_COMMIT_MSI_TRANSACTION:
1617 hrResult = OnMsiCommitTransaction((BYTE*)pMsg->pvData, pMsg->cbData); 1629 hrResult = OnMsiCommitTransaction(pContext->pPackages, (BYTE*)pMsg->pvData, pMsg->cbData);
1618 break; 1630 break;
1619 1631
1620 case BURN_ELEVATION_MESSAGE_TYPE_ROLLBACK_MSI_TRANSACTION: 1632 case BURN_ELEVATION_MESSAGE_TYPE_ROLLBACK_MSI_TRANSACTION:
1621 hrResult = OnMsiRollbackTransaction((BYTE*)pMsg->pvData, pMsg->cbData); 1633 hrResult = OnMsiRollbackTransaction(pContext->pPackages, (BYTE*)pMsg->pvData, pMsg->cbData);
1622 break; 1634 break;
1623 1635
1624 case BURN_ELEVATION_MESSAGE_TYPE_APPLY_INITIALIZE: 1636 case BURN_ELEVATION_MESSAGE_TYPE_APPLY_INITIALIZE:
@@ -2824,64 +2836,115 @@ LExit:
2824} 2836}
2825 2837
2826static HRESULT OnMsiBeginTransaction( 2838static HRESULT OnMsiBeginTransaction(
2839 __in BURN_PACKAGES* pPackages,
2827 __in BYTE* pbData, 2840 __in BYTE* pbData,
2828 __in DWORD cbData 2841 __in DWORD cbData
2829 ) 2842 )
2830{ 2843{
2831 HRESULT hr = S_OK; 2844 HRESULT hr = S_OK;
2832 SIZE_T iData = 0; 2845 SIZE_T iData = 0;
2833 LPWSTR sczName = NULL; 2846 LPWSTR sczId = NULL;
2847 LPWSTR sczLogPath = NULL;
2848 BURN_ROLLBACK_BOUNDARY* pRollbackBoundary = NULL;
2834 2849
2835 // Deserialize message data. 2850 // Deserialize message data.
2836 hr = BuffReadString(pbData, cbData, &iData, &sczName); 2851 hr = BuffReadString(pbData, cbData, &iData, &sczId);
2837 ExitOnFailure(hr, "Failed to read transaction name."); 2852 ExitOnFailure(hr, "Failed to read rollback boundary id.");
2838 2853
2839 hr = MsiEngineBeginTransaction(sczName); 2854 hr = BuffReadString(pbData, cbData, &iData, &sczLogPath);
2855 ExitOnFailure(hr, "Failed to read transaction log path.");
2856
2857 PackageFindRollbackBoundaryById(pPackages, sczId, &pRollbackBoundary);
2858 ExitOnFailure(hr, "Failed to find rollback boundary: %ls", sczId);
2859
2860 pRollbackBoundary->sczLogPath = sczLogPath;
2861
2862 hr = MsiEngineBeginTransaction(pRollbackBoundary);
2840 2863
2841LExit: 2864LExit:
2842 ReleaseStr(sczName); 2865 ReleaseStr(sczId);
2866 ReleaseStr(sczLogPath);
2867
2868 if (pRollbackBoundary)
2869 {
2870 pRollbackBoundary->sczLogPath = NULL;
2871 }
2843 2872
2844 return hr; 2873 return hr;
2845} 2874}
2846 2875
2847static HRESULT OnMsiCommitTransaction( 2876static HRESULT OnMsiCommitTransaction(
2877 __in BURN_PACKAGES* pPackages,
2848 __in BYTE* pbData, 2878 __in BYTE* pbData,
2849 __in DWORD cbData 2879 __in DWORD cbData
2850 ) 2880 )
2851{ 2881{
2852 HRESULT hr = S_OK; 2882 HRESULT hr = S_OK;
2853 SIZE_T iData = 0; 2883 SIZE_T iData = 0;
2854 LPWSTR sczName = NULL; 2884 LPWSTR sczId = NULL;
2885 LPWSTR sczLogPath = NULL;
2886 BURN_ROLLBACK_BOUNDARY* pRollbackBoundary = NULL;
2855 2887
2856 // Deserialize message data. 2888 // Deserialize message data.
2857 hr = BuffReadString(pbData, cbData, &iData, &sczName); 2889 hr = BuffReadString(pbData, cbData, &iData, &sczId);
2858 ExitOnFailure(hr, "Failed to read transaction name."); 2890 ExitOnFailure(hr, "Failed to read rollback boundary id.");
2859 2891
2860 hr = MsiEngineCommitTransaction(sczName); 2892 hr = BuffReadString(pbData, cbData, &iData, &sczLogPath);
2893 ExitOnFailure(hr, "Failed to read transaction log path.");
2894
2895 PackageFindRollbackBoundaryById(pPackages, sczId, &pRollbackBoundary);
2896 ExitOnFailure(hr, "Failed to find rollback boundary: %ls", sczId);
2897
2898 pRollbackBoundary->sczLogPath = sczLogPath;
2899
2900 hr = MsiEngineCommitTransaction(pRollbackBoundary);
2861 2901
2862LExit: 2902LExit:
2863 ReleaseStr(sczName); 2903 ReleaseStr(sczId);
2904 ReleaseStr(sczLogPath);
2905
2906 if (pRollbackBoundary)
2907 {
2908 pRollbackBoundary->sczLogPath = NULL;
2909 }
2864 2910
2865 return hr; 2911 return hr;
2866} 2912}
2867 2913
2868static HRESULT OnMsiRollbackTransaction( 2914static HRESULT OnMsiRollbackTransaction(
2915 __in BURN_PACKAGES* pPackages,
2869 __in BYTE* pbData, 2916 __in BYTE* pbData,
2870 __in DWORD cbData 2917 __in DWORD cbData
2871 ) 2918 )
2872{ 2919{
2873 HRESULT hr = S_OK; 2920 HRESULT hr = S_OK;
2874 SIZE_T iData = 0; 2921 SIZE_T iData = 0;
2875 LPWSTR sczName = NULL; 2922 LPWSTR sczId = NULL;
2923 LPWSTR sczLogPath = NULL;
2924 BURN_ROLLBACK_BOUNDARY* pRollbackBoundary = NULL;
2876 2925
2877 // Deserialize message data. 2926 // Deserialize message data.
2878 hr = BuffReadString(pbData, cbData, &iData, &sczName); 2927 hr = BuffReadString(pbData, cbData, &iData, &sczId);
2879 ExitOnFailure(hr, "Failed to read transaction name."); 2928 ExitOnFailure(hr, "Failed to read rollback boundary id.");
2880 2929
2881 hr = MsiEngineRollbackTransaction(sczName); 2930 hr = BuffReadString(pbData, cbData, &iData, &sczLogPath);
2931 ExitOnFailure(hr, "Failed to read transaction log path.");
2932
2933 PackageFindRollbackBoundaryById(pPackages, sczId, &pRollbackBoundary);
2934 ExitOnFailure(hr, "Failed to find rollback boundary: %ls", sczId);
2935
2936 pRollbackBoundary->sczLogPath = sczLogPath;
2937
2938 hr = MsiEngineRollbackTransaction(pRollbackBoundary);
2882 2939
2883LExit: 2940LExit:
2884 ReleaseStr(sczName); 2941 ReleaseStr(sczId);
2942 ReleaseStr(sczLogPath);
2943
2944 if (pRollbackBoundary)
2945 {
2946 pRollbackBoundary->sczLogPath = NULL;
2947 }
2885 2948
2886 return hr; 2949 return hr;
2887} 2950}
diff --git a/src/engine/elevation.h b/src/engine/elevation.h
index e254dea5..9ce8cef9 100644
--- a/src/engine/elevation.h
+++ b/src/engine/elevation.h
@@ -156,15 +156,15 @@ HRESULT ElevationChildResumeAutomaticUpdates();
156 156
157HRESULT ElevationMsiBeginTransaction( 157HRESULT ElevationMsiBeginTransaction(
158 __in HANDLE hPipe, 158 __in HANDLE hPipe,
159 __in LPCWSTR wzName 159 __in BURN_ROLLBACK_BOUNDARY* pRollbackBoundary
160 ); 160 );
161HRESULT ElevationMsiCommitTransaction( 161HRESULT ElevationMsiCommitTransaction(
162 __in HANDLE hPipe, 162 __in HANDLE hPipe,
163 __in LPCWSTR wzName 163 __in BURN_ROLLBACK_BOUNDARY* pRollbackBoundary
164 ); 164 );
165HRESULT ElevationMsiRollbackTransaction( 165HRESULT ElevationMsiRollbackTransaction(
166 __in HANDLE hPipe, 166 __in HANDLE hPipe,
167 __in LPCWSTR wzName 167 __in BURN_ROLLBACK_BOUNDARY* pRollbackBoundary
168 ); 168 );
169 169
170#ifdef __cplusplus 170#ifdef __cplusplus
diff --git a/src/engine/msiengine.cpp b/src/engine/msiengine.cpp
index f0aa784e..6c5b760b 100644
--- a/src/engine/msiengine.cpp
+++ b/src/engine/msiengine.cpp
@@ -1016,40 +1016,41 @@ LExit:
1016} 1016}
1017 1017
1018extern "C" HRESULT MsiEngineBeginTransaction( 1018extern "C" HRESULT MsiEngineBeginTransaction(
1019 __in LPCWSTR wzName 1019 __in BURN_ROLLBACK_BOUNDARY* pRollbackBoundary
1020 ) 1020 )
1021{ 1021{
1022 HRESULT hr = S_OK; 1022 HRESULT hr = S_OK;
1023 UINT uResult = ERROR_SUCCESS;
1024 MSIHANDLE hTransactionHandle = NULL; 1023 MSIHANDLE hTransactionHandle = NULL;
1025 HANDLE hChangeOfOwnerEvent = NULL; 1024 HANDLE hChangeOfOwnerEvent = NULL;
1026 1025
1027 LogId(REPORT_STANDARD, MSG_MSI_TRANSACTION_BEGIN, wzName); 1026 LogId(REPORT_STANDARD, MSG_MSI_TRANSACTION_BEGIN, pRollbackBoundary->sczId);
1028 1027
1029 uResult = ::MsiBeginTransaction(wzName, 0, &hTransactionHandle, &hChangeOfOwnerEvent); 1028 hr = WiuBeginTransaction(pRollbackBoundary->sczId, 0, &hTransactionHandle, &hChangeOfOwnerEvent, WIU_LOG_DEFAULT | INSTALLLOGMODE_VERBOSE, pRollbackBoundary->sczLogPath);
1030 1029
1031 if (ERROR_ROLLBACK_DISABLED == uResult) 1030 if (HRESULT_FROM_WIN32(ERROR_ROLLBACK_DISABLED) == hr)
1032 { 1031 {
1033 LogId(REPORT_ERROR, MSG_MSI_TRANSACTIONS_DISABLED); 1032 LogId(REPORT_ERROR, MSG_MSI_TRANSACTIONS_DISABLED);
1034 } 1033 }
1035 1034
1036 ExitOnWin32Error(uResult, hr, "Failed to begin an MSI transaction"); 1035 ExitOnFailure(hr, "Failed to begin an MSI transaction");
1037 1036
1038LExit: 1037LExit:
1038 ReleaseMsi(hTransactionHandle);
1039 ReleaseHandle(hChangeOfOwnerEvent);
1040
1039 return hr; 1041 return hr;
1040} 1042}
1041 1043
1042extern "C" HRESULT MsiEngineCommitTransaction( 1044extern "C" HRESULT MsiEngineCommitTransaction(
1043 __in LPCWSTR wzName 1045 __in BURN_ROLLBACK_BOUNDARY* pRollbackBoundary
1044 ) 1046 )
1045{ 1047{
1046 HRESULT hr = S_OK; 1048 HRESULT hr = S_OK;
1047 UINT uResult = ERROR_SUCCESS;
1048 1049
1049 LogId(REPORT_STANDARD, MSG_MSI_TRANSACTION_COMMIT, wzName); 1050 LogId(REPORT_STANDARD, MSG_MSI_TRANSACTION_COMMIT, pRollbackBoundary->sczId);
1050 1051
1051 uResult = ::MsiEndTransaction(MSITRANSACTIONSTATE_COMMIT); 1052 hr = WiuEndTransaction(MSITRANSACTIONSTATE_COMMIT, WIU_LOG_DEFAULT | INSTALLLOGMODE_VERBOSE, pRollbackBoundary->sczLogPath);
1052 ExitOnWin32Error(uResult, hr, "Failed to commit the MSI transaction"); 1053 ExitOnFailure(hr, "Failed to commit the MSI transaction");
1053 1054
1054LExit: 1055LExit:
1055 1056
@@ -1057,16 +1058,15 @@ LExit:
1057} 1058}
1058 1059
1059extern "C" HRESULT MsiEngineRollbackTransaction( 1060extern "C" HRESULT MsiEngineRollbackTransaction(
1060 __in LPCWSTR wzName 1061 __in BURN_ROLLBACK_BOUNDARY* pRollbackBoundary
1061 ) 1062 )
1062{ 1063{
1063 HRESULT hr = S_OK; 1064 HRESULT hr = S_OK;
1064 UINT uResult = ERROR_SUCCESS;
1065 1065
1066 LogId(REPORT_WARNING, MSG_MSI_TRANSACTION_ROLLBACK, wzName); 1066 LogId(REPORT_WARNING, MSG_MSI_TRANSACTION_ROLLBACK, pRollbackBoundary->sczId);
1067 1067
1068 uResult = ::MsiEndTransaction(MSITRANSACTIONSTATE_ROLLBACK); 1068 hr = WiuEndTransaction(MSITRANSACTIONSTATE_ROLLBACK, WIU_LOG_DEFAULT | INSTALLLOGMODE_VERBOSE, pRollbackBoundary->sczLogPath);
1069 ExitOnWin32Error(uResult, hr, "Failed to rollback the MSI transaction"); 1069 ExitOnFailure(hr, "Failed to rollback the MSI transaction");
1070 1070
1071LExit: 1071LExit:
1072 1072
diff --git a/src/engine/msiengine.h b/src/engine/msiengine.h
index e2dc5e82..99f97413 100644
--- a/src/engine/msiengine.h
+++ b/src/engine/msiengine.h
@@ -54,13 +54,13 @@ HRESULT MsiEnginePlanAddPackage(
54 __in BOOL fPlanPackageCacheRollback 54 __in BOOL fPlanPackageCacheRollback
55 ); 55 );
56HRESULT MsiEngineBeginTransaction( 56HRESULT MsiEngineBeginTransaction(
57 __in LPCWSTR wzName 57 __in BURN_ROLLBACK_BOUNDARY* pRollbackBoundary
58 ); 58 );
59HRESULT MsiEngineCommitTransaction( 59HRESULT MsiEngineCommitTransaction(
60 __in LPCWSTR wzName 60 __in BURN_ROLLBACK_BOUNDARY* pRollbackBoundary
61 ); 61 );
62HRESULT MsiEngineRollbackTransaction( 62HRESULT MsiEngineRollbackTransaction(
63 __in LPCWSTR wzName 63 __in BURN_ROLLBACK_BOUNDARY* pRollbackBoundary
64 ); 64 );
65HRESULT MsiEngineExecutePackage( 65HRESULT MsiEngineExecutePackage(
66 __in_opt HWND hwndParent, 66 __in_opt HWND hwndParent,
diff --git a/src/engine/package.cpp b/src/engine/package.cpp
index 115866f3..124b356b 100644
--- a/src/engine/package.cpp
+++ b/src/engine/package.cpp
@@ -377,6 +377,7 @@ extern "C" void PackagesUninitialize(
377 for (DWORD i = 0; i < pPackages->cRollbackBoundaries; ++i) 377 for (DWORD i = 0; i < pPackages->cRollbackBoundaries; ++i)
378 { 378 {
379 ReleaseStr(pPackages->rgRollbackBoundaries[i].sczId); 379 ReleaseStr(pPackages->rgRollbackBoundaries[i].sczId);
380 ReleaseStr(pPackages->rgRollbackBoundaries[i].sczLogPath);
380 } 381 }
381 MemFree(pPackages->rgRollbackBoundaries); 382 MemFree(pPackages->rgRollbackBoundaries);
382 } 383 }
@@ -511,6 +512,32 @@ LExit:
511 return hr; 512 return hr;
512} 513}
513 514
515extern "C" HRESULT PackageFindRollbackBoundaryById(
516 __in BURN_PACKAGES* pPackages,
517 __in_z LPCWSTR wzId,
518 __out BURN_ROLLBACK_BOUNDARY** ppRollbackBoundary
519 )
520{
521 HRESULT hr = S_OK;
522 BURN_ROLLBACK_BOUNDARY* pRollbackBoundary = NULL;
523
524 for (DWORD i = 0; i < pPackages->cRollbackBoundaries; ++i)
525 {
526 pRollbackBoundary = &pPackages->rgRollbackBoundaries[i];
527
528 if (CSTR_EQUAL == ::CompareStringW(LOCALE_INVARIANT, 0, pRollbackBoundary->sczId, -1, wzId, -1))
529 {
530 *ppRollbackBoundary = pRollbackBoundary;
531 ExitFunction1(hr = S_OK);
532 }
533 }
534
535 hr = E_NOTFOUND;
536
537LExit:
538 return hr;
539}
540
514 541
515// internal function declarations 542// internal function declarations
516 543
diff --git a/src/engine/package.h b/src/engine/package.h
index 3a95852e..42f1febe 100644
--- a/src/engine/package.h
+++ b/src/engine/package.h
@@ -214,6 +214,7 @@ typedef struct _BURN_ROLLBACK_BOUNDARY
214 BOOL fVital; 214 BOOL fVital;
215 BOOL fTransaction; 215 BOOL fTransaction;
216 BOOL fActiveTransaction; // only valid during Apply. 216 BOOL fActiveTransaction; // only valid during Apply.
217 LPWSTR sczLogPath;
217} BURN_ROLLBACK_BOUNDARY; 218} BURN_ROLLBACK_BOUNDARY;
218 219
219typedef struct _BURN_PATCH_TARGETCODE 220typedef struct _BURN_PATCH_TARGETCODE
@@ -386,6 +387,11 @@ HRESULT PackageGetProperty(
386 __in_z LPCWSTR wzProperty, 387 __in_z LPCWSTR wzProperty,
387 __out_z_opt LPWSTR* psczValue 388 __out_z_opt LPWSTR* psczValue
388 ); 389 );
390HRESULT PackageFindRollbackBoundaryById(
391 __in BURN_PACKAGES* pPackages,
392 __in_z LPCWSTR wzId,
393 __out BURN_ROLLBACK_BOUNDARY** ppRollbackBoundary
394 );
389 395
390 396
391#if defined(__cplusplus) 397#if defined(__cplusplus)
diff --git a/src/engine/plan.cpp b/src/engine/plan.cpp
index a4b8d0c1..65da4ab3 100644
--- a/src/engine/plan.cpp
+++ b/src/engine/plan.cpp
@@ -1946,6 +1946,7 @@ static void ResetPlannedRollbackBoundaryState(
1946 ) 1946 )
1947{ 1947{
1948 pRollbackBoundary->fActiveTransaction = FALSE; 1948 pRollbackBoundary->fActiveTransaction = FALSE;
1949 ReleaseNullStr(pRollbackBoundary->sczLogPath);
1949} 1950}
1950 1951
1951static HRESULT GetActionDefaultRequestState( 1952static HRESULT GetActionDefaultRequestState(
diff --git a/src/engine/userexperience.cpp b/src/engine/userexperience.cpp
index ad1529ea..5a225651 100644
--- a/src/engine/userexperience.cpp
+++ b/src/engine/userexperience.cpp
@@ -2117,16 +2117,6 @@ extern "C" int UserExperienceCheckExecuteResult(
2117 return nResult; 2117 return nResult;
2118} 2118}
2119 2119
2120extern "C" HRESULT UserExperienceInterpretResult(
2121 __in BURN_USER_EXPERIENCE* /*pUserExperience*/,
2122 __in DWORD dwAllowedResults,
2123 __in int nResult
2124 )
2125{
2126 int nFilteredResult = FilterResult(dwAllowedResults, nResult);
2127 return IDOK == nFilteredResult || IDNOACTION == nFilteredResult ? S_OK : IDCANCEL == nFilteredResult || IDABORT == nFilteredResult ? HRESULT_FROM_WIN32(ERROR_INSTALL_USEREXIT) : HRESULT_FROM_WIN32(ERROR_INSTALL_FAILURE);
2128}
2129
2130extern "C" HRESULT UserExperienceInterpretExecuteResult( 2120extern "C" HRESULT UserExperienceInterpretExecuteResult(
2131 __in BURN_USER_EXPERIENCE* pUserExperience, 2121 __in BURN_USER_EXPERIENCE* pUserExperience,
2132 __in BOOL fRollback, 2122 __in BOOL fRollback,
diff --git a/src/engine/userexperience.h b/src/engine/userexperience.h
index bac79e33..cef9d769 100644
--- a/src/engine/userexperience.h
+++ b/src/engine/userexperience.h
@@ -469,11 +469,6 @@ BAAPI UserExperienceOnUnregisterComplete(
469 __in BURN_USER_EXPERIENCE* pUserExperience, 469 __in BURN_USER_EXPERIENCE* pUserExperience,
470 __in HRESULT hrStatus 470 __in HRESULT hrStatus
471 ); 471 );
472HRESULT UserExperienceInterpretResult(
473 __in BURN_USER_EXPERIENCE* pUserExperience,
474 __in DWORD dwAllowedResults,
475 __in int nResult
476 );
477int UserExperienceCheckExecuteResult( 472int UserExperienceCheckExecuteResult(
478 __in BURN_USER_EXPERIENCE* pUserExperience, 473 __in BURN_USER_EXPERIENCE* pUserExperience,
479 __in BOOL fRollback, 474 __in BOOL fRollback,