summaryrefslogtreecommitdiff
path: root/src/ext/Bal/wixstdba/WixStandardBootstrapperApplication.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'src/ext/Bal/wixstdba/WixStandardBootstrapperApplication.cpp')
-rw-r--r--src/ext/Bal/wixstdba/WixStandardBootstrapperApplication.cpp179
1 files changed, 159 insertions, 20 deletions
diff --git a/src/ext/Bal/wixstdba/WixStandardBootstrapperApplication.cpp b/src/ext/Bal/wixstdba/WixStandardBootstrapperApplication.cpp
index 3774f49c..9c0f9576 100644
--- a/src/ext/Bal/wixstdba/WixStandardBootstrapperApplication.cpp
+++ b/src/ext/Bal/wixstdba/WixStandardBootstrapperApplication.cpp
@@ -30,6 +30,8 @@ enum WIXSTDBA_STATE
30 WIXSTDBA_STATE_HELP, 30 WIXSTDBA_STATE_HELP,
31 WIXSTDBA_STATE_DETECTING, 31 WIXSTDBA_STATE_DETECTING,
32 WIXSTDBA_STATE_DETECTED, 32 WIXSTDBA_STATE_DETECTED,
33 WIXSTDBA_STATE_PLANNING_PREREQS,
34 WIXSTDBA_STATE_PLANNED_PREREQS,
33 WIXSTDBA_STATE_PLANNING, 35 WIXSTDBA_STATE_PLANNING,
34 WIXSTDBA_STATE_PLANNED, 36 WIXSTDBA_STATE_PLANNED,
35 WIXSTDBA_STATE_APPLYING, 37 WIXSTDBA_STATE_APPLYING,
@@ -49,6 +51,7 @@ enum WM_WIXSTDBA
49 WM_WIXSTDBA_APPLY_PACKAGES, 51 WM_WIXSTDBA_APPLY_PACKAGES,
50 WM_WIXSTDBA_CHANGE_STATE, 52 WM_WIXSTDBA_CHANGE_STATE,
51 WM_WIXSTDBA_SHOW_FAILURE, 53 WM_WIXSTDBA_SHOW_FAILURE,
54 WM_WIXSTDBA_PLAN_PREREQS,
52}; 55};
53 56
54// This enum must be kept in the same order as the vrgwzPageNames array. 57// This enum must be kept in the same order as the vrgwzPageNames array.
@@ -217,9 +220,11 @@ public: // IBootstrapperApplication
217 : "A restart is required by the prerequisites but the user delayed it. The bootstrapper application will be reloaded after the computer is restarted."); 220 : "A restart is required by the prerequisites but the user delayed it. The bootstrapper application will be reloaded after the computer is restarted.");
218 } 221 }
219 } 222 }
220 else if (m_fPrereqInstalled) 223 else if (m_fPrereqInstalled || m_fPrereqSkipped)
221 { 224 {
222 BalLog(BOOTSTRAPPER_LOG_LEVEL_STANDARD, "The prerequisites were successfully installed. The bootstrapper application will be reloaded."); 225 BalLog(BOOTSTRAPPER_LOG_LEVEL_STANDARD, m_fPrereqInstalled
226 ? "The prerequisites were successfully installed. The bootstrapper application will be reloaded."
227 : "The prerequisites were already installed. The bootstrapper application will be reloaded.");
223 *pAction = BOOTSTRAPPER_SHUTDOWN_ACTION_RELOAD_BOOTSTRAPPER; 228 *pAction = BOOTSTRAPPER_SHUTDOWN_ACTION_RELOAD_BOOTSTRAPPER;
224 m_pPrereqData->fCompleted = TRUE; 229 m_pPrereqData->fCompleted = TRUE;
225 } 230 }
@@ -275,13 +280,16 @@ public: // IBootstrapperApplication
275 hr = S_OK; 280 hr = S_OK;
276 } 281 }
277 282
278 // If the UI should be visible, display it now and hide the splash screen 283 if (!m_fPreplanPrereqs)
279 if (BOOTSTRAPPER_DISPLAY_NONE < m_command.display)
280 { 284 {
281 ::ShowWindow(m_pTheme->hwndParent, SW_SHOW); 285 // If the UI should be visible, display it now and hide the splash screen
282 } 286 if (BOOTSTRAPPER_DISPLAY_NONE < m_command.display)
287 {
288 ::ShowWindow(m_pTheme->hwndParent, SW_SHOW);
289 }
283 290
284 m_pEngine->CloseSplashScreen(); 291 m_pEngine->CloseSplashScreen();
292 }
285 293
286 return __super::OnDetectBegin(fCached, registrationType, cPackages, pfCancel); 294 return __super::OnDetectBegin(fCached, registrationType, cPackages, pfCancel);
287 } 295 }
@@ -331,24 +339,37 @@ public: // IBootstrapperApplication
331 if (fEvaluateConditions) 339 if (fEvaluateConditions)
332 { 340 {
333 hrStatus = EvaluateConditions(); 341 hrStatus = EvaluateConditions();
334
335 if (FAILED(hrStatus))
336 {
337 fSkipToPlan = FALSE;
338 }
339 } 342 }
340 343
341 SetState(WIXSTDBA_STATE_DETECTED, hrStatus); 344 SetState(WIXSTDBA_STATE_DETECTED, hrStatus);
342 345
343 if (fSkipToPlan) 346 if (SUCCEEDED(hrStatus))
344 { 347 {
345 ::PostMessageW(m_hWnd, WM_WIXSTDBA_PLAN_PACKAGES, 0, m_command.action); 348 if (m_fPreplanPrereqs)
349 {
350 ::PostMessageW(m_hWnd, WM_WIXSTDBA_PLAN_PREREQS, 0, BOOTSTRAPPER_ACTION_INSTALL);
351 }
352 else if (fSkipToPlan)
353 {
354 ::PostMessageW(m_hWnd, WM_WIXSTDBA_PLAN_PACKAGES, 0, m_command.action);
355 }
346 } 356 }
347 357
348 return hr; 358 return hr;
349 } 359 }
350 360
351 361
362 virtual STDMETHODIMP OnPlanBegin(
363 __in DWORD cPackages,
364 __in BOOL* pfCancel
365 )
366 {
367 m_fPrereqPackagePlanned = FALSE;
368
369 return __super::OnPlanBegin(cPackages, pfCancel);
370 }
371
372
352 virtual STDMETHODIMP OnPlanRelatedBundleType( 373 virtual STDMETHODIMP OnPlanRelatedBundleType(
353 __in_z LPCWSTR wzBundleId, 374 __in_z LPCWSTR wzBundleId,
354 __in BOOTSTRAPPER_RELATED_BUNDLE_PLAN_TYPE recommendedType, 375 __in BOOTSTRAPPER_RELATED_BUNDLE_PLAN_TYPE recommendedType,
@@ -484,24 +505,97 @@ public: // IBootstrapperApplication
484 } 505 }
485 506
486 507
508 virtual STDMETHODIMP OnPlannedPackage(
509 __in_z LPCWSTR wzPackageId,
510 __in BOOTSTRAPPER_ACTION_STATE execute,
511 __in BOOTSTRAPPER_ACTION_STATE rollback,
512 __in BOOL fPlannedCache,
513 __in BOOL fPlannedUncache
514 )
515 {
516 if (m_fPrereq && BOOTSTRAPPER_ACTION_STATE_NONE != execute)
517 {
518 m_fPrereqPackagePlanned = TRUE;
519 }
520
521 return __super::OnPlannedPackage(wzPackageId, execute, rollback, fPlannedCache, fPlannedUncache);
522 }
523
524
487 virtual STDMETHODIMP OnPlanComplete( 525 virtual STDMETHODIMP OnPlanComplete(
488 __in HRESULT hrStatus 526 __in HRESULT hrStatus
489 ) 527 )
490 { 528 {
491 HRESULT hr = S_OK; 529 HRESULT hr = S_OK;
530 BOOL fPlannedPrereqs = WIXSTDBA_STATE_PLANNING_PREREQS == m_state;
531 WIXSTDBA_STATE completedState = WIXSTDBA_STATE_PLANNED;
532 BOOL fApply = TRUE;
492 533
493 SetState(WIXSTDBA_STATE_PLANNED, hrStatus); 534 if (fPlannedPrereqs)
535 {
536 if (SUCCEEDED(hrStatus) && !m_fPrereqPackagePlanned)
537 {
538 // Nothing to do, so close and let the parent BA take over.
539 m_fPrereqSkipped = TRUE;
540 SetState(WIXSTDBA_STATE_APPLIED, S_OK);
541 ExitFunction();
542 }
543 else if (BOOTSTRAPPER_ACTION_HELP == m_command.action)
544 {
545 // If prereq packages were planned then the managed BA probably can't be loaded, so show the help from this BA.
494 546
495 if (SUCCEEDED(hrStatus)) 547 // Need to force the state change since normally moving backwards is prevented.
548 ::PostMessageW(m_hWnd, WM_WIXSTDBA_CHANGE_STATE, 0, WIXSTDBA_STATE_HELP);
549
550 ::PostMessageW(m_hWnd, WM_WIXSTDBA_SHOW_HELP, 0, 0);
551
552 ExitFunction();
553 }
554
555 completedState = WIXSTDBA_STATE_PLANNED_PREREQS;
556 }
557
558 SetState(completedState, hrStatus);
559
560 if (FAILED(hrStatus))
561 {
562 ExitFunction();
563 }
564
565 if (fPlannedPrereqs)
566 {
567 // If the UI should be visible, display it now and hide the splash screen
568 if (BOOTSTRAPPER_DISPLAY_NONE < m_command.display)
569 {
570 ::ShowWindow(m_pTheme->hwndParent, SW_SHOW);
571 }
572
573 m_pEngine->CloseSplashScreen();
574
575 fApply = BOOTSTRAPPER_DISPLAY_FULL > m_command.display ||
576 BOOTSTRAPPER_RESUME_TYPE_REBOOT == m_command.resumeType;
577 }
578
579 if (fApply)
496 { 580 {
497 ::PostMessageW(m_hWnd, WM_WIXSTDBA_APPLY_PACKAGES, 0, 0); 581 ::PostMessageW(m_hWnd, WM_WIXSTDBA_APPLY_PACKAGES, 0, 0);
498 } 582 }
499 583
584 LExit:
585 return hr;
586 }
587
588
589 virtual STDMETHODIMP OnApplyBegin(
590 __in DWORD dwPhaseCount,
591 __in BOOL* pfCancel
592 )
593 {
500 m_fStartedExecution = FALSE; 594 m_fStartedExecution = FALSE;
501 m_dwCalculatedCacheProgress = 0; 595 m_dwCalculatedCacheProgress = 0;
502 m_dwCalculatedExecuteProgress = 0; 596 m_dwCalculatedExecuteProgress = 0;
503 597
504 return hr; 598 return __super::OnApplyBegin(dwPhaseCount, pfCancel);
505 } 599 }
506 600
507 601
@@ -2149,6 +2243,7 @@ private:
2149 BOOL fRet = FALSE; 2243 BOOL fRet = FALSE;
2150 MSG msg = { }; 2244 MSG msg = { };
2151 DWORD dwQuit = 0; 2245 DWORD dwQuit = 0;
2246 WM_WIXSTDBA firstAction = WM_WIXSTDBA_DETECT_PACKAGES;
2152 2247
2153 // Initialize COM and theme. 2248 // Initialize COM and theme.
2154 hr = ::CoInitialize(NULL); 2249 hr = ::CoInitialize(NULL);
@@ -2169,15 +2264,21 @@ private:
2169 if (FAILED(pThis->m_hrFinal)) 2264 if (FAILED(pThis->m_hrFinal))
2170 { 2265 {
2171 pThis->SetState(WIXSTDBA_STATE_FAILED, hr); 2266 pThis->SetState(WIXSTDBA_STATE_FAILED, hr);
2172 ::PostMessageW(pThis->m_hWnd, WM_WIXSTDBA_SHOW_FAILURE, 0, 0); 2267 firstAction = WM_WIXSTDBA_SHOW_FAILURE;
2173 } 2268 }
2174 else 2269 else
2175 { 2270 {
2176 // Okay, we're ready for packages now. 2271 // Okay, we're ready for packages now.
2177 pThis->SetState(WIXSTDBA_STATE_INITIALIZED, hr); 2272 pThis->SetState(WIXSTDBA_STATE_INITIALIZED, hr);
2178 ::PostMessageW(pThis->m_hWnd, BOOTSTRAPPER_ACTION_HELP == pThis->m_command.action ? WM_WIXSTDBA_SHOW_HELP : WM_WIXSTDBA_DETECT_PACKAGES, 0, 0); 2273
2274 if (!pThis->m_fPreplanPrereqs && BOOTSTRAPPER_ACTION_HELP == pThis->m_command.action)
2275 {
2276 firstAction = WM_WIXSTDBA_SHOW_HELP;
2277 }
2179 } 2278 }
2180 2279
2280 ::PostMessageW(pThis->m_hWnd, firstAction, 0, 0);
2281
2181 // message pump 2282 // message pump
2182 while (0 != (fRet = ::GetMessageW(&msg, NULL, 0, 0))) 2283 while (0 != (fRet = ::GetMessageW(&msg, NULL, 0, 0)))
2183 { 2284 {
@@ -2647,7 +2748,7 @@ private:
2647 2748
2648 // Calculate the window style based on the theme style and command display value. 2749 // Calculate the window style based on the theme style and command display value.
2649 dwWindowStyle = m_pTheme->dwStyle; 2750 dwWindowStyle = m_pTheme->dwStyle;
2650 if (BOOTSTRAPPER_DISPLAY_NONE >= m_command.display) 2751 if (BOOTSTRAPPER_DISPLAY_NONE >= m_command.display || m_fPreplanPrereqs)
2651 { 2752 {
2652 dwWindowStyle &= ~WS_VISIBLE; 2753 dwWindowStyle &= ~WS_VISIBLE;
2653 } 2754 }
@@ -2850,6 +2951,10 @@ private:
2850 pBA->OnShowFailure(); 2951 pBA->OnShowFailure();
2851 return 0; 2952 return 0;
2852 2953
2954 case WM_WIXSTDBA_PLAN_PREREQS:
2955 pBA->OnPlanPrereqs(static_cast<BOOTSTRAPPER_ACTION>(lParam));
2956 return 0;
2957
2853 case WM_THMUTIL_CONTROL_WM_COMMAND: 2958 case WM_THMUTIL_CONTROL_WM_COMMAND:
2854 return pBA->OnThemeControlWmCommand(reinterpret_cast<THEME_CONTROLWMCOMMAND_ARGS*>(wParam), reinterpret_cast<THEME_CONTROLWMCOMMAND_RESULTS*>(lParam)); 2959 return pBA->OnThemeControlWmCommand(reinterpret_cast<THEME_CONTROLWMCOMMAND_ARGS*>(wParam), reinterpret_cast<THEME_CONTROLWMCOMMAND_RESULTS*>(lParam));
2855 2960
@@ -3141,6 +3246,30 @@ private:
3141 3246
3142 3247
3143 // 3248 //
3249 // OnPlanPrereqs - preplan the packages to see if the preqba can be skipped.
3250 //
3251 void OnPlanPrereqs(
3252 __in BOOTSTRAPPER_ACTION action
3253 )
3254 {
3255 HRESULT hr = S_OK;
3256
3257 m_plannedAction = action;
3258
3259 SetState(WIXSTDBA_STATE_PLANNING_PREREQS, hr);
3260
3261 hr = m_pEngine->Plan(action);
3262 BalExitOnFailure(hr, "Failed to start planning prereq packages.");
3263
3264 LExit:
3265 if (FAILED(hr))
3266 {
3267 SetState(WIXSTDBA_STATE_PLANNING_PREREQS, hr);
3268 }
3269 }
3270
3271
3272 //
3144 // OnApply - apply the packages. 3273 // OnApply - apply the packages.
3145 // 3274 //
3146 void OnApply() 3275 void OnApply()
@@ -3838,6 +3967,8 @@ LExit:
3838 break; 3967 break;
3839 3968
3840 case WIXSTDBA_STATE_DETECTED: __fallthrough; 3969 case WIXSTDBA_STATE_DETECTED: __fallthrough;
3970 case WIXSTDBA_STATE_PLANNING_PREREQS: __fallthrough;
3971 case WIXSTDBA_STATE_PLANNED_PREREQS: __fallthrough;
3841 case WIXSTDBA_STATE_PLANNING: __fallthrough; 3972 case WIXSTDBA_STATE_PLANNING: __fallthrough;
3842 case WIXSTDBA_STATE_PLANNED: __fallthrough; 3973 case WIXSTDBA_STATE_PLANNED: __fallthrough;
3843 case WIXSTDBA_STATE_APPLYING: __fallthrough; 3974 case WIXSTDBA_STATE_APPLYING: __fallthrough;
@@ -3874,6 +4005,8 @@ LExit:
3874 break; 4005 break;
3875 4006
3876 case WIXSTDBA_STATE_DETECTED: 4007 case WIXSTDBA_STATE_DETECTED:
4008 case WIXSTDBA_STATE_PLANNING_PREREQS: __fallthrough;
4009 case WIXSTDBA_STATE_PLANNED_PREREQS: __fallthrough;
3877 switch (m_command.action) 4010 switch (m_command.action)
3878 { 4011 {
3879 case BOOTSTRAPPER_ACTION_INSTALL: 4012 case BOOTSTRAPPER_ACTION_INSTALL:
@@ -4124,7 +4257,10 @@ public:
4124 4257
4125 m_pPrereqData = pPrereqData; 4258 m_pPrereqData = pPrereqData;
4126 m_fPrereq = NULL != pPrereqData; 4259 m_fPrereq = NULL != pPrereqData;
4260 m_fPreplanPrereqs = m_fPrereq && m_pPrereqData->fAlwaysInstallPrereqs;
4261 m_fPrereqPackagePlanned = FALSE;
4127 m_fPrereqInstalled = FALSE; 4262 m_fPrereqInstalled = FALSE;
4263 m_fPrereqSkipped = FALSE;
4128 4264
4129 pEngine->AddRef(); 4265 pEngine->AddRef();
4130 m_pEngine = pEngine; 4266 m_pEngine = pEngine;
@@ -4405,7 +4541,10 @@ private:
4405 4541
4406 PREQBA_DATA* m_pPrereqData; 4542 PREQBA_DATA* m_pPrereqData;
4407 BOOL m_fPrereq; 4543 BOOL m_fPrereq;
4544 BOOL m_fPreplanPrereqs;
4545 BOOL m_fPrereqPackagePlanned;
4408 BOOL m_fPrereqInstalled; 4546 BOOL m_fPrereqInstalled;
4547 BOOL m_fPrereqSkipped;
4409 4548
4410 ITaskbarList3* m_pTaskbarList; 4549 ITaskbarList3* m_pTaskbarList;
4411 UINT m_uTaskbarButtonCreatedMessage; 4550 UINT m_uTaskbarButtonCreatedMessage;