diff options
Diffstat (limited to 'src/burn/engine/externalengine.cpp')
-rw-r--r-- | src/burn/engine/externalengine.cpp | 166 |
1 files changed, 115 insertions, 51 deletions
diff --git a/src/burn/engine/externalengine.cpp b/src/burn/engine/externalengine.cpp index 5e540c2a..262bb1a9 100644 --- a/src/burn/engine/externalengine.cpp +++ b/src/burn/engine/externalengine.cpp | |||
@@ -13,6 +13,10 @@ static HRESULT ProcessUnknownEmbeddedMessages( | |||
13 | __in_opt LPVOID /*pvContext*/, | 13 | __in_opt LPVOID /*pvContext*/, |
14 | __out DWORD* pdwResult | 14 | __out DWORD* pdwResult |
15 | ); | 15 | ); |
16 | static HRESULT EnqueueAction( | ||
17 | __in BOOTSTRAPPER_ENGINE_CONTEXT* pEngineContext, | ||
18 | __inout BOOTSTRAPPER_ENGINE_ACTION** ppAction | ||
19 | ); | ||
16 | 20 | ||
17 | // function definitions | 21 | // function definitions |
18 | 22 | ||
@@ -582,69 +586,91 @@ HRESULT ExternalEngineCompareVersions( | |||
582 | } | 586 | } |
583 | 587 | ||
584 | HRESULT ExternalEngineDetect( | 588 | HRESULT ExternalEngineDetect( |
585 | __in const DWORD dwThreadId, | 589 | __in BOOTSTRAPPER_ENGINE_CONTEXT* pEngineContext, |
586 | __in_opt const HWND hwndParent | 590 | __in_opt const HWND hwndParent |
587 | ) | 591 | ) |
588 | { | 592 | { |
589 | HRESULT hr = S_OK; | 593 | HRESULT hr = S_OK; |
594 | BOOTSTRAPPER_ENGINE_ACTION* pAction = NULL; | ||
590 | 595 | ||
591 | if (!::PostThreadMessageW(dwThreadId, WM_BURN_DETECT, 0, reinterpret_cast<LPARAM>(hwndParent))) | 596 | pAction = (BOOTSTRAPPER_ENGINE_ACTION*)MemAlloc(sizeof(BOOTSTRAPPER_ENGINE_ACTION), TRUE); |
592 | { | 597 | ExitOnNull(pAction, hr, E_OUTOFMEMORY, "Failed to alloc BOOTSTRAPPER_ENGINE_ACTION"); |
593 | ExitWithLastError(hr, "Failed to post detect message."); | 598 | |
594 | } | 599 | pAction->dwMessage = WM_BURN_DETECT; |
600 | pAction->detect.hwndParent = hwndParent; | ||
601 | |||
602 | hr = EnqueueAction(pEngineContext, &pAction); | ||
603 | ExitOnFailure(hr, "Failed to enqueue detect action."); | ||
595 | 604 | ||
596 | LExit: | 605 | LExit: |
606 | ReleaseMem(pAction); | ||
607 | |||
597 | return hr; | 608 | return hr; |
598 | } | 609 | } |
599 | 610 | ||
600 | HRESULT ExternalEnginePlan( | 611 | HRESULT ExternalEnginePlan( |
601 | __in const DWORD dwThreadId, | 612 | __in BOOTSTRAPPER_ENGINE_CONTEXT* pEngineContext, |
602 | __in const BOOTSTRAPPER_ACTION action | 613 | __in const BOOTSTRAPPER_ACTION action |
603 | ) | 614 | ) |
604 | { | 615 | { |
605 | HRESULT hr = S_OK; | 616 | HRESULT hr = S_OK; |
617 | BOOTSTRAPPER_ENGINE_ACTION* pAction = NULL; | ||
606 | 618 | ||
607 | if (BOOTSTRAPPER_ACTION_LAYOUT > action || BOOTSTRAPPER_ACTION_UPDATE_REPLACE_EMBEDDED < action) | 619 | if (BOOTSTRAPPER_ACTION_LAYOUT > action || BOOTSTRAPPER_ACTION_UPDATE_REPLACE_EMBEDDED < action) |
608 | { | 620 | { |
609 | ExitOnRootFailure(hr = E_INVALIDARG, "BA passed invalid action to Plan: %u.", action); | 621 | ExitOnRootFailure(hr = E_INVALIDARG, "BA passed invalid action to Plan: %u.", action); |
610 | } | 622 | } |
611 | 623 | ||
612 | if (!::PostThreadMessageW(dwThreadId, WM_BURN_PLAN, 0, action)) | 624 | pAction = (BOOTSTRAPPER_ENGINE_ACTION*)MemAlloc(sizeof(BOOTSTRAPPER_ENGINE_ACTION), TRUE); |
613 | { | 625 | ExitOnNull(pAction, hr, E_OUTOFMEMORY, "Failed to alloc BOOTSTRAPPER_ENGINE_ACTION"); |
614 | ExitWithLastError(hr, "Failed to post plan message."); | 626 | |
615 | } | 627 | pAction->dwMessage = WM_BURN_PLAN; |
628 | pAction->plan.action = action; | ||
629 | |||
630 | hr = EnqueueAction(pEngineContext, &pAction); | ||
631 | ExitOnFailure(hr, "Failed to enqueue plan action."); | ||
616 | 632 | ||
617 | LExit: | 633 | LExit: |
634 | ReleaseMem(pAction); | ||
635 | |||
618 | return hr; | 636 | return hr; |
619 | } | 637 | } |
620 | 638 | ||
621 | HRESULT ExternalEngineElevate( | 639 | HRESULT ExternalEngineElevate( |
622 | __in BURN_ENGINE_STATE* pEngineState, | 640 | __in BOOTSTRAPPER_ENGINE_CONTEXT* pEngineContext, |
623 | __in const DWORD dwThreadId, | ||
624 | __in_opt const HWND hwndParent | 641 | __in_opt const HWND hwndParent |
625 | ) | 642 | ) |
626 | { | 643 | { |
627 | HRESULT hr = S_OK; | 644 | HRESULT hr = S_OK; |
645 | BOOTSTRAPPER_ENGINE_ACTION* pAction = NULL; | ||
628 | 646 | ||
629 | if (INVALID_HANDLE_VALUE != pEngineState->companionConnection.hPipe) | 647 | if (INVALID_HANDLE_VALUE != pEngineContext->pEngineState->companionConnection.hPipe) |
630 | { | ||
631 | hr = HRESULT_FROM_WIN32(ERROR_ALREADY_INITIALIZED); | ||
632 | } | ||
633 | else if (!::PostThreadMessageW(dwThreadId, WM_BURN_ELEVATE, 0, reinterpret_cast<LPARAM>(hwndParent))) | ||
634 | { | 648 | { |
635 | ExitWithLastError(hr, "Failed to post elevate message."); | 649 | ExitFunction1(hr = HRESULT_FROM_WIN32(ERROR_ALREADY_INITIALIZED)); |
636 | } | 650 | } |
637 | 651 | ||
652 | pAction = (BOOTSTRAPPER_ENGINE_ACTION*)MemAlloc(sizeof(BOOTSTRAPPER_ENGINE_ACTION), TRUE); | ||
653 | ExitOnNull(pAction, hr, E_OUTOFMEMORY, "Failed to alloc BOOTSTRAPPER_ENGINE_ACTION"); | ||
654 | |||
655 | pAction->dwMessage = WM_BURN_ELEVATE; | ||
656 | pAction->elevate.hwndParent = hwndParent; | ||
657 | |||
658 | hr = EnqueueAction(pEngineContext, &pAction); | ||
659 | ExitOnFailure(hr, "Failed to enqueue elevate action."); | ||
660 | |||
638 | LExit: | 661 | LExit: |
662 | ReleaseMem(pAction); | ||
663 | |||
639 | return hr; | 664 | return hr; |
640 | } | 665 | } |
641 | 666 | ||
642 | HRESULT ExternalEngineApply( | 667 | HRESULT ExternalEngineApply( |
643 | __in const DWORD dwThreadId, | 668 | __in BOOTSTRAPPER_ENGINE_CONTEXT* pEngineContext, |
644 | __in_opt const HWND hwndParent | 669 | __in_opt const HWND hwndParent |
645 | ) | 670 | ) |
646 | { | 671 | { |
647 | HRESULT hr = S_OK; | 672 | HRESULT hr = S_OK; |
673 | BOOTSTRAPPER_ENGINE_ACTION* pAction = NULL; | ||
648 | 674 | ||
649 | ExitOnNull(hwndParent, hr, E_INVALIDARG, "BA passed NULL hwndParent to Apply."); | 675 | ExitOnNull(hwndParent, hr, E_INVALIDARG, "BA passed NULL hwndParent to Apply."); |
650 | if (!::IsWindow(hwndParent)) | 676 | if (!::IsWindow(hwndParent)) |
@@ -652,34 +678,46 @@ HRESULT ExternalEngineApply( | |||
652 | ExitOnRootFailure(hr = E_INVALIDARG, "BA passed invalid hwndParent to Apply."); | 678 | ExitOnRootFailure(hr = E_INVALIDARG, "BA passed invalid hwndParent to Apply."); |
653 | } | 679 | } |
654 | 680 | ||
655 | if (!::PostThreadMessageW(dwThreadId, WM_BURN_APPLY, 0, reinterpret_cast<LPARAM>(hwndParent))) | 681 | pAction = (BOOTSTRAPPER_ENGINE_ACTION*)MemAlloc(sizeof(BOOTSTRAPPER_ENGINE_ACTION), TRUE); |
656 | { | 682 | ExitOnNull(pAction, hr, E_OUTOFMEMORY, "Failed to alloc BOOTSTRAPPER_ENGINE_ACTION"); |
657 | ExitWithLastError(hr, "Failed to post apply message."); | 683 | |
658 | } | 684 | pAction->dwMessage = WM_BURN_APPLY; |
685 | pAction->apply.hwndParent = hwndParent; | ||
686 | |||
687 | hr = EnqueueAction(pEngineContext, &pAction); | ||
688 | ExitOnFailure(hr, "Failed to enqueue apply action."); | ||
659 | 689 | ||
660 | LExit: | 690 | LExit: |
691 | ReleaseMem(pAction); | ||
692 | |||
661 | return hr; | 693 | return hr; |
662 | } | 694 | } |
663 | 695 | ||
664 | HRESULT ExternalEngineQuit( | 696 | HRESULT ExternalEngineQuit( |
665 | __in const DWORD dwThreadId, | 697 | __in BOOTSTRAPPER_ENGINE_CONTEXT* pEngineContext, |
666 | __in const DWORD dwExitCode | 698 | __in const DWORD dwExitCode |
667 | ) | 699 | ) |
668 | { | 700 | { |
669 | HRESULT hr = S_OK; | 701 | HRESULT hr = S_OK; |
702 | BOOTSTRAPPER_ENGINE_ACTION* pAction = NULL; | ||
670 | 703 | ||
671 | if (!::PostThreadMessageW(dwThreadId, WM_BURN_QUIT, static_cast<WPARAM>(dwExitCode), 0)) | 704 | pAction = (BOOTSTRAPPER_ENGINE_ACTION*)MemAlloc(sizeof(BOOTSTRAPPER_ENGINE_ACTION), TRUE); |
672 | { | 705 | ExitOnNull(pAction, hr, E_OUTOFMEMORY, "Failed to alloc BOOTSTRAPPER_ENGINE_ACTION"); |
673 | ExitWithLastError(hr, "Failed to post shutdown message."); | 706 | |
674 | } | 707 | pAction->dwMessage = WM_BURN_QUIT; |
708 | pAction->quit.dwExitCode = dwExitCode; | ||
709 | |||
710 | hr = EnqueueAction(pEngineContext, &pAction); | ||
711 | ExitOnFailure(hr, "Failed to enqueue shutdown action."); | ||
675 | 712 | ||
676 | LExit: | 713 | LExit: |
714 | ReleaseMem(pAction); | ||
715 | |||
677 | return hr; | 716 | return hr; |
678 | } | 717 | } |
679 | 718 | ||
680 | HRESULT ExternalEngineLaunchApprovedExe( | 719 | HRESULT ExternalEngineLaunchApprovedExe( |
681 | __in BURN_ENGINE_STATE* pEngineState, | 720 | __in BOOTSTRAPPER_ENGINE_CONTEXT* pEngineContext, |
682 | __in const DWORD dwThreadId, | ||
683 | __in_opt const HWND hwndParent, | 721 | __in_opt const HWND hwndParent, |
684 | __in_z LPCWSTR wzApprovedExeForElevationId, | 722 | __in_z LPCWSTR wzApprovedExeForElevationId, |
685 | __in_z_opt LPCWSTR wzArguments, | 723 | __in_z_opt LPCWSTR wzArguments, |
@@ -688,25 +726,23 @@ HRESULT ExternalEngineLaunchApprovedExe( | |||
688 | { | 726 | { |
689 | HRESULT hr = S_OK; | 727 | HRESULT hr = S_OK; |
690 | BURN_APPROVED_EXE* pApprovedExe = NULL; | 728 | BURN_APPROVED_EXE* pApprovedExe = NULL; |
691 | BOOL fLeaveCriticalSection = FALSE; | ||
692 | BURN_LAUNCH_APPROVED_EXE* pLaunchApprovedExe = NULL; | 729 | BURN_LAUNCH_APPROVED_EXE* pLaunchApprovedExe = NULL; |
693 | 730 | BOOTSTRAPPER_ENGINE_ACTION* pAction = NULL; | |
694 | pLaunchApprovedExe = (BURN_LAUNCH_APPROVED_EXE*)MemAlloc(sizeof(BURN_LAUNCH_APPROVED_EXE), TRUE); | ||
695 | ExitOnNull(pLaunchApprovedExe, hr, E_OUTOFMEMORY, "Failed to alloc BURN_LAUNCH_APPROVED_EXE"); | ||
696 | |||
697 | ::EnterCriticalSection(&pEngineState->userExperience.csEngineActive); | ||
698 | fLeaveCriticalSection = TRUE; | ||
699 | hr = UserExperienceEnsureEngineInactive(&pEngineState->userExperience); | ||
700 | ExitOnFailure(hr, "Engine is active, cannot change engine state."); | ||
701 | 731 | ||
702 | if (!wzApprovedExeForElevationId || !*wzApprovedExeForElevationId) | 732 | if (!wzApprovedExeForElevationId || !*wzApprovedExeForElevationId) |
703 | { | 733 | { |
704 | ExitFunction1(hr = E_INVALIDARG); | 734 | ExitFunction1(hr = E_INVALIDARG); |
705 | } | 735 | } |
706 | 736 | ||
707 | hr = ApprovedExesFindById(&pEngineState->approvedExes, wzApprovedExeForElevationId, &pApprovedExe); | 737 | hr = ApprovedExesFindById(&pEngineContext->pEngineState->approvedExes, wzApprovedExeForElevationId, &pApprovedExe); |
708 | ExitOnFailure(hr, "BA requested unknown approved exe with id: %ls", wzApprovedExeForElevationId); | 738 | ExitOnFailure(hr, "BA requested unknown approved exe with id: %ls", wzApprovedExeForElevationId); |
709 | 739 | ||
740 | pAction = (BOOTSTRAPPER_ENGINE_ACTION*)MemAlloc(sizeof(BOOTSTRAPPER_ENGINE_ACTION), TRUE); | ||
741 | ExitOnNull(pAction, hr, E_OUTOFMEMORY, "Failed to alloc BOOTSTRAPPER_ENGINE_ACTION"); | ||
742 | |||
743 | pAction->dwMessage = WM_BURN_LAUNCH_APPROVED_EXE; | ||
744 | pLaunchApprovedExe = &pAction->launchApprovedExe; | ||
745 | |||
710 | hr = StrAllocString(&pLaunchApprovedExe->sczId, wzApprovedExeForElevationId, NULL); | 746 | hr = StrAllocString(&pLaunchApprovedExe->sczId, wzApprovedExeForElevationId, NULL); |
711 | ExitOnFailure(hr, "Failed to copy the id."); | 747 | ExitOnFailure(hr, "Failed to copy the id."); |
712 | 748 | ||
@@ -720,20 +756,14 @@ HRESULT ExternalEngineLaunchApprovedExe( | |||
720 | 756 | ||
721 | pLaunchApprovedExe->hwndParent = hwndParent; | 757 | pLaunchApprovedExe->hwndParent = hwndParent; |
722 | 758 | ||
723 | if (!::PostThreadMessageW(dwThreadId, WM_BURN_LAUNCH_APPROVED_EXE, 0, reinterpret_cast<LPARAM>(pLaunchApprovedExe))) | 759 | hr = EnqueueAction(pEngineContext, &pAction); |
724 | { | 760 | ExitOnFailure(hr, "Failed to enqueue launch approved exe action."); |
725 | ExitWithLastError(hr, "Failed to post launch approved exe message."); | ||
726 | } | ||
727 | 761 | ||
728 | LExit: | 762 | LExit: |
729 | if (fLeaveCriticalSection) | 763 | if (pAction) |
730 | { | 764 | { |
731 | ::LeaveCriticalSection(&pEngineState->userExperience.csEngineActive); | 765 | CoreBootstrapperEngineActionUninitialize(pAction); |
732 | } | 766 | MemFree(pAction); |
733 | |||
734 | if (FAILED(hr)) | ||
735 | { | ||
736 | ApprovedExesUninitializeLaunch(pLaunchApprovedExe); | ||
737 | } | 767 | } |
738 | 768 | ||
739 | return hr; | 769 | return hr; |
@@ -836,3 +866,37 @@ static HRESULT ProcessUnknownEmbeddedMessages( | |||
836 | 866 | ||
837 | return S_OK; | 867 | return S_OK; |
838 | } | 868 | } |
869 | |||
870 | static HRESULT EnqueueAction( | ||
871 | __in BOOTSTRAPPER_ENGINE_CONTEXT* pEngineContext, | ||
872 | __inout BOOTSTRAPPER_ENGINE_ACTION** ppAction | ||
873 | ) | ||
874 | { | ||
875 | HRESULT hr = S_OK; | ||
876 | |||
877 | ::EnterCriticalSection(&pEngineContext->csQueue); | ||
878 | |||
879 | if (pEngineContext->pEngineState->fQuit) | ||
880 | { | ||
881 | LogId(REPORT_WARNING, MSG_IGNORE_OPERATION_AFTER_QUIT, LoggingBurnMessageToString((*ppAction)->dwMessage)); | ||
882 | hr = E_INVALIDSTATE; | ||
883 | } | ||
884 | else | ||
885 | { | ||
886 | hr = QueEnqueue(pEngineContext->hQueue, *ppAction); | ||
887 | } | ||
888 | |||
889 | ::LeaveCriticalSection(&pEngineContext->csQueue); | ||
890 | |||
891 | ExitOnFailure(hr, "Failed to enqueue action."); | ||
892 | |||
893 | *ppAction = NULL; | ||
894 | |||
895 | if (!::ReleaseSemaphore(pEngineContext->hQueueSemaphore, 1, NULL)) | ||
896 | { | ||
897 | ExitWithLastError(hr, "Failed to signal queue semaphore."); | ||
898 | } | ||
899 | |||
900 | LExit: | ||
901 | return hr; | ||
902 | } | ||