aboutsummaryrefslogtreecommitdiff
path: root/src/engine/plan.cpp
diff options
context:
space:
mode:
authorSean Hall <r.sean.hall@gmail.com>2021-04-28 16:43:48 -0500
committerSean Hall <r.sean.hall@gmail.com>2021-04-29 14:05:34 -0500
commit752f0e0576dc27e937c553ed9dce5576bd388e95 (patch)
treef95013ccb3bdea206cf8879d6bbf2411a04663c6 /src/engine/plan.cpp
parent7099dd38ab902e7fb92706314fa8710a34f165a5 (diff)
downloadwix-752f0e0576dc27e937c553ed9dce5576bd388e95.tar.gz
wix-752f0e0576dc27e937c553ed9dce5576bd388e95.tar.bz2
wix-752f0e0576dc27e937c553ed9dce5576bd388e95.zip
Let BA override the package's cache type during Plan.
Rename cache types to REMOVE, KEEP, FORCE. Change implementation of FORCE to not be through CACHED request state. Create package condition enum so BA can tell when InstallCondition wasn't specified. Tell BA when package is cached. Tell BA when package is planned to be cached and uncached.
Diffstat (limited to 'src/engine/plan.cpp')
-rw-r--r--src/engine/plan.cpp97
1 files changed, 52 insertions, 45 deletions
diff --git a/src/engine/plan.cpp b/src/engine/plan.cpp
index e5c1ee36..9a4aa5f1 100644
--- a/src/engine/plan.cpp
+++ b/src/engine/plan.cpp
@@ -137,6 +137,10 @@ static BOOL NeedsCache(
137 __in BURN_PACKAGE* pPackage, 137 __in BURN_PACKAGE* pPackage,
138 __in BOOL fExecute 138 __in BOOL fExecute
139 ); 139 );
140static BOOL ForceCache(
141 __in BURN_PLAN* pPlan,
142 __in BURN_PACKAGE* pPackage
143 );
140 144
141// function definitions 145// function definitions
142 146
@@ -312,28 +316,20 @@ extern "C" HRESULT PlanDefaultPackageRequestState(
312 __in BURN_PACKAGE_TYPE packageType, 316 __in BURN_PACKAGE_TYPE packageType,
313 __in BOOTSTRAPPER_PACKAGE_STATE currentState, 317 __in BOOTSTRAPPER_PACKAGE_STATE currentState,
314 __in BOOL fPermanent, 318 __in BOOL fPermanent,
315 __in BURN_CACHE_TYPE cacheType,
316 __in BOOTSTRAPPER_ACTION action, 319 __in BOOTSTRAPPER_ACTION action,
317 __in BOOL fInstallCondition, 320 __in BOOTSTRAPPER_PACKAGE_CONDITION_RESULT installCondition,
318 __in BOOTSTRAPPER_RELATION_TYPE relationType, 321 __in BOOTSTRAPPER_RELATION_TYPE relationType,
319 __out BOOTSTRAPPER_REQUEST_STATE* pRequestState 322 __out BOOTSTRAPPER_REQUEST_STATE* pRequestState
320 ) 323 )
321{ 324{
322 HRESULT hr = S_OK; 325 HRESULT hr = S_OK;
323 BOOTSTRAPPER_REQUEST_STATE defaultRequestState = BOOTSTRAPPER_REQUEST_STATE_NONE; 326 BOOTSTRAPPER_REQUEST_STATE defaultRequestState = BOOTSTRAPPER_REQUEST_STATE_NONE;
324 BOOL fFallbackToCache = BURN_CACHE_TYPE_ALWAYS == cacheType && BOOTSTRAPPER_ACTION_UNINSTALL != action && BOOTSTRAPPER_PACKAGE_STATE_CACHED > currentState;
325 327
326 // If doing layout, then always default to requesting the file be cached. 328 // If doing layout, then always default to requesting the package be cached.
327 if (BOOTSTRAPPER_ACTION_LAYOUT == action) 329 if (BOOTSTRAPPER_ACTION_LAYOUT == action)
328 { 330 {
329 *pRequestState = BOOTSTRAPPER_REQUEST_STATE_CACHE; 331 *pRequestState = BOOTSTRAPPER_REQUEST_STATE_CACHE;
330 } 332 }
331 else if (BOOTSTRAPPER_PACKAGE_STATE_SUPERSEDED == currentState && BOOTSTRAPPER_ACTION_UNINSTALL != action)
332 {
333 // Superseded means the package is on the machine but not active, so only uninstall operations are allowed.
334 // Requesting present makes sure always-cached packages are cached.
335 *pRequestState = BOOTSTRAPPER_REQUEST_STATE_PRESENT;
336 }
337 else if (BOOTSTRAPPER_RELATION_PATCH == relationType && BURN_PACKAGE_TYPE_MSP == packageType) 333 else if (BOOTSTRAPPER_RELATION_PATCH == relationType && BURN_PACKAGE_TYPE_MSP == packageType)
338 { 334 {
339 // For patch related bundles, only install a patch if currently absent during install, modify, or repair. 335 // For patch related bundles, only install a patch if currently absent during install, modify, or repair.
@@ -341,20 +337,22 @@ extern "C" HRESULT PlanDefaultPackageRequestState(
341 { 337 {
342 *pRequestState = BOOTSTRAPPER_REQUEST_STATE_PRESENT; 338 *pRequestState = BOOTSTRAPPER_REQUEST_STATE_PRESENT;
343 } 339 }
344 else if (fFallbackToCache)
345 {
346 *pRequestState = BOOTSTRAPPER_REQUEST_STATE_CACHE;
347 }
348 else 340 else
349 { 341 {
350 *pRequestState = BOOTSTRAPPER_REQUEST_STATE_NONE; 342 *pRequestState = BOOTSTRAPPER_REQUEST_STATE_NONE;
351 } 343 }
352 } 344 }
345 else if (BOOTSTRAPPER_PACKAGE_STATE_SUPERSEDED == currentState && BOOTSTRAPPER_ACTION_UNINSTALL != action)
346 {
347 // Superseded means the package is on the machine but not active, so only uninstall operations are allowed.
348 // All other operations do nothing.
349 *pRequestState = BOOTSTRAPPER_REQUEST_STATE_NONE;
350 }
353 else if (BOOTSTRAPPER_PACKAGE_STATE_OBSOLETE == currentState && !(BOOTSTRAPPER_ACTION_UNINSTALL == action && BURN_PACKAGE_TYPE_MSP == packageType)) 351 else if (BOOTSTRAPPER_PACKAGE_STATE_OBSOLETE == currentState && !(BOOTSTRAPPER_ACTION_UNINSTALL == action && BURN_PACKAGE_TYPE_MSP == packageType))
354 { 352 {
355 // Obsolete means the package is not on the machine and should not be installed, *except* patches can be obsolete 353 // Obsolete means the package is not on the machine and should not be installed, *except* patches can be obsolete
356 // and present so allow them to be removed during uninstall. Everyone else, gets nothing. 354 // and present so allow them to be removed during uninstall. Everyone else, gets nothing.
357 *pRequestState = fFallbackToCache ? BOOTSTRAPPER_REQUEST_STATE_CACHE : BOOTSTRAPPER_REQUEST_STATE_NONE; 355 *pRequestState = BOOTSTRAPPER_REQUEST_STATE_NONE;
358 } 356 }
359 else // pick the best option for the action state and install condition. 357 else // pick the best option for the action state and install condition.
360 { 358 {
@@ -363,7 +361,7 @@ extern "C" HRESULT PlanDefaultPackageRequestState(
363 361
364 // If we're doing an install, use the install condition 362 // If we're doing an install, use the install condition
365 // to determine whether to use the default request state or make the package absent. 363 // to determine whether to use the default request state or make the package absent.
366 if (BOOTSTRAPPER_ACTION_UNINSTALL != action && !fInstallCondition) 364 if (BOOTSTRAPPER_ACTION_UNINSTALL != action && BOOTSTRAPPER_PACKAGE_CONDITION_FALSE == installCondition)
367 { 365 {
368 *pRequestState = BOOTSTRAPPER_REQUEST_STATE_ABSENT; 366 *pRequestState = BOOTSTRAPPER_REQUEST_STATE_ABSENT;
369 } 367 }
@@ -371,11 +369,6 @@ extern "C" HRESULT PlanDefaultPackageRequestState(
371 { 369 {
372 *pRequestState = defaultRequestState; 370 *pRequestState = defaultRequestState;
373 } 371 }
374
375 if (fFallbackToCache && BOOTSTRAPPER_REQUEST_STATE_CACHE > *pRequestState)
376 {
377 *pRequestState = BOOTSTRAPPER_REQUEST_STATE_CACHE;
378 }
379 } 372 }
380 373
381LExit: 374LExit:
@@ -844,8 +837,8 @@ static HRESULT PlanPackagesHelper(
844 { 837 {
845 DWORD iPackage = (BOOTSTRAPPER_ACTION_UNINSTALL == pPlan->action) ? cPackages - 1 - i : i; 838 DWORD iPackage = (BOOTSTRAPPER_ACTION_UNINSTALL == pPlan->action) ? cPackages - 1 - i : i;
846 BURN_PACKAGE* pPackage = rgPackages + iPackage; 839 BURN_PACKAGE* pPackage = rgPackages + iPackage;
847 840
848 UserExperienceOnPlannedPackage(pUX, pPackage->sczId, pPackage->execute, pPackage->rollback); 841 UserExperienceOnPlannedPackage(pUX, pPackage->sczId, pPackage->execute, pPackage->rollback, pPackage->fPlannedCache, pPackage->fPlannedUncache);
849 } 842 }
850 843
851LExit: 844LExit:
@@ -861,6 +854,7 @@ static HRESULT InitializePackage(
861 ) 854 )
862{ 855{
863 HRESULT hr = S_OK; 856 HRESULT hr = S_OK;
857 BOOTSTRAPPER_PACKAGE_CONDITION_RESULT installCondition = BOOTSTRAPPER_PACKAGE_CONDITION_DEFAULT;
864 BOOL fInstallCondition = FALSE; 858 BOOL fInstallCondition = FALSE;
865 BOOL fBeginCalled = FALSE; 859 BOOL fBeginCalled = FALSE;
866 860
@@ -874,20 +868,18 @@ static HRESULT InitializePackage(
874 { 868 {
875 hr = ConditionEvaluate(pVariables, pPackage->sczInstallCondition, &fInstallCondition); 869 hr = ConditionEvaluate(pVariables, pPackage->sczInstallCondition, &fInstallCondition);
876 ExitOnFailure(hr, "Failed to evaluate install condition."); 870 ExitOnFailure(hr, "Failed to evaluate install condition.");
877 } 871
878 else 872 installCondition = fInstallCondition ? BOOTSTRAPPER_PACKAGE_CONDITION_TRUE : BOOTSTRAPPER_PACKAGE_CONDITION_FALSE;
879 {
880 fInstallCondition = TRUE;
881 } 873 }
882 874
883 // Remember the default requested state so the engine doesn't get blamed for planning the wrong thing if the BA changes it. 875 // Remember the default requested state so the engine doesn't get blamed for planning the wrong thing if the BA changes it.
884 hr = PlanDefaultPackageRequestState(pPackage->type, pPackage->currentState, !pPackage->fUninstallable, pPackage->cacheType, pPlan->action, fInstallCondition, relationType, &pPackage->defaultRequested); 876 hr = PlanDefaultPackageRequestState(pPackage->type, pPackage->currentState, !pPackage->fUninstallable, pPlan->action, installCondition, relationType, &pPackage->defaultRequested);
885 ExitOnFailure(hr, "Failed to set default package state."); 877 ExitOnFailure(hr, "Failed to set default package state.");
886 878
887 pPackage->requested = pPackage->defaultRequested; 879 pPackage->requested = pPackage->defaultRequested;
888 fBeginCalled = TRUE; 880 fBeginCalled = TRUE;
889 881
890 hr = UserExperienceOnPlanPackageBegin(pUX, pPackage->sczId, pPackage->currentState, fInstallCondition, &pPackage->requested); 882 hr = UserExperienceOnPlanPackageBegin(pUX, pPackage->sczId, pPackage->currentState, pPackage->fCached, installCondition, &pPackage->requested, &pPackage->cacheType);
891 ExitOnRootFailure(hr, "BA aborted plan package begin."); 883 ExitOnRootFailure(hr, "BA aborted plan package begin.");
892 884
893 if (BURN_PACKAGE_TYPE_MSI == pPackage->type) 885 if (BURN_PACKAGE_TYPE_MSI == pPackage->type)
@@ -926,8 +918,11 @@ static HRESULT ProcessPackage(
926 918
927 if (BOOTSTRAPPER_ACTION_LAYOUT == pPlan->action) 919 if (BOOTSTRAPPER_ACTION_LAYOUT == pPlan->action)
928 { 920 {
929 hr = PlanLayoutPackage(pPlan, pPackage); 921 if (BOOTSTRAPPER_REQUEST_STATE_NONE != pPackage->requested)
930 ExitOnFailure(hr, "Failed to plan layout package."); 922 {
923 hr = PlanLayoutPackage(pPlan, pPackage);
924 ExitOnFailure(hr, "Failed to plan layout package.");
925 }
931 } 926 }
932 else 927 else
933 { 928 {
@@ -939,6 +934,17 @@ static HRESULT ProcessPackage(
939 } 934 }
940 else 935 else
941 { 936 {
937 if (ForceCache(pPlan, pPackage))
938 {
939 hr = AddCachePackage(pPlan, pPackage, phSyncpointEvent);
940 ExitOnFailure(hr, "Failed to plan cache package.");
941
942 if (pPackage->fPerMachine)
943 {
944 pPlan->fPerMachine = TRUE;
945 }
946 }
947
942 // Make sure the package is properly ref-counted even if no plan is requested. 948 // Make sure the package is properly ref-counted even if no plan is requested.
943 hr = PlanDependencyActions(fBundlePerMachine, pPlan, pPackage); 949 hr = PlanDependencyActions(fBundlePerMachine, pPlan, pPackage);
944 ExitOnFailure(hr, "Failed to plan dependency actions for package: %ls", pPackage->sczId); 950 ExitOnFailure(hr, "Failed to plan dependency actions for package: %ls", pPackage->sczId);
@@ -1072,8 +1078,7 @@ extern "C" HRESULT PlanExecutePackage(
1072 ) 1078 )
1073{ 1079{
1074 HRESULT hr = S_OK; 1080 HRESULT hr = S_OK;
1075 BOOL fRequestedCache = BOOTSTRAPPER_REQUEST_STATE_CACHE == pPackage->requested || 1081 BOOL fRequestedCache = BOOTSTRAPPER_REQUEST_STATE_CACHE == pPackage->requested || ForceCache(pPlan, pPackage);
1076 BOOTSTRAPPER_REQUEST_STATE_ABSENT < pPackage->requested && BURN_CACHE_TYPE_ALWAYS == pPackage->cacheType;
1077 1082
1078 hr = CalculateExecuteActions(pPackage, pPlan->pActiveRollbackBoundary); 1083 hr = CalculateExecuteActions(pPackage, pPlan->pActiveRollbackBoundary);
1079 ExitOnFailure(hr, "Failed to calculate plan actions for package: %ls", pPackage->sczId); 1084 ExitOnFailure(hr, "Failed to calculate plan actions for package: %ls", pPackage->sczId);
@@ -1097,12 +1102,12 @@ extern "C" HRESULT PlanExecutePackage(
1097 1102
1098 // Add the cache and install size to estimated size if it will be on the machine at the end of the install 1103 // Add the cache and install size to estimated size if it will be on the machine at the end of the install
1099 if (BOOTSTRAPPER_REQUEST_STATE_PRESENT == pPackage->requested || 1104 if (BOOTSTRAPPER_REQUEST_STATE_PRESENT == pPackage->requested ||
1100 BOOTSTRAPPER_REQUEST_STATE_CACHE == pPackage->requested || 1105 fRequestedCache ||
1101 (BOOTSTRAPPER_PACKAGE_STATE_PRESENT == pPackage->currentState && BOOTSTRAPPER_REQUEST_STATE_ABSENT < pPackage->requested) 1106 (BOOTSTRAPPER_PACKAGE_STATE_PRESENT == pPackage->currentState && BOOTSTRAPPER_REQUEST_STATE_ABSENT < pPackage->requested)
1102 ) 1107 )
1103 { 1108 {
1104 // If the package will remain in the cache, add the package size to the estimated size 1109 // If the package will remain in the cache, add the package size to the estimated size
1105 if (BURN_CACHE_TYPE_NO < pPackage->cacheType) 1110 if (BOOTSTRAPPER_CACHE_TYPE_REMOVE < pPackage->cacheType)
1106 { 1111 {
1107 pPlan->qwEstimatedSize += pPackage->qwSize; 1112 pPlan->qwEstimatedSize += pPackage->qwSize;
1108 } 1113 }
@@ -1522,12 +1527,12 @@ extern "C" HRESULT PlanCleanPackage(
1522 BURN_CLEAN_ACTION* pCleanAction = NULL; 1527 BURN_CLEAN_ACTION* pCleanAction = NULL;
1523 1528
1524 // The following is a complex set of logic that determines when a package should be cleaned from the cache. 1529 // The following is a complex set of logic that determines when a package should be cleaned from the cache.
1525 if (BURN_CACHE_TYPE_ALWAYS > pPackage->cacheType || BOOTSTRAPPER_ACTION_CACHE > pPlan->action) 1530 if (BOOTSTRAPPER_CACHE_TYPE_FORCE > pPackage->cacheType || BOOTSTRAPPER_ACTION_CACHE > pPlan->action)
1526 { 1531 {
1527 // The following are all different reasons why the package should be cleaned from the cache. 1532 // The following are all different reasons why the package should be cleaned from the cache.
1528 // The else-ifs are used to make the conditions easier to see (rather than have them combined 1533 // The else-ifs are used to make the conditions easier to see (rather than have them combined
1529 // in one huge condition). 1534 // in one huge condition).
1530 if (BURN_CACHE_TYPE_YES > pPackage->cacheType) // easy, package is not supposed to stay cached. 1535 if (BOOTSTRAPPER_CACHE_TYPE_KEEP > pPackage->cacheType) // easy, package is not supposed to stay cached.
1531 { 1536 {
1532 fPlanCleanPackage = TRUE; 1537 fPlanCleanPackage = TRUE;
1533 } 1538 }
@@ -1867,6 +1872,7 @@ static void ResetPlannedPackageState(
1867 ) 1872 )
1868{ 1873{
1869 // Reset package state that is a result of planning. 1874 // Reset package state that is a result of planning.
1875 pPackage->cacheType = pPackage->authoredCacheType;
1870 pPackage->defaultRequested = BOOTSTRAPPER_REQUEST_STATE_NONE; 1876 pPackage->defaultRequested = BOOTSTRAPPER_REQUEST_STATE_NONE;
1871 pPackage->requested = BOOTSTRAPPER_REQUEST_STATE_NONE; 1877 pPackage->requested = BOOTSTRAPPER_REQUEST_STATE_NONE;
1872 pPackage->fPlannedCache = FALSE; 1878 pPackage->fPlannedCache = FALSE;
@@ -1948,10 +1954,6 @@ static HRESULT GetActionDefaultRequestState(
1948 *pRequestState = BOOTSTRAPPER_REQUEST_STATE_PRESENT; 1954 *pRequestState = BOOTSTRAPPER_REQUEST_STATE_PRESENT;
1949 break; 1955 break;
1950 1956
1951 case BOOTSTRAPPER_PACKAGE_STATE_CACHED:
1952 *pRequestState = BOOTSTRAPPER_REQUEST_STATE_NONE;
1953 break;
1954
1955 default: 1957 default:
1956 *pRequestState = BOOTSTRAPPER_REQUEST_STATE_CACHE; 1958 *pRequestState = BOOTSTRAPPER_REQUEST_STATE_CACHE;
1957 break; 1959 break;
@@ -1979,10 +1981,6 @@ static HRESULT GetActionDefaultRequestState(
1979 *pRequestState = BOOTSTRAPPER_REQUEST_STATE_ABSENT; 1981 *pRequestState = BOOTSTRAPPER_REQUEST_STATE_ABSENT;
1980 break; 1982 break;
1981 1983
1982 case BOOTSTRAPPER_PACKAGE_STATE_CACHED:
1983 *pRequestState = BOOTSTRAPPER_REQUEST_STATE_CACHE;
1984 break;
1985
1986 case BOOTSTRAPPER_PACKAGE_STATE_PRESENT: 1984 case BOOTSTRAPPER_PACKAGE_STATE_PRESENT:
1987 *pRequestState = BOOTSTRAPPER_REQUEST_STATE_PRESENT; 1985 *pRequestState = BOOTSTRAPPER_REQUEST_STATE_PRESENT;
1988 break; 1986 break;
@@ -2524,6 +2522,15 @@ static BOOL NeedsCache(
2524 } 2522 }
2525} 2523}
2526 2524
2525static BOOL ForceCache(
2526 __in BURN_PLAN* pPlan,
2527 __in BURN_PACKAGE* pPackage
2528 )
2529{
2530 // All packages that have cacheType set to force should be cached if the bundle is going to be present.
2531 return BOOTSTRAPPER_CACHE_TYPE_FORCE == pPackage->cacheType && BOOTSTRAPPER_ACTION_UNINSTALL < pPlan->action;
2532}
2533
2527static void CacheActionLog( 2534static void CacheActionLog(
2528 __in DWORD iAction, 2535 __in DWORD iAction,
2529 __in BURN_CACHE_ACTION* pAction, 2536 __in BURN_CACHE_ACTION* pAction,