This commit is contained in:
Sean Hall 2018-12-29 22:24:05 -06:00
Родитель 681527e783
Коммит 60069b189d
17 изменённых файлов: 4724 добавлений и 0 удалений

Просмотреть файл

@ -0,0 +1,720 @@
// Copyright (c) .NET Foundation and contributors. All rights reserved. Licensed under the Microsoft Reciprocal License. See LICENSE.TXT file in the project root for full license information.
#include "precomp.h"
class CBalBootstrapperEngine : public IBootstrapperEngine, public IMarshal
{
public: // IUnknown
virtual STDMETHODIMP QueryInterface(
__in REFIID riid,
__out LPVOID *ppvObject
)
{
if (!ppvObject)
{
return E_INVALIDARG;
}
*ppvObject = NULL;
if (::IsEqualIID(__uuidof(IBootstrapperEngine), riid))
{
*ppvObject = static_cast<IBootstrapperEngine*>(this);
}
else if (::IsEqualIID(IID_IMarshal, riid))
{
*ppvObject = static_cast<IMarshal*>(this);
}
else if (::IsEqualIID(IID_IUnknown, riid))
{
*ppvObject = reinterpret_cast<IUnknown*>(this);
}
else // no interface for requested iid
{
return E_NOINTERFACE;
}
AddRef();
return S_OK;
}
virtual STDMETHODIMP_(ULONG) AddRef()
{
return ::InterlockedIncrement(&this->m_cReferences);
}
virtual STDMETHODIMP_(ULONG) Release()
{
long l = ::InterlockedDecrement(&this->m_cReferences);
if (0 < l)
{
return l;
}
delete this;
return 0;
}
public: // IBootstrapperEngine
virtual STDMETHODIMP GetPackageCount(
__out DWORD* pcPackages
)
{
HRESULT hr = S_OK;
BAENGINE_GETPACKAGECOUNT_ARGS args = { };
BAENGINE_GETPACKAGECOUNT_RESULTS results = { };
ExitOnNull(pcPackages, hr, E_INVALIDARG, "pcPackages is required");
args.cbSize = sizeof(args);
results.cbSize = sizeof(results);
hr = m_pfnBAEngineProc(BOOTSTRAPPER_ENGINE_MESSAGE_GETPACKAGECOUNT, &args, &results, m_pvBAEngineProcContext);
*pcPackages = results.cPackages;
LExit:
return hr;
}
virtual STDMETHODIMP GetVariableNumeric(
__in_z LPCWSTR wzVariable,
__out LONGLONG* pllValue
)
{
HRESULT hr = S_OK;
BAENGINE_GETVARIABLENUMERIC_ARGS args = { };
BAENGINE_GETVARIABLENUMERIC_RESULTS results = { };
ExitOnNull(pllValue, hr, E_INVALIDARG, "pllValue is required");
args.cbSize = sizeof(args);
args.wzVariable = wzVariable;
results.cbSize = sizeof(results);
hr = m_pfnBAEngineProc(BOOTSTRAPPER_ENGINE_MESSAGE_GETVARIABLENUMERIC, &args, &results, m_pvBAEngineProcContext);
*pllValue = results.llValue;
LExit:
SecureZeroMemory(&results, sizeof(results));
return hr;
}
virtual STDMETHODIMP GetVariableString(
__in_z LPCWSTR wzVariable,
__out_ecount_opt(*pcchValue) LPWSTR wzValue,
__inout DWORD* pcchValue
)
{
HRESULT hr = S_OK;
BAENGINE_GETVARIABLESTRING_ARGS args = { };
BAENGINE_GETVARIABLESTRING_RESULTS results = { };
ExitOnNull(pcchValue, hr, E_INVALIDARG, "pcchValue is required");
args.cbSize = sizeof(args);
args.wzVariable = wzVariable;
results.cbSize = sizeof(results);
results.wzValue = wzValue;
results.cchValue = *pcchValue;
hr = m_pfnBAEngineProc(BOOTSTRAPPER_ENGINE_MESSAGE_GETVARIABLESTRING, &args, &results, m_pvBAEngineProcContext);
*pcchValue = results.cchValue;
LExit:
return hr;
}
virtual STDMETHODIMP GetVariableVersion(
__in_z LPCWSTR wzVariable,
__out DWORD64* pqwValue
)
{
HRESULT hr = S_OK;
BAENGINE_GETVARIABLEVERSION_ARGS args = { };
BAENGINE_GETVARIABLEVERSION_RESULTS results = { };
ExitOnNull(pqwValue, hr, E_INVALIDARG, "pqwValue is required");
args.cbSize = sizeof(args);
args.wzVariable = wzVariable;
results.cbSize = sizeof(results);
hr = m_pfnBAEngineProc(BOOTSTRAPPER_ENGINE_MESSAGE_GETVARIABLEVERSION, &args, &results, m_pvBAEngineProcContext);
*pqwValue = results.qwValue;
LExit:
SecureZeroMemory(&results, sizeof(results));
return hr;
}
virtual STDMETHODIMP FormatString(
__in_z LPCWSTR wzIn,
__out_ecount_opt(*pcchOut) LPWSTR wzOut,
__inout DWORD* pcchOut
)
{
HRESULT hr = S_OK;
BAENGINE_FORMATSTRING_ARGS args = { };
BAENGINE_FORMATSTRING_RESULTS results = { };
ExitOnNull(pcchOut, hr, E_INVALIDARG, "pcchOut is required");
args.cbSize = sizeof(args);
args.wzIn = wzIn;
results.cbSize = sizeof(results);
results.wzOut = wzOut;
results.cchOut = *pcchOut;
hr = m_pfnBAEngineProc(BOOTSTRAPPER_ENGINE_MESSAGE_FORMATSTRING, &args, &results, m_pvBAEngineProcContext);
*pcchOut = results.cchOut;
LExit:
return hr;
}
virtual STDMETHODIMP EscapeString(
__in_z LPCWSTR wzIn,
__out_ecount_opt(*pcchOut) LPWSTR wzOut,
__inout DWORD* pcchOut
)
{
HRESULT hr = S_OK;
BAENGINE_ESCAPESTRING_ARGS args = { };
BAENGINE_ESCAPESTRING_RESULTS results = { };
ExitOnNull(pcchOut, hr, E_INVALIDARG, "pcchOut is required");
args.cbSize = sizeof(args);
args.wzIn = wzIn;
results.cbSize = sizeof(results);
results.wzOut = wzOut;
results.cchOut = *pcchOut;
hr = m_pfnBAEngineProc(BOOTSTRAPPER_ENGINE_MESSAGE_ESCAPESTRING, &args, &results, m_pvBAEngineProcContext);
*pcchOut = results.cchOut;
LExit:
return hr;
}
virtual STDMETHODIMP EvaluateCondition(
__in_z LPCWSTR wzCondition,
__out BOOL* pf
)
{
HRESULT hr = S_OK;
BAENGINE_EVALUATECONDITION_ARGS args = { };
BAENGINE_EVALUATECONDITION_RESULTS results = { };
ExitOnNull(pf, hr, E_INVALIDARG, "pf is required");
args.cbSize = sizeof(args);
args.wzCondition = wzCondition;
results.cbSize = sizeof(results);
hr = m_pfnBAEngineProc(BOOTSTRAPPER_ENGINE_MESSAGE_EVALUATECONDITION, &args, &results, m_pvBAEngineProcContext);
*pf = results.f;
LExit:
return hr;
}
virtual STDMETHODIMP Log(
__in BOOTSTRAPPER_LOG_LEVEL level,
__in_z LPCWSTR wzMessage
)
{
BAENGINE_LOG_ARGS args = { };
BAENGINE_LOG_RESULTS results = { };
args.cbSize = sizeof(args);
args.level = level;
args.wzMessage = wzMessage;
results.cbSize = sizeof(results);
return m_pfnBAEngineProc(BOOTSTRAPPER_ENGINE_MESSAGE_LOG, &args, &results, m_pvBAEngineProcContext);
}
virtual STDMETHODIMP SendEmbeddedError(
__in DWORD dwErrorCode,
__in_z_opt LPCWSTR wzMessage,
__in DWORD dwUIHint,
__out int* pnResult
)
{
HRESULT hr = S_OK;
BAENGINE_SENDEMBEDDEDERROR_ARGS args = { };
BAENGINE_SENDEMBEDDEDERROR_RESULTS results = { };
ExitOnNull(pnResult, hr, E_INVALIDARG, "pnResult is required");
args.cbSize = sizeof(args);
args.dwErrorCode = dwErrorCode;
args.wzMessage = wzMessage;
args.dwUIHint = dwUIHint;
results.cbSize = sizeof(results);
hr = m_pfnBAEngineProc(BOOTSTRAPPER_ENGINE_MESSAGE_SENDEMBEDDEDERROR, &args, &results, m_pvBAEngineProcContext);
*pnResult = results.nResult;
LExit:
return hr;
}
virtual STDMETHODIMP SendEmbeddedProgress(
__in DWORD dwProgressPercentage,
__in DWORD dwOverallProgressPercentage,
__out int* pnResult
)
{
HRESULT hr = S_OK;
BAENGINE_SENDEMBEDDEDPROGRESS_ARGS args = { };
BAENGINE_SENDEMBEDDEDPROGRESS_RESULTS results = { };
ExitOnNull(pnResult, hr, E_INVALIDARG, "pnResult is required");
args.cbSize = sizeof(args);
args.dwProgressPercentage = dwProgressPercentage;
args.dwOverallProgressPercentage = dwOverallProgressPercentage;
results.cbSize = sizeof(results);
hr = m_pfnBAEngineProc(BOOTSTRAPPER_ENGINE_MESSAGE_SENDEMBEDDEDPROGRESS, &args, &results, m_pvBAEngineProcContext);
*pnResult = results.nResult;
LExit:
return hr;
}
virtual STDMETHODIMP SetUpdate(
__in_z_opt LPCWSTR wzLocalSource,
__in_z_opt LPCWSTR wzDownloadSource,
__in DWORD64 qwSize,
__in BOOTSTRAPPER_UPDATE_HASH_TYPE hashType,
__in_bcount_opt(cbHash) BYTE* rgbHash,
__in DWORD cbHash
)
{
BAENGINE_SETUPDATE_ARGS args = { };
BAENGINE_SETUPDATE_RESULTS results = { };
args.cbSize = sizeof(args);
args.wzLocalSource = wzLocalSource;
args.wzDownloadSource = wzDownloadSource;
args.qwSize = qwSize;
args.hashType = hashType;
args.rgbHash = rgbHash;
args.cbHash = cbHash;
results.cbSize = sizeof(results);
return m_pfnBAEngineProc(BOOTSTRAPPER_ENGINE_MESSAGE_SETUPDATE, &args, &results, m_pvBAEngineProcContext);
}
virtual STDMETHODIMP SetLocalSource(
__in_z LPCWSTR wzPackageOrContainerId,
__in_z_opt LPCWSTR wzPayloadId,
__in_z LPCWSTR wzPath
)
{
BAENGINE_SETLOCALSOURCE_ARGS args = { };
BAENGINE_SETLOCALSOURCE_RESULTS results = { };
args.cbSize = sizeof(args);
args.wzPackageOrContainerId = wzPackageOrContainerId;
args.wzPayloadId = wzPayloadId;
args.wzPath = wzPath;
results.cbSize = sizeof(results);
return m_pfnBAEngineProc(BOOTSTRAPPER_ENGINE_MESSAGE_SETLOCALSOURCE, &args, &results, m_pvBAEngineProcContext);
}
virtual STDMETHODIMP SetDownloadSource(
__in_z LPCWSTR wzPackageOrContainerId,
__in_z_opt LPCWSTR wzPayloadId,
__in_z LPCWSTR wzUrl,
__in_z_opt LPCWSTR wzUser,
__in_z_opt LPCWSTR wzPassword
)
{
BAENGINE_SETDOWNLOADSOURCE_ARGS args = { };
BAENGINE_SETDOWNLOADSOURCE_RESULTS results = { };
args.cbSize = sizeof(args);
args.wzPackageOrContainerId = wzPackageOrContainerId;
args.wzPayloadId = wzPayloadId;
args.wzUrl = wzUrl;
args.wzUser = wzUser;
args.wzPassword = wzPassword;
results.cbSize = sizeof(results);
return m_pfnBAEngineProc(BOOTSTRAPPER_ENGINE_MESSAGE_SETDOWNLOADSOURCE, &args, &results, m_pvBAEngineProcContext);
}
virtual STDMETHODIMP SetVariableNumeric(
__in_z LPCWSTR wzVariable,
__in LONGLONG llValue
)
{
BAENGINE_SETVARIABLENUMERIC_ARGS args = { };
BAENGINE_SETVARIABLENUMERIC_RESULTS results = { };
args.cbSize = sizeof(args);
args.wzVariable = wzVariable;
args.llValue = llValue;
results.cbSize = sizeof(results);
return m_pfnBAEngineProc(BOOTSTRAPPER_ENGINE_MESSAGE_SETVARIABLENUMERIC, &args, &results, m_pvBAEngineProcContext);
}
virtual STDMETHODIMP SetVariableString(
__in_z LPCWSTR wzVariable,
__in_z_opt LPCWSTR wzValue
)
{
BAENGINE_SETVARIABLESTRING_ARGS args = { };
BAENGINE_SETVARIABLESTRING_RESULTS results = { };
args.cbSize = sizeof(args);
args.wzVariable = wzVariable;
args.wzValue = wzValue;
results.cbSize = sizeof(results);
return m_pfnBAEngineProc(BOOTSTRAPPER_ENGINE_MESSAGE_SETVARIABLESTRING, &args, &results, m_pvBAEngineProcContext);
}
virtual STDMETHODIMP SetVariableVersion(
__in_z LPCWSTR wzVariable,
__in DWORD64 qwValue
)
{
BAENGINE_SETVARIABLEVERSION_ARGS args = { };
BAENGINE_SETVARIABLEVERSION_RESULTS results = { };
args.cbSize = sizeof(args);
args.wzVariable = wzVariable;
args.qwValue = qwValue;
results.cbSize = sizeof(results);
return m_pfnBAEngineProc(BOOTSTRAPPER_ENGINE_MESSAGE_SETVARIABLEVERSION, &args, &results, m_pvBAEngineProcContext);
}
virtual STDMETHODIMP CloseSplashScreen()
{
BAENGINE_CLOSESPLASHSCREEN_ARGS args = { };
BAENGINE_CLOSESPLASHSCREEN_RESULTS results = { };
args.cbSize = sizeof(args);
results.cbSize = sizeof(results);
return m_pfnBAEngineProc(BOOTSTRAPPER_ENGINE_MESSAGE_CLOSESPLASHSCREEN, &args, &results, m_pvBAEngineProcContext);
}
virtual STDMETHODIMP Detect(
__in_opt HWND hwndParent
)
{
BAENGINE_DETECT_ARGS args = { };
BAENGINE_DETECT_RESULTS results = { };
args.cbSize = sizeof(args);
args.hwndParent = hwndParent;
results.cbSize = sizeof(results);
return m_pfnBAEngineProc(BOOTSTRAPPER_ENGINE_MESSAGE_DETECT, &args, &results, m_pvBAEngineProcContext);
}
virtual STDMETHODIMP Plan(
__in BOOTSTRAPPER_ACTION action
)
{
BAENGINE_PLAN_ARGS args = { };
BAENGINE_PLAN_RESULTS results = { };
args.cbSize = sizeof(args);
args.action = action;
results.cbSize = sizeof(results);
return m_pfnBAEngineProc(BOOTSTRAPPER_ENGINE_MESSAGE_PLAN, &args, &results, m_pvBAEngineProcContext);
}
virtual STDMETHODIMP Elevate(
__in_opt HWND hwndParent
)
{
BAENGINE_ELEVATE_ARGS args = { };
BAENGINE_ELEVATE_RESULTS results = { };
args.cbSize = sizeof(args);
args.hwndParent = hwndParent;
results.cbSize = sizeof(results);
return m_pfnBAEngineProc(BOOTSTRAPPER_ENGINE_MESSAGE_ELEVATE, &args, &results, m_pvBAEngineProcContext);
}
virtual STDMETHODIMP Apply(
__in_opt HWND hwndParent
)
{
BAENGINE_APPLY_ARGS args = { };
BAENGINE_APPLY_RESULTS results = { };
args.cbSize = sizeof(args);
args.hwndParent = hwndParent;
results.cbSize = sizeof(results);
return m_pfnBAEngineProc(BOOTSTRAPPER_ENGINE_MESSAGE_APPLY, &args, &results, m_pvBAEngineProcContext);
}
virtual STDMETHODIMP Quit(
__in DWORD dwExitCode
)
{
BAENGINE_QUIT_ARGS args = { };
BAENGINE_QUIT_RESULTS results = { };
args.cbSize = sizeof(args);
args.dwExitCode = dwExitCode;
results.cbSize = sizeof(results);
return m_pfnBAEngineProc(BOOTSTRAPPER_ENGINE_MESSAGE_QUIT, &args, &results, m_pvBAEngineProcContext);
}
virtual STDMETHODIMP LaunchApprovedExe(
__in_opt HWND hwndParent,
__in_z LPCWSTR wzApprovedExeForElevationId,
__in_z_opt LPCWSTR wzArguments,
__in DWORD dwWaitForInputIdleTimeout
)
{
BAENGINE_LAUNCHAPPROVEDEXE_ARGS args = { };
BAENGINE_LAUNCHAPPROVEDEXE_RESULTS results = { };
args.cbSize = sizeof(args);
args.hwndParent = hwndParent;
args.wzApprovedExeForElevationId = wzApprovedExeForElevationId;
args.wzArguments = wzArguments;
args.dwWaitForInputIdleTimeout = dwWaitForInputIdleTimeout;
results.cbSize = sizeof(results);
return m_pfnBAEngineProc(BOOTSTRAPPER_ENGINE_MESSAGE_LAUNCHAPPROVEDEXE, &args, &results, m_pvBAEngineProcContext);
}
public: // IMarshal
virtual STDMETHODIMP GetUnmarshalClass(
__in REFIID /*riid*/,
__in_opt LPVOID /*pv*/,
__in DWORD /*dwDestContext*/,
__reserved LPVOID /*pvDestContext*/,
__in DWORD /*mshlflags*/,
__out LPCLSID /*pCid*/
)
{
return E_NOTIMPL;
}
virtual STDMETHODIMP GetMarshalSizeMax(
__in REFIID riid,
__in_opt LPVOID /*pv*/,
__in DWORD dwDestContext,
__reserved LPVOID /*pvDestContext*/,
__in DWORD /*mshlflags*/,
__out DWORD *pSize
)
{
HRESULT hr = S_OK;
// We only support marshaling the IBootstrapperEngine interface in-proc.
if (__uuidof(IBootstrapperEngine) != riid)
{
// Skip logging the following message since it appears way too often in the log.
// "Unexpected IID requested to be marshalled. BootstrapperEngineForApplication can only marshal the IBootstrapperEngine interface."
ExitFunction1(hr = E_NOINTERFACE);
}
else if (0 == (MSHCTX_INPROC & dwDestContext))
{
hr = E_FAIL;
ExitOnRootFailure(hr, "Cannot marshal IBootstrapperEngine interface out of proc.");
}
// E_FAIL is used because E_INVALIDARG is not a supported return value.
ExitOnNull(pSize, hr, E_FAIL, "Invalid size output parameter is NULL.");
// Specify enough size to marshal just the interface pointer across threads.
*pSize = sizeof(LPVOID);
LExit:
return hr;
}
virtual STDMETHODIMP MarshalInterface(
__in IStream* pStm,
__in REFIID riid,
__in_opt LPVOID pv,
__in DWORD dwDestContext,
__reserved LPVOID /*pvDestContext*/,
__in DWORD /*mshlflags*/
)
{
HRESULT hr = S_OK;
IBootstrapperEngine *pThis = NULL;
ULONG ulWritten = 0;
// We only support marshaling the IBootstrapperEngine interface in-proc.
if (__uuidof(IBootstrapperEngine) != riid)
{
// Skip logging the following message since it appears way too often in the log.
// "Unexpected IID requested to be marshalled. BootstrapperEngineForApplication can only marshal the IBootstrapperEngine interface."
ExitFunction1(hr = E_NOINTERFACE);
}
else if (0 == (MSHCTX_INPROC & dwDestContext))
{
hr = E_FAIL;
ExitOnRootFailure(hr, "Cannot marshal IBootstrapperEngine interface out of proc.");
}
// "pv" may not be set, so we should us "this" otherwise.
if (pv)
{
pThis = reinterpret_cast<IBootstrapperEngine*>(pv);
}
else
{
pThis = static_cast<IBootstrapperEngine*>(this);
}
// E_INVALIDARG is not a supported return value.
ExitOnNull(pStm, hr, E_FAIL, "The marshaling stream parameter is NULL.");
// Marshal the interface pointer in-proc as is.
hr = pStm->Write(pThis, sizeof(pThis), &ulWritten);
if (STG_E_MEDIUMFULL == hr)
{
ExitOnFailure(hr, "Failed to write the stream because the stream is full.");
}
else if (FAILED(hr))
{
// All other STG error must be converted into E_FAIL based on IMarshal documentation.
hr = E_FAIL;
ExitOnFailure(hr, "Failed to write the IBootstrapperEngine interface pointer to the marshaling stream.");
}
LExit:
return hr;
}
virtual STDMETHODIMP UnmarshalInterface(
__in IStream* pStm,
__in REFIID riid,
__deref_out LPVOID* ppv
)
{
HRESULT hr = S_OK;
ULONG ulRead = 0;
// We only support marshaling the engine in-proc.
if (__uuidof(IBootstrapperEngine) != riid)
{
// Skip logging the following message since it appears way too often in the log.
// "Unexpected IID requested to be marshalled. BootstrapperEngineForApplication can only marshal the IBootstrapperEngine interface."
ExitFunction1(hr = E_NOINTERFACE);
}
// E_FAIL is used because E_INVALIDARG is not a supported return value.
ExitOnNull(pStm, hr, E_FAIL, "The marshaling stream parameter is NULL.");
ExitOnNull(ppv, hr, E_FAIL, "The interface output parameter is NULL.");
// Unmarshal the interface pointer in-proc as is.
hr = pStm->Read(*ppv, sizeof(LPVOID), &ulRead);
if (FAILED(hr))
{
// All STG errors must be converted into E_FAIL based on IMarshal documentation.
hr = E_FAIL;
ExitOnFailure(hr, "Failed to read the IBootstrapperEngine interface pointer from the marshaling stream.");
}
LExit:
return hr;
}
virtual STDMETHODIMP ReleaseMarshalData(
__in IStream* /*pStm*/
)
{
return E_NOTIMPL;
}
virtual STDMETHODIMP DisconnectObject(
__in DWORD /*dwReserved*/
)
{
return E_NOTIMPL;
}
public:
CBalBootstrapperEngine(
__in PFN_BOOTSTRAPPER_ENGINE_PROC pfnBAEngineProc,
__in_opt LPVOID pvBAEngineProcContext
)
{
m_cReferences = 1;
m_pfnBAEngineProc = pfnBAEngineProc;
m_pvBAEngineProcContext = pvBAEngineProcContext;
}
private:
long m_cReferences;
PFN_BOOTSTRAPPER_ENGINE_PROC m_pfnBAEngineProc;
LPVOID m_pvBAEngineProcContext;
};
HRESULT BalBootstrapperEngineCreate(
__in PFN_BOOTSTRAPPER_ENGINE_PROC pfnBAEngineProc,
__in_opt LPVOID pvBAEngineProcContext,
__out IBootstrapperEngine** ppBootstrapperEngine
)
{
HRESULT hr = S_OK;
CBalBootstrapperEngine* pBootstrapperEngine = NULL;
pBootstrapperEngine = new CBalBootstrapperEngine(pfnBAEngineProc, pvBAEngineProcContext);
ExitOnNull(pBootstrapperEngine, hr, E_OUTOFMEMORY, "Failed to allocate new BalBootstrapperEngine object.");
hr = pBootstrapperEngine->QueryInterface(IID_PPV_ARGS(ppBootstrapperEngine));
ExitOnFailure(hr, "Failed to QI for IBootstrapperEngine from BalBootstrapperEngine object.");
LExit:
ReleaseObject(pBootstrapperEngine);
return hr;
}

Просмотреть файл

@ -0,0 +1,124 @@
// Copyright (c) .NET Foundation and contributors. All rights reserved. Licensed under the Microsoft Reciprocal License. See LICENSE.TXT file in the project root for full license information.
#include "precomp.h"
// prototypes
DAPI_(HRESULT) BalConditionsParseFromXml(
__in BAL_CONDITIONS* pConditions,
__in IXMLDOMDocument* pixdManifest,
__in_opt WIX_LOCALIZATION* pWixLoc
)
{
HRESULT hr = S_OK;
IXMLDOMNodeList* pNodeList = NULL;
IXMLDOMNode* pNode = NULL;
BAL_CONDITION* prgConditions = NULL;
DWORD cConditions = 0;
hr = XmlSelectNodes(pixdManifest, L"/BootstrapperApplicationData/WixBalCondition", &pNodeList);
ExitOnFailure(hr, "Failed to select all conditions.");
hr = pNodeList->get_length(reinterpret_cast<long*>(&cConditions));
ExitOnFailure(hr, "Failed to get the condition count.");
if (!cConditions)
{
ExitFunction();
}
prgConditions = static_cast<BAL_CONDITION*>(MemAlloc(sizeof(BAL_CONDITION) * cConditions, TRUE));
ExitOnNull(prgConditions, hr, E_OUTOFMEMORY, "Failed to allocate memory for conditions.");
DWORD iCondition = 0;
while (S_OK == (hr = XmlNextElement(pNodeList, &pNode, NULL)))
{
hr = XmlGetAttributeEx(pNode, L"Condition", &prgConditions[iCondition].sczCondition);
ExitOnFailure(hr, "Failed to get condition for condition.");
hr = XmlGetAttributeEx(pNode, L"Message", &prgConditions[iCondition].sczMessage);
ExitOnFailure(hr, "Failed to get message for condition.");
if (pWixLoc && prgConditions[iCondition].sczMessage && *prgConditions[iCondition].sczMessage)
{
hr = LocLocalizeString(pWixLoc, &prgConditions[iCondition].sczMessage);
ExitOnFailure(hr, "Failed to localize condition message.");
}
++iCondition;
ReleaseNullObject(pNode);
}
ExitOnFailure(hr, "Failed to parse all condition elements.");
if (S_FALSE == hr)
{
hr = S_OK;
}
pConditions->cConditions = cConditions;
pConditions->rgConditions = prgConditions;
prgConditions = NULL;
LExit:
ReleaseMem(prgConditions);
ReleaseObject(pNode);
ReleaseObject(pNodeList);
return hr;
}
//the contents of psczMessage may be sensitive, should keep encrypted and SecureZeroFree
DAPI_(HRESULT) BalConditionEvaluate(
__in BAL_CONDITION* pCondition,
__in IBootstrapperEngine* pEngine,
__out BOOL* pfResult,
__out_z_opt LPWSTR* psczMessage
)
{
HRESULT hr = S_OK;
DWORD_PTR cchMessage = 0;
hr = pEngine->EvaluateCondition(pCondition->sczCondition, pfResult);
ExitOnFailure(hr, "Failed to evaluate condition with bootstrapper engine.");
if (psczMessage)
{
if (*psczMessage)
{
hr = StrMaxLength(*psczMessage, &cchMessage);
ExitOnFailure(hr, "Failed to get length of message.");
}
hr = pEngine->FormatString(pCondition->sczMessage, *psczMessage, reinterpret_cast<DWORD*>(&cchMessage));
if (E_MOREDATA == hr)
{
++cchMessage;
hr = StrAllocSecure(psczMessage, cchMessage);
ExitOnFailure(hr, "Failed to allocate string for condition's formatted message.");
hr = pEngine->FormatString(pCondition->sczMessage, *psczMessage, reinterpret_cast<DWORD*>(&cchMessage));
}
ExitOnFailure(hr, "Failed to format condition's message.");
}
LExit:
return hr;
}
DAPI_(void) BalConditionsUninitialize(
__in BAL_CONDITIONS* pConditions
)
{
for (DWORD i = 0; i < pConditions->cConditions; ++i)
{
ReleaseStr(pConditions->rgConditions[i].sczMessage);
ReleaseStr(pConditions->rgConditions[i].sczCondition);
}
ReleaseMem(pConditions->rgConditions);
memset(pConditions, 0, sizeof(BAL_CONDITIONS));
}

288
src/balutil/balinfo.cpp Normal file
Просмотреть файл

@ -0,0 +1,288 @@
// Copyright (c) .NET Foundation and contributors. All rights reserved. Licensed under the Microsoft Reciprocal License. See LICENSE.TXT file in the project root for full license information.
#include "precomp.h"
// prototypes
static HRESULT ParsePackagesFromXml(
__in BAL_INFO_PACKAGES* pPackages,
__in IXMLDOMDocument* pixdManifest
);
DAPI_(HRESULT) BalInfoParseFromXml(
__in BAL_INFO_BUNDLE* pBundle,
__in IXMLDOMDocument* pixdManifest
)
{
HRESULT hr = S_OK;
IXMLDOMNode* pNode = NULL;
hr = XmlSelectSingleNode(pixdManifest, L"/BootstrapperApplicationData/WixBundleProperties", &pNode);
ExitOnFailure(hr, "Failed to select bundle information.");
if (S_OK == hr)
{
hr = XmlGetYesNoAttribute(pNode, L"PerMachine", &pBundle->fPerMachine);
if (E_NOTFOUND != hr)
{
ExitOnFailure(hr, "Failed to read bundle information per-machine.");
}
hr = XmlGetAttributeEx(pNode, L"DisplayName", &pBundle->sczName);
if (E_NOTFOUND != hr)
{
ExitOnFailure(hr, "Failed to read bundle information display name.");
}
hr = XmlGetAttributeEx(pNode, L"LogPathVariable", &pBundle->sczLogVariable);
if (E_NOTFOUND != hr)
{
ExitOnFailure(hr, "Failed to read bundle information log path variable.");
}
}
hr = ParsePackagesFromXml(&pBundle->packages, pixdManifest);
BalExitOnFailure(hr, "Failed to parse package information from bootstrapper application data.");
LExit:
ReleaseObject(pNode);
return hr;
}
DAPI_(HRESULT) BalInfoAddRelatedBundleAsPackage(
__in BAL_INFO_PACKAGES* pPackages,
__in LPCWSTR wzId,
__in BOOTSTRAPPER_RELATION_TYPE relationType,
__in BOOL /*fPerMachine*/
)
{
HRESULT hr = S_OK;
BAL_INFO_PACKAGE_TYPE type = BAL_INFO_PACKAGE_TYPE_UNKNOWN;
BAL_INFO_PACKAGE* pPackage = NULL;
// Ensure we have a supported relation type.
switch (relationType)
{
case BOOTSTRAPPER_RELATION_ADDON:
type = BAL_INFO_PACKAGE_TYPE_BUNDLE_ADDON;
break;
case BOOTSTRAPPER_RELATION_PATCH:
type = BAL_INFO_PACKAGE_TYPE_BUNDLE_PATCH;
break;
case BOOTSTRAPPER_RELATION_UPGRADE:
type = BAL_INFO_PACKAGE_TYPE_BUNDLE_UPGRADE;
break;
default:
ExitOnFailure(hr = E_INVALIDARG, "Unknown related bundle type: %u", relationType);
}
// Check to see if the bundle is already in the list of packages.
for (DWORD i = 0; i < pPackages->cPackages; ++i)
{
if (CSTR_EQUAL == ::CompareStringW(LOCALE_NEUTRAL, 0, wzId, -1, pPackages->rgPackages[i].sczId, -1))
{
ExitFunction1(hr = HRESULT_FROM_WIN32(ERROR_ALREADY_EXISTS));
}
}
// Add the related bundle as a package.
hr = MemEnsureArraySize(reinterpret_cast<LPVOID*>(&pPackages->rgPackages), pPackages->cPackages + 1, sizeof(BAL_INFO_PACKAGE), 2);
ExitOnFailure(hr, "Failed to allocate memory for related bundle package information.");
pPackage = pPackages->rgPackages + pPackages->cPackages;
++pPackages->cPackages;
hr = StrAllocString(&pPackage->sczId, wzId, 0);
ExitOnFailure(hr, "Failed to copy related bundle package id.");
pPackage->type = type;
// TODO: try to look up the DisplayName and Description in Add/Remove Programs with the wzId.
LExit:
return hr;
}
DAPI_(HRESULT) BalInfoFindPackageById(
__in BAL_INFO_PACKAGES* pPackages,
__in LPCWSTR wzId,
__out BAL_INFO_PACKAGE** ppPackage
)
{
*ppPackage = NULL;
for (DWORD i = 0; i < pPackages->cPackages; ++i)
{
if (CSTR_EQUAL == ::CompareStringW(LOCALE_NEUTRAL, 0, wzId, -1, pPackages->rgPackages[i].sczId, -1))
{
*ppPackage = pPackages->rgPackages + i;
break;
}
}
return *ppPackage ? S_OK : E_NOTFOUND;
}
DAPI_(void) BalInfoUninitialize(
__in BAL_INFO_BUNDLE* pBundle
)
{
for (DWORD i = 0; i < pBundle->packages.cPackages; ++i)
{
ReleaseStr(pBundle->packages.rgPackages[i].sczDisplayName);
ReleaseStr(pBundle->packages.rgPackages[i].sczDescription);
ReleaseStr(pBundle->packages.rgPackages[i].sczId);
ReleaseStr(pBundle->packages.rgPackages[i].sczProductCode);
ReleaseStr(pBundle->packages.rgPackages[i].sczUpgradeCode);
ReleaseStr(pBundle->packages.rgPackages[i].sczVersion);
ReleaseStr(pBundle->packages.rgPackages[i].sczInstallCondition);
}
ReleaseMem(pBundle->packages.rgPackages);
ReleaseStr(pBundle->sczName);
ReleaseStr(pBundle->sczLogVariable);
memset(pBundle, 0, sizeof(BAL_INFO_BUNDLE));
}
static HRESULT ParsePackagesFromXml(
__in BAL_INFO_PACKAGES* pPackages,
__in IXMLDOMDocument* pixdManifest
)
{
HRESULT hr = S_OK;
IXMLDOMNodeList* pNodeList = NULL;
IXMLDOMNode* pNode = NULL;
BAL_INFO_PACKAGE* prgPackages = NULL;
DWORD cPackages = 0;
LPWSTR scz = NULL;
hr = XmlSelectNodes(pixdManifest, L"/BootstrapperApplicationData/WixPackageProperties", &pNodeList);
ExitOnFailure(hr, "Failed to select all packages.");
hr = pNodeList->get_length(reinterpret_cast<long*>(&cPackages));
ExitOnFailure(hr, "Failed to get the package count.");
prgPackages = static_cast<BAL_INFO_PACKAGE*>(MemAlloc(sizeof(BAL_INFO_PACKAGE) * cPackages, TRUE));
ExitOnNull(prgPackages, hr, E_OUTOFMEMORY, "Failed to allocate memory for packages.");
DWORD iPackage = 0;
while (S_OK == (hr = XmlNextElement(pNodeList, &pNode, NULL)))
{
hr = XmlGetAttributeEx(pNode, L"Package", &prgPackages[iPackage].sczId);
ExitOnFailure(hr, "Failed to get package identifier for package.");
hr = XmlGetAttributeEx(pNode, L"DisplayName", &prgPackages[iPackage].sczDisplayName);
if (E_NOTFOUND != hr)
{
ExitOnFailure(hr, "Failed to get display name for package.");
}
hr = XmlGetAttributeEx(pNode, L"Description", &prgPackages[iPackage].sczDescription);
if (E_NOTFOUND != hr)
{
ExitOnFailure(hr, "Failed to get description for package.");
}
hr = XmlGetAttributeEx(pNode, L"PackageType", &scz);
ExitOnFailure(hr, "Failed to get package type for package.");
if (CSTR_EQUAL == ::CompareStringW(LOCALE_NEUTRAL, 0, L"Exe", -1, scz, -1))
{
prgPackages[iPackage].type = BAL_INFO_PACKAGE_TYPE_EXE;
}
else if (CSTR_EQUAL == ::CompareStringW(LOCALE_NEUTRAL, 0, L"Msi", -1, scz, -1))
{
prgPackages[iPackage].type = BAL_INFO_PACKAGE_TYPE_MSI;
}
else if (CSTR_EQUAL == ::CompareStringW(LOCALE_NEUTRAL, 0, L"Msp", -1, scz, -1))
{
prgPackages[iPackage].type = BAL_INFO_PACKAGE_TYPE_MSP;
}
else if (CSTR_EQUAL == ::CompareStringW(LOCALE_NEUTRAL, 0, L"Msu", -1, scz, -1))
{
prgPackages[iPackage].type = BAL_INFO_PACKAGE_TYPE_MSU;
}
hr = XmlGetYesNoAttribute(pNode, L"Permanent", &prgPackages[iPackage].fPermanent);
ExitOnFailure(hr, "Failed to get permanent setting for package.");
hr = XmlGetYesNoAttribute(pNode, L"Vital", &prgPackages[iPackage].fVital);
ExitOnFailure(hr, "Failed to get vital setting for package.");
hr = XmlGetYesNoAttribute(pNode, L"DisplayInternalUI", &prgPackages[iPackage].fDisplayInternalUI);
if (E_NOTFOUND != hr)
{
ExitOnFailure(hr, "Failed to get DisplayInternalUI setting for package.");
}
hr = XmlGetAttributeEx(pNode, L"ProductCode", &prgPackages[iPackage].sczProductCode);
if (E_NOTFOUND != hr)
{
ExitOnFailure(hr, "Failed to get product code for package.");
}
hr = XmlGetAttributeEx(pNode, L"UpgradeCode", &prgPackages[iPackage].sczUpgradeCode);
if (E_NOTFOUND != hr)
{
ExitOnFailure(hr, "Failed to get upgrade code for package.");
}
hr = XmlGetAttributeEx(pNode, L"Version", &prgPackages[iPackage].sczVersion);
if (E_NOTFOUND != hr)
{
ExitOnFailure(hr, "Failed to get version for package.");
}
hr = XmlGetAttributeEx(pNode, L"InstallCondition", &prgPackages[iPackage].sczInstallCondition);
if (E_NOTFOUND != hr)
{
ExitOnFailure(hr, "Failed to get install condition for package.");
}
hr = XmlGetAttributeEx(pNode, L"Cache", &scz);
ExitOnFailure(hr, "Failed to get cache type for package.");
if (CSTR_EQUAL == ::CompareStringW(LOCALE_NEUTRAL, 0, scz, -1, L"no", -1))
{
prgPackages[iPackage].cacheType = BAL_INFO_CACHE_TYPE_NO;
}
else if (CSTR_EQUAL == ::CompareStringW(LOCALE_NEUTRAL, 0, scz, -1, L"yes", -1))
{
prgPackages[iPackage].cacheType = BAL_INFO_CACHE_TYPE_YES;
}
else if (CSTR_EQUAL == ::CompareStringW(LOCALE_NEUTRAL, 0, scz, -1, L"always", -1))
{
prgPackages[iPackage].cacheType = BAL_INFO_CACHE_TYPE_ALWAYS;
}
++iPackage;
ReleaseNullObject(pNode);
}
ExitOnFailure(hr, "Failed to parse all package property elements.");
if (S_FALSE == hr)
{
hr = S_OK;
}
pPackages->cPackages = cPackages;
pPackages->rgPackages = prgPackages;
prgPackages = NULL;
LExit:
ReleaseStr(scz);
ReleaseMem(prgPackages);
ReleaseObject(pNode);
ReleaseObject(pNodeList);
return hr;
}

191
src/balutil/balretry.cpp Normal file
Просмотреть файл

@ -0,0 +1,191 @@
// Copyright (c) .NET Foundation and contributors. All rights reserved. Licensed under the Microsoft Reciprocal License. See LICENSE.TXT file in the project root for full license information.
#include "precomp.h"
struct BALRETRY_INFO
{
LPWSTR sczId; // package or container id.
LPWSTR sczPayloadId; // optional payload id.
DWORD cRetries;
DWORD dwLastError;
};
static DWORD vdwMaxRetries = 0;
static DWORD vdwTimeout = 0;
static BALRETRY_INFO vrgRetryInfo[2];
// prototypes
static BOOL IsActiveRetryEntry(
__in BALRETRY_TYPE type,
__in_z LPCWSTR wzPackageId,
__in_z_opt LPCWSTR wzPayloadId
);
DAPI_(void) BalRetryInitialize(
__in DWORD dwMaxRetries,
__in DWORD dwTimeout
)
{
BalRetryUninitialize(); // clean everything out.
vdwMaxRetries = dwMaxRetries;
vdwTimeout = dwTimeout;
}
DAPI_(void) BalRetryUninitialize()
{
for (DWORD i = 0; i < countof(vrgRetryInfo); ++i)
{
ReleaseStr(vrgRetryInfo[i].sczId);
ReleaseStr(vrgRetryInfo[i].sczPayloadId);
memset(vrgRetryInfo + i, 0, sizeof(BALRETRY_INFO));
}
vdwMaxRetries = 0;
vdwTimeout = 0;
}
DAPI_(void) BalRetryStartPackage(
__in BALRETRY_TYPE type,
__in_z_opt LPCWSTR wzPackageId,
__in_z_opt LPCWSTR wzPayloadId
)
{
if (!wzPackageId || !*wzPackageId)
{
ReleaseNullStr(vrgRetryInfo[type].sczId);
ReleaseNullStr(vrgRetryInfo[type].sczPayloadId);
}
else if (IsActiveRetryEntry(type, wzPackageId, wzPayloadId))
{
++vrgRetryInfo[type].cRetries;
::Sleep(vdwTimeout);
}
else
{
StrAllocString(&vrgRetryInfo[type].sczId, wzPackageId, 0);
if (wzPayloadId)
{
StrAllocString(&vrgRetryInfo[type].sczPayloadId, wzPayloadId, 0);
}
vrgRetryInfo[type].cRetries = 0;
}
vrgRetryInfo[type].dwLastError = ERROR_SUCCESS;
}
DAPI_(void) BalRetryErrorOccurred(
__in_z LPCWSTR wzPackageId,
__in DWORD dwError
)
{
if (IsActiveRetryEntry(BALRETRY_TYPE_CACHE, wzPackageId, NULL))
{
vrgRetryInfo[BALRETRY_TYPE_CACHE].dwLastError = dwError;
}
else if (IsActiveRetryEntry(BALRETRY_TYPE_EXECUTE, wzPackageId, NULL))
{
vrgRetryInfo[BALRETRY_TYPE_EXECUTE].dwLastError = dwError;
}
}
DAPI_(HRESULT) BalRetryEndPackage(
__in BALRETRY_TYPE type,
__in_z_opt LPCWSTR wzPackageId,
__in_z_opt LPCWSTR wzPayloadId,
__in HRESULT hrError,
__inout BOOL* pfRetry
)
{
HRESULT hr = S_OK;
if (!wzPackageId || !*wzPackageId)
{
ReleaseNullStr(vrgRetryInfo[type].sczId);
ReleaseNullStr(vrgRetryInfo[type].sczPayloadId);
}
else if (FAILED(hrError) && vrgRetryInfo[type].cRetries < vdwMaxRetries && IsActiveRetryEntry(type, wzPackageId, wzPayloadId))
{
if (BALRETRY_TYPE_CACHE == type)
{
// Retry on all errors except the following.
if (HRESULT_FROM_WIN32(ERROR_INSTALL_USEREXIT) != hrError &&
BG_E_NETWORK_DISCONNECTED != hrError &&
HRESULT_FROM_WIN32(ERROR_FILE_NOT_FOUND) != hrError &&
HRESULT_FROM_WIN32(ERROR_INTERNET_NAME_NOT_RESOLVED) != hrError)
{
*pfRetry = TRUE;
}
}
else if (BALRETRY_TYPE_EXECUTE == type)
{
// If the service is out of whack, just try again.
if (HRESULT_FROM_WIN32(ERROR_INSTALL_SERVICE_FAILURE) == hrError)
{
*pfRetry = TRUE;
}
else if (HRESULT_FROM_WIN32(ERROR_INSTALL_FAILURE) == hrError)
{
DWORD dwError = vrgRetryInfo[type].dwLastError;
// If we failed with one of these specific error codes, then retry since
// we've seen these have a high success of succeeding on retry.
if (1303 == dwError ||
1304 == dwError ||
1306 == dwError ||
1307 == dwError ||
1309 == dwError ||
1310 == dwError ||
1311 == dwError ||
1312 == dwError ||
1316 == dwError ||
1317 == dwError ||
1321 == dwError ||
1335 == dwError ||
1402 == dwError ||
1406 == dwError ||
1606 == dwError ||
1706 == dwError ||
1719 == dwError ||
1723 == dwError ||
1923 == dwError ||
1931 == dwError)
{
*pfRetry = TRUE;
}
}
else if (HRESULT_FROM_WIN32(ERROR_INSTALL_ALREADY_RUNNING) == hrError)
{
*pfRetry = TRUE;
}
}
}
return hr;
}
// Internal functions.
static BOOL IsActiveRetryEntry(
__in BALRETRY_TYPE type,
__in_z LPCWSTR wzPackageId,
__in_z_opt LPCWSTR wzPayloadId
)
{
BOOL fActive = FALSE;
fActive = vrgRetryInfo[type].sczId && CSTR_EQUAL == ::CompareStringW(LOCALE_NEUTRAL, 0, wzPackageId, -1, vrgRetryInfo[type].sczId, -1);
if (fActive && wzPayloadId) // if a payload id was provided ensure it matches.
{
fActive = vrgRetryInfo[type].sczPayloadId && CSTR_EQUAL == ::CompareStringW(LOCALE_NEUTRAL, 0, wzPayloadId, -1, vrgRetryInfo[type].sczPayloadId, -1);
}
return fActive;
}

382
src/balutil/balutil.cpp Normal file
Просмотреть файл

@ -0,0 +1,382 @@
// Copyright (c) .NET Foundation and contributors. All rights reserved. Licensed under the Microsoft Reciprocal License. See LICENSE.TXT file in the project root for full license information.
#include "precomp.h"
const DWORD VARIABLE_GROW_FACTOR = 80;
static IBootstrapperEngine* vpEngine = NULL;
// prototypes
DAPI_(void) BalInitialize(
__in IBootstrapperEngine* pEngine
)
{
pEngine->AddRef();
ReleaseObject(vpEngine);
vpEngine = pEngine;
}
DAPI_(HRESULT) BalInitializeFromCreateArgs(
__in const BOOTSTRAPPER_CREATE_ARGS* pArgs,
__out_opt IBootstrapperEngine** ppEngine
)
{
HRESULT hr = S_OK;
IBootstrapperEngine* pEngine = NULL;
hr = BalBootstrapperEngineCreate(pArgs->pfnBootstrapperEngineProc, pArgs->pvBootstrapperEngineProcContext, &pEngine);
ExitOnFailure(hr, "Failed to create BalBootstrapperEngine.");
BalInitialize(pEngine);
if (ppEngine)
{
*ppEngine = pEngine;
}
pEngine = NULL;
LExit:
ReleaseObject(pEngine);
return hr;
}
DAPI_(void) BalUninitialize()
{
ReleaseNullObject(vpEngine);
}
DAPI_(HRESULT) BalManifestLoad(
__in HMODULE hBootstrapperApplicationModule,
__out IXMLDOMDocument** ppixdManifest
)
{
HRESULT hr = S_OK;
LPWSTR sczPath = NULL;
hr = PathRelativeToModule(&sczPath, BAL_MANIFEST_FILENAME, hBootstrapperApplicationModule);
ExitOnFailure(hr, "Failed to get path to bootstrapper application manifest: %ls", BAL_MANIFEST_FILENAME);
hr = XmlLoadDocumentFromFile(sczPath, ppixdManifest);
ExitOnFailure(hr, "Failed to load bootstrapper application manifest '%ls' from path: %ls", BAL_MANIFEST_FILENAME, sczPath);
LExit:
ReleaseStr(sczPath);
return hr;
}
DAPI_(HRESULT) BalEvaluateCondition(
__in_z LPCWSTR wzCondition,
__out BOOL* pf
)
{
HRESULT hr = S_OK;
if (!vpEngine)
{
hr = E_POINTER;
ExitOnRootFailure(hr, "BalInitialize() must be called first.");
}
hr = vpEngine->EvaluateCondition(wzCondition, pf);
LExit:
return hr;
}
// The contents of psczOut may be sensitive, should keep encrypted and SecureZeroFree.
DAPI_(HRESULT) BalFormatString(
__in_z LPCWSTR wzFormat,
__inout LPWSTR* psczOut
)
{
HRESULT hr = S_OK;
DWORD cch = 0;
if (!vpEngine)
{
hr = E_POINTER;
ExitOnRootFailure(hr, "BalInitialize() must be called first.");
}
if (*psczOut)
{
hr = StrMaxLength(*psczOut, reinterpret_cast<DWORD_PTR*>(&cch));
ExitOnFailure(hr, "Failed to determine length of value.");
}
hr = vpEngine->FormatString(wzFormat, *psczOut, &cch);
if (E_MOREDATA == hr)
{
++cch;
hr = StrAllocSecure(psczOut, cch);
ExitOnFailure(hr, "Failed to allocate value.");
hr = vpEngine->FormatString(wzFormat, *psczOut, &cch);
}
LExit:
return hr;
}
// The contents of pllValue may be sensitive, if variable is hidden should keep value encrypted and SecureZeroMemory.
DAPI_(HRESULT) BalGetNumericVariable(
__in_z LPCWSTR wzVariable,
__out LONGLONG* pllValue
)
{
HRESULT hr = S_OK;
if (!vpEngine)
{
hr = E_POINTER;
ExitOnRootFailure(hr, "BalInitialize() must be called first.");
}
hr = vpEngine->GetVariableNumeric(wzVariable, pllValue);
LExit:
return hr;
}
DAPI_(HRESULT) BalSetNumericVariable(
__in_z LPCWSTR wzVariable,
__in LONGLONG llValue
)
{
HRESULT hr = S_OK;
if (!vpEngine)
{
hr = E_POINTER;
ExitOnRootFailure(hr, "BalInitialize() must be called first.");
}
hr = vpEngine->SetVariableNumeric(wzVariable, llValue);
LExit:
return hr;
}
DAPI_(BOOL) BalStringVariableExists(
__in_z LPCWSTR wzVariable
)
{
HRESULT hr = S_OK;
DWORD cch = 0;
if (!vpEngine)
{
hr = E_POINTER;
ExitOnRootFailure(hr, "BalInitialize() must be called first.");
}
hr = vpEngine->GetVariableString(wzVariable, NULL, &cch);
LExit:
return E_MOREDATA == hr; // string exists only if there are more than zero characters in the variable.
}
// The contents of psczValue may be sensitive, if variable is hidden should keep value encrypted and SecureZeroFree.
DAPI_(HRESULT) BalGetStringVariable(
__in_z LPCWSTR wzVariable,
__inout LPWSTR* psczValue
)
{
HRESULT hr = S_OK;
DWORD cch = 0;
if (!vpEngine)
{
hr = E_POINTER;
ExitOnRootFailure(hr, "BalInitialize() must be called first.");
}
if (*psczValue)
{
hr = StrMaxLength(*psczValue, reinterpret_cast<DWORD_PTR*>(&cch));
ExitOnFailure(hr, "Failed to determine length of value.");
}
hr = vpEngine->GetVariableString(wzVariable, *psczValue, &cch);
if (E_MOREDATA == hr)
{
++cch;
hr = StrAllocSecure(psczValue, cch);
ExitOnFailure(hr, "Failed to allocate value.");
hr = vpEngine->GetVariableString(wzVariable, *psczValue, &cch);
}
LExit:
return hr;
}
DAPI_(HRESULT) BalSetStringVariable(
__in_z LPCWSTR wzVariable,
__in_z_opt LPCWSTR wzValue
)
{
HRESULT hr = S_OK;
if (!vpEngine)
{
hr = E_POINTER;
ExitOnRootFailure(hr, "BalInitialize() must be called first.");
}
hr = vpEngine->SetVariableString(wzVariable, wzValue);
LExit:
return hr;
}
DAPIV_(HRESULT) BalLog(
__in BOOTSTRAPPER_LOG_LEVEL level,
__in_z __format_string LPCSTR szFormat,
...
)
{
HRESULT hr = S_OK;
va_list args;
LPSTR sczFormattedAnsi = NULL;
LPWSTR sczMessage = NULL;
if (!vpEngine)
{
hr = E_POINTER;
ExitOnRootFailure(hr, "BalInitialize() must be called first.");
}
va_start(args, szFormat);
hr = StrAnsiAllocFormattedArgs(&sczFormattedAnsi, szFormat, args);
va_end(args);
ExitOnFailure(hr, "Failed to format log string.");
hr = StrAllocStringAnsi(&sczMessage, sczFormattedAnsi, 0, CP_UTF8);
ExitOnFailure(hr, "Failed to convert log string to Unicode.");
hr = vpEngine->Log(level, sczMessage);
LExit:
ReleaseStr(sczMessage);
ReleaseStr(sczFormattedAnsi);
return hr;
}
DAPIV_(HRESULT) BalLogError(
__in HRESULT hrError,
__in_z __format_string LPCSTR szFormat,
...
)
{
HRESULT hr = S_OK;
va_list args;
LPSTR sczFormattedAnsi = NULL;
LPWSTR sczMessage = NULL;
if (!vpEngine)
{
hr = E_POINTER;
ExitOnRootFailure(hr, "BalInitialize() must be called first.");
}
va_start(args, szFormat);
hr = StrAnsiAllocFormattedArgs(&sczFormattedAnsi, szFormat, args);
va_end(args);
ExitOnFailure(hr, "Failed to format error log string.");
hr = StrAllocFormatted(&sczMessage, L"Error 0x%08x: %S", hrError, sczFormattedAnsi);
ExitOnFailure(hr, "Failed to prepend error number to error log string.");
hr = vpEngine->Log(BOOTSTRAPPER_LOG_LEVEL_ERROR, sczMessage);
LExit:
ReleaseStr(sczMessage);
ReleaseStr(sczFormattedAnsi);
return hr;
}
DAPIV_(HRESULT) BalLogId(
__in BOOTSTRAPPER_LOG_LEVEL level,
__in DWORD dwLogId,
__in HMODULE hModule,
...
)
{
HRESULT hr = S_OK;
va_list args;
if (!vpEngine)
{
hr = E_POINTER;
ExitOnRootFailure(hr, "BalInitialize() must be called first.");
}
va_start(args, hModule);
hr = BalLogIdArgs(level, dwLogId, hModule, args);
va_end(args);
LExit:
return hr;
}
DAPI_(HRESULT) BalLogIdArgs(
__in BOOTSTRAPPER_LOG_LEVEL level,
__in DWORD dwLogId,
__in HMODULE hModule,
__in va_list args
)
{
HRESULT hr = S_OK;
LPWSTR pwz = NULL;
DWORD cch = 0;
if (!vpEngine)
{
hr = E_POINTER;
ExitOnRootFailure(hr, "BalInitialize() must be called first.");
}
// Get the string for the id.
#pragma prefast(push)
#pragma prefast(disable:25028)
#pragma prefast(disable:25068)
cch = ::FormatMessageW(FORMAT_MESSAGE_ALLOCATE_BUFFER | FORMAT_MESSAGE_FROM_HMODULE,
static_cast<LPCVOID>(hModule), dwLogId, 0, reinterpret_cast<LPWSTR>(&pwz), 0, &args);
#pragma prefast(pop)
if (0 == cch)
{
ExitOnLastError(hr, "Failed to log id: %d", dwLogId);
}
if (2 <= cch && L'\r' == pwz[cch - 2] && L'\n' == pwz[cch - 1])
{
pwz[cch - 2] = L'\0'; // remove newline from message table.
}
hr = vpEngine->Log(level, pwz);
LExit:
if (pwz)
{
::LocalFree(pwz);
}
return hr;
}

Просмотреть файл

@ -0,0 +1,130 @@
#pragma once
// Copyright (c) .NET Foundation and contributors. All rights reserved. Licensed under the Microsoft Reciprocal License. See LICENSE.TXT file in the project root for full license information.
#ifdef __cplusplus
extern "C" {
#endif
// The first 1024 messages are reserved so that the BA messages have the same value here.
enum BA_FUNCTIONS_MESSAGE
{
BA_FUNCTIONS_MESSAGE_ONDETECTBEGIN = BOOTSTRAPPER_APPLICATION_MESSAGE_ONDETECTBEGIN,
BA_FUNCTIONS_MESSAGE_ONDETECTCOMPLETE = BOOTSTRAPPER_APPLICATION_MESSAGE_ONDETECTCOMPLETE,
BA_FUNCTIONS_MESSAGE_ONPLANBEGIN = BOOTSTRAPPER_APPLICATION_MESSAGE_ONPLANBEGIN,
BA_FUNCTIONS_MESSAGE_ONPLANCOMPLETE = BOOTSTRAPPER_APPLICATION_MESSAGE_ONPLANCOMPLETE,
BA_FUNCTIONS_MESSAGE_ONSTARTUP = BOOTSTRAPPER_APPLICATION_MESSAGE_ONSTARTUP,
BA_FUNCTIONS_MESSAGE_ONSHUTDOWN = BOOTSTRAPPER_APPLICATION_MESSAGE_ONSHUTDOWN,
BA_FUNCTIONS_MESSAGE_ONSYSTEMSHUTDOWN = BOOTSTRAPPER_APPLICATION_MESSAGE_ONSYSTEMSHUTDOWN,
BA_FUNCTIONS_MESSAGE_ONDETECTFORWARDCOMPATIBLEBUNDLE = BOOTSTRAPPER_APPLICATION_MESSAGE_ONDETECTFORWARDCOMPATIBLEBUNDLE,
BA_FUNCTIONS_MESSAGE_ONDETECTUPDATEBEGIN = BOOTSTRAPPER_APPLICATION_MESSAGE_ONDETECTUPDATEBEGIN,
BA_FUNCTIONS_MESSAGE_ONDETECTUPDATE = BOOTSTRAPPER_APPLICATION_MESSAGE_ONDETECTUPDATE,
BA_FUNCTIONS_MESSAGE_ONDETECTUPDATECOMPLETE = BOOTSTRAPPER_APPLICATION_MESSAGE_ONDETECTUPDATECOMPLETE,
BA_FUNCTIONS_MESSAGE_ONDETECTRELATEDBUNDLE = BOOTSTRAPPER_APPLICATION_MESSAGE_ONDETECTRELATEDBUNDLE,
BA_FUNCTIONS_MESSAGE_ONDETECTPACKAGEBEGIN = BOOTSTRAPPER_APPLICATION_MESSAGE_ONDETECTPACKAGEBEGIN,
BA_FUNCTIONS_MESSAGE_ONDETECTCOMPATIBLEMSIPACKAGE = BOOTSTRAPPER_APPLICATION_MESSAGE_ONDETECTCOMPATIBLEMSIPACKAGE,
BA_FUNCTIONS_MESSAGE_ONDETECTRELATEDMSIPACKAGE = BOOTSTRAPPER_APPLICATION_MESSAGE_ONDETECTRELATEDMSIPACKAGE,
BA_FUNCTIONS_MESSAGE_ONDETECTTARGETMSIPACKAGE = BOOTSTRAPPER_APPLICATION_MESSAGE_ONDETECTTARGETMSIPACKAGE,
BA_FUNCTIONS_MESSAGE_ONDETECTMSIFEATURE = BOOTSTRAPPER_APPLICATION_MESSAGE_ONDETECTMSIFEATURE,
BA_FUNCTIONS_MESSAGE_ONDETECTPACKAGECOMPLETE = BOOTSTRAPPER_APPLICATION_MESSAGE_ONDETECTPACKAGECOMPLETE,
BA_FUNCTIONS_MESSAGE_ONPLANRELATEDBUNDLE = BOOTSTRAPPER_APPLICATION_MESSAGE_ONPLANRELATEDBUNDLE,
BA_FUNCTIONS_MESSAGE_ONPLANPACKAGEBEGIN = BOOTSTRAPPER_APPLICATION_MESSAGE_ONPLANPACKAGEBEGIN,
BA_FUNCTIONS_MESSAGE_ONPLANCOMPATIBLEMSIPACKAGEBEGIN = BOOTSTRAPPER_APPLICATION_MESSAGE_ONPLANCOMPATIBLEMSIPACKAGEBEGIN,
BA_FUNCTIONS_MESSAGE_ONPLANCOMPATIBLEMSIPACKAGECOMPLETE = BOOTSTRAPPER_APPLICATION_MESSAGE_ONPLANCOMPATIBLEMSIPACKAGECOMPLETE,
BA_FUNCTIONS_MESSAGE_ONPLANTARGETMSIPACKAGE = BOOTSTRAPPER_APPLICATION_MESSAGE_ONPLANTARGETMSIPACKAGE,
BA_FUNCTIONS_MESSAGE_ONPLANMSIFEATURE = BOOTSTRAPPER_APPLICATION_MESSAGE_ONPLANMSIFEATURE,
BA_FUNCTIONS_MESSAGE_ONPLANPACKAGECOMPLETE = BOOTSTRAPPER_APPLICATION_MESSAGE_ONPLANPACKAGECOMPLETE,
BA_FUNCTIONS_MESSAGE_ONAPPLYBEGIN = BOOTSTRAPPER_APPLICATION_MESSAGE_ONAPPLYBEGIN,
BA_FUNCTIONS_MESSAGE_ONELEVATEBEGIN = BOOTSTRAPPER_APPLICATION_MESSAGE_ONELEVATEBEGIN,
BA_FUNCTIONS_MESSAGE_ONELEVATECOMPLETE = BOOTSTRAPPER_APPLICATION_MESSAGE_ONELEVATECOMPLETE,
BA_FUNCTIONS_MESSAGE_ONPROGRESS = BOOTSTRAPPER_APPLICATION_MESSAGE_ONPROGRESS,
BA_FUNCTIONS_MESSAGE_ONERROR = BOOTSTRAPPER_APPLICATION_MESSAGE_ONERROR,
BA_FUNCTIONS_MESSAGE_ONREGISTERBEGIN = BOOTSTRAPPER_APPLICATION_MESSAGE_ONREGISTERBEGIN,
BA_FUNCTIONS_MESSAGE_ONREGISTERCOMPLETE = BOOTSTRAPPER_APPLICATION_MESSAGE_ONREGISTERCOMPLETE,
BA_FUNCTIONS_MESSAGE_ONCACHEBEGIN = BOOTSTRAPPER_APPLICATION_MESSAGE_ONCACHEBEGIN,
BA_FUNCTIONS_MESSAGE_ONCACHEPACKAGEBEGIN = BOOTSTRAPPER_APPLICATION_MESSAGE_ONCACHEPACKAGEBEGIN,
BA_FUNCTIONS_MESSAGE_ONCACHEACQUIREBEGIN = BOOTSTRAPPER_APPLICATION_MESSAGE_ONCACHEACQUIREBEGIN,
BA_FUNCTIONS_MESSAGE_ONCACHEACQUIREPROGRESS = BOOTSTRAPPER_APPLICATION_MESSAGE_ONCACHEACQUIREPROGRESS,
BA_FUNCTIONS_MESSAGE_ONRESOLVESOURCE = BOOTSTRAPPER_APPLICATION_MESSAGE_ONRESOLVESOURCE,
BA_FUNCTIONS_MESSAGE_ONCACHEACQUIRECOMPLETE = BOOTSTRAPPER_APPLICATION_MESSAGE_ONCACHEACQUIRECOMPLETE,
BA_FUNCTIONS_MESSAGE_ONCACHEVERIFYBEGIN = BOOTSTRAPPER_APPLICATION_MESSAGE_ONCACHEVERIFYBEGIN,
BA_FUNCTIONS_MESSAGE_ONCACHEVERIFYCOMPLETE = BOOTSTRAPPER_APPLICATION_MESSAGE_ONCACHEVERIFYCOMPLETE,
BA_FUNCTIONS_MESSAGE_ONCACHEPACKAGECOMPLETE = BOOTSTRAPPER_APPLICATION_MESSAGE_ONCACHEPACKAGECOMPLETE,
BA_FUNCTIONS_MESSAGE_ONCACHECOMPLETE = BOOTSTRAPPER_APPLICATION_MESSAGE_ONCACHECOMPLETE,
BA_FUNCTIONS_MESSAGE_ONEXECUTEBEGIN = BOOTSTRAPPER_APPLICATION_MESSAGE_ONEXECUTEBEGIN,
BA_FUNCTIONS_MESSAGE_ONEXECUTEPACKAGEBEGIN = BOOTSTRAPPER_APPLICATION_MESSAGE_ONEXECUTEPACKAGEBEGIN,
BA_FUNCTIONS_MESSAGE_ONEXECUTEPATCHTARGET = BOOTSTRAPPER_APPLICATION_MESSAGE_ONEXECUTEPATCHTARGET,
BA_FUNCTIONS_MESSAGE_ONEXECUTEPROGRESS = BOOTSTRAPPER_APPLICATION_MESSAGE_ONEXECUTEPROGRESS,
BA_FUNCTIONS_MESSAGE_ONEXECUTEMSIMESSAGE = BOOTSTRAPPER_APPLICATION_MESSAGE_ONEXECUTEMSIMESSAGE,
BA_FUNCTIONS_MESSAGE_ONEXECUTEFILESINUSE = BOOTSTRAPPER_APPLICATION_MESSAGE_ONEXECUTEFILESINUSE,
BA_FUNCTIONS_MESSAGE_ONEXECUTEPACKAGECOMPLETE = BOOTSTRAPPER_APPLICATION_MESSAGE_ONEXECUTEPACKAGECOMPLETE,
BA_FUNCTIONS_MESSAGE_ONEXECUTECOMPLETE = BOOTSTRAPPER_APPLICATION_MESSAGE_ONEXECUTECOMPLETE,
BA_FUNCTIONS_MESSAGE_ONUNREGISTERBEGIN = BOOTSTRAPPER_APPLICATION_MESSAGE_ONUNREGISTERBEGIN,
BA_FUNCTIONS_MESSAGE_ONUNREGISTERCOMPLETE = BOOTSTRAPPER_APPLICATION_MESSAGE_ONUNREGISTERCOMPLETE,
BA_FUNCTIONS_MESSAGE_ONAPPLYCOMPLETE = BOOTSTRAPPER_APPLICATION_MESSAGE_ONAPPLYCOMPLETE,
BA_FUNCTIONS_MESSAGE_ONLAUNCHAPPROVEDEXEBEGIN = BOOTSTRAPPER_APPLICATION_MESSAGE_ONLAUNCHAPPROVEDEXEBEGIN,
BA_FUNCTIONS_MESSAGE_ONLAUNCHAPPROVEDEXECOMPLETE = BOOTSTRAPPER_APPLICATION_MESSAGE_ONLAUNCHAPPROVEDEXECOMPLETE,
BA_FUNCTIONS_MESSAGE_ONTHEMELOADED = 1024,
BA_FUNCTIONS_MESSAGE_WNDPROC,
};
typedef HRESULT(WINAPI *PFN_BA_FUNCTIONS_PROC)(
__in BA_FUNCTIONS_MESSAGE message,
__in const LPVOID pvArgs,
__inout LPVOID pvResults,
__in_opt LPVOID pvContext
);
struct BA_FUNCTIONS_CREATE_ARGS
{
DWORD cbSize;
DWORD64 qwBAFunctionsAPIVersion;
BOOTSTRAPPER_CREATE_ARGS* pBootstrapperCreateArgs;
};
struct BA_FUNCTIONS_CREATE_RESULTS
{
DWORD cbSize;
PFN_BA_FUNCTIONS_PROC pfnBAFunctionsProc;
LPVOID pvBAFunctionsProcContext;
};
struct BA_FUNCTIONS_ONTHEMELOADED_ARGS
{
DWORD cbSize;
THEME* pTheme;
WIX_LOCALIZATION* pWixLoc;
};
struct BA_FUNCTIONS_ONTHEMELOADED_RESULTS
{
DWORD cbSize;
};
struct BA_FUNCTIONS_WNDPROC_ARGS
{
DWORD cbSize;
THEME* pTheme;
HWND hWnd;
UINT uMsg;
WPARAM wParam;
LPARAM lParam;
};
struct BA_FUNCTIONS_WNDPROC_RESULTS
{
DWORD cbSize;
LRESULT lres;
};
typedef HRESULT(WINAPI *PFN_BA_FUNCTIONS_CREATE)(
__in const BA_FUNCTIONS_CREATE_ARGS* pArgs,
__inout BA_FUNCTIONS_CREATE_RESULTS* pResults
);
typedef void (WINAPI *PFN_BA_FUNCTIONS_DESTROY)();
#ifdef __cplusplus
}
#endif

Просмотреть файл

@ -0,0 +1,700 @@
#pragma once
// Copyright (c) .NET Foundation and contributors. All rights reserved. Licensed under the Microsoft Reciprocal License. See LICENSE.TXT file in the project root for full license information.
#include <windows.h>
#include <msiquery.h>
#include "dutil.h"
#include "locutil.h"
#include "thmutil.h"
#include "BAFunctions.h"
#include "IBAFunctions.h"
#include "BootstrapperEngine.h"
#include "BootstrapperApplication.h"
#include "IBootstrapperEngine.h"
#include "IBootstrapperApplication.h"
class CBalBaseBAFunctions : public IBAFunctions
{
public: // IUnknown
virtual STDMETHODIMP QueryInterface(
__in REFIID riid,
__out LPVOID *ppvObject
)
{
if (!ppvObject)
{
return E_INVALIDARG;
}
*ppvObject = NULL;
if (::IsEqualIID(__uuidof(IBAFunctions), riid))
{
*ppvObject = static_cast<IBAFunctions*>(this);
}
else if (::IsEqualIID(__uuidof(IBootstrapperApplication), riid))
{
*ppvObject = static_cast<IBootstrapperApplication*>(this);
}
else if (::IsEqualIID(IID_IUnknown, riid))
{
*ppvObject = static_cast<IUnknown*>(this);
}
else // no interface for requested iid
{
return E_NOINTERFACE;
}
AddRef();
return S_OK;
}
virtual STDMETHODIMP_(ULONG) AddRef()
{
return ::InterlockedIncrement(&this->m_cReferences);
}
virtual STDMETHODIMP_(ULONG) Release()
{
long l = ::InterlockedDecrement(&this->m_cReferences);
if (0 < l)
{
return l;
}
delete this;
return 0;
}
public: // IBootstrapperApplication
virtual STDMETHODIMP OnStartup()
{
return S_OK;
}
virtual STDMETHODIMP OnShutdown(
__inout BOOTSTRAPPER_SHUTDOWN_ACTION* /*pAction*/
)
{
return S_OK;
}
virtual STDMETHODIMP OnSystemShutdown(
__in DWORD /*dwEndSession*/,
__inout BOOL* /*pfCancel*/
)
{
return S_OK;
}
virtual STDMETHODIMP OnDetectBegin(
__in BOOL /*fInstalled*/,
__in DWORD /*cPackages*/,
__inout BOOL* /*pfCancel*/
)
{
return S_OK;
}
virtual STDMETHODIMP OnDetectForwardCompatibleBundle(
__in_z LPCWSTR /*wzBundleId*/,
__in BOOTSTRAPPER_RELATION_TYPE /*relationType*/,
__in_z LPCWSTR /*wzBundleTag*/,
__in BOOL /*fPerMachine*/,
__in DWORD64 /*dw64Version*/,
__inout BOOL* /*pfCancel*/,
__inout BOOL* /*pfIgnoreBundle*/
)
{
return S_OK;
}
virtual STDMETHODIMP OnDetectUpdateBegin(
__in_z LPCWSTR /*wzUpdateLocation*/,
__inout BOOL* /*pfCancel*/,
__inout BOOL* /*pfSkip*/
)
{
return S_OK;
}
virtual STDMETHODIMP OnDetectUpdate(
__in_z LPCWSTR /*wzUpdateLocation*/,
__in DWORD64 /*dw64Size*/,
__in DWORD64 /*dw64Version*/,
__in_z LPCWSTR /*wzTitle*/,
__in_z LPCWSTR /*wzSummary*/,
__in_z LPCWSTR /*wzContentType*/,
__in_z LPCWSTR /*wzContent*/,
__inout BOOL* /*pfCancel*/,
__inout BOOL* /*pfStopProcessingUpdates*/
)
{
return S_OK;
}
virtual STDMETHODIMP OnDetectUpdateComplete(
__in HRESULT /*hrStatus*/,
__inout BOOL* /*pfIgnoreError*/
)
{
return S_OK;
}
virtual STDMETHODIMP OnDetectRelatedBundle(
__in_z LPCWSTR /*wzBundleId*/,
__in BOOTSTRAPPER_RELATION_TYPE /*relationType*/,
__in_z LPCWSTR /*wzBundleTag*/,
__in BOOL /*fPerMachine*/,
__in DWORD64 /*dw64Version*/,
__in BOOTSTRAPPER_RELATED_OPERATION /*operation*/,
__inout BOOL* /*pfCancel*/
)
{
return S_OK;
}
virtual STDMETHODIMP OnDetectPackageBegin(
__in_z LPCWSTR /*wzPackageId*/,
__inout BOOL* /*pfCancel*/
)
{
return S_OK;
}
virtual STDMETHODIMP OnDetectCompatibleMsiPackage(
__in_z LPCWSTR /*wzPackageId*/,
__in_z LPCWSTR /*wzCompatiblePackageId*/,
__in DWORD64 /*dw64CompatiblePackageVersion*/,
__inout BOOL* /*pfCancel*/
)
{
return S_OK;
}
virtual STDMETHODIMP OnDetectRelatedMsiPackage(
__in_z LPCWSTR /*wzPackageId*/,
__in_z LPCWSTR /*wzUpgradeCode*/,
__in_z LPCWSTR /*wzProductCode*/,
__in BOOL /*fPerMachine*/,
__in DWORD64 /*dw64Version*/,
__in BOOTSTRAPPER_RELATED_OPERATION /*operation*/,
__inout BOOL* /*pfCancel*/
)
{
return S_OK;
}
virtual STDMETHODIMP OnDetectTargetMsiPackage(
__in_z LPCWSTR /*wzPackageId*/,
__in_z LPCWSTR /*wzProductCode*/,
__in BOOTSTRAPPER_PACKAGE_STATE /*patchState*/,
__inout BOOL* /*pfCancel*/
)
{
return S_OK;
}
virtual STDMETHODIMP OnDetectMsiFeature(
__in_z LPCWSTR /*wzPackageId*/,
__in_z LPCWSTR /*wzFeatureId*/,
__in BOOTSTRAPPER_FEATURE_STATE /*state*/,
__inout BOOL* /*pfCancel*/
)
{
return S_OK;
}
virtual STDMETHODIMP OnDetectPackageComplete(
__in_z LPCWSTR /*wzPackageId*/,
__in HRESULT /*hrStatus*/,
__in BOOTSTRAPPER_PACKAGE_STATE /*state*/
)
{
return S_OK;
}
virtual STDMETHODIMP OnDetectComplete(
__in HRESULT /*hrStatus*/
)
{
return S_OK;
}
virtual STDMETHODIMP OnPlanBegin(
__in DWORD /*cPackages*/,
__inout BOOL* /*pfCancel*/
)
{
return S_OK;
}
virtual STDMETHODIMP OnPlanRelatedBundle(
__in_z LPCWSTR /*wzBundleId*/,
__in BOOTSTRAPPER_REQUEST_STATE /*recommendedState*/,
__inout BOOTSTRAPPER_REQUEST_STATE* /*pRequestedState*/,
__inout BOOL* /*pfCancel*/
)
{
return S_OK;
}
virtual STDMETHODIMP OnPlanPackageBegin(
__in_z LPCWSTR /*wzPackageId*/,
__in BOOTSTRAPPER_REQUEST_STATE /*recommendedState*/,
__inout BOOTSTRAPPER_REQUEST_STATE* /*pRequestState*/,
__inout BOOL* /*pfCancel*/
)
{
return S_OK;
}
virtual STDMETHODIMP OnPlanCompatibleMsiPackageBegin(
__in_z LPCWSTR /*wzPackageId*/,
__in_z LPCWSTR /*wzCompatiblePackageId*/,
__in DWORD64 /*dw64CompatiblePackageVersion*/,
__in BOOTSTRAPPER_REQUEST_STATE /*recommendedState*/,
__inout BOOTSTRAPPER_REQUEST_STATE* /*pRequestedState*/,
__inout BOOL* /*pfCancel*/
)
{
return S_OK;
}
virtual STDMETHODIMP OnPlanCompatibleMsiPackageComplete(
__in_z LPCWSTR /*wzPackageId*/,
__in_z LPCWSTR /*wzCompatiblePackageId*/,
__in HRESULT /*hrStatus*/,
__in BOOTSTRAPPER_PACKAGE_STATE /*state*/,
__in BOOTSTRAPPER_REQUEST_STATE /*requested*/,
__in BOOTSTRAPPER_ACTION_STATE /*execute*/,
__in BOOTSTRAPPER_ACTION_STATE /*rollback*/
)
{
return S_OK;
}
virtual STDMETHODIMP OnPlanTargetMsiPackage(
__in_z LPCWSTR /*wzPackageId*/,
__in_z LPCWSTR /*wzProductCode*/,
__in BOOTSTRAPPER_REQUEST_STATE /*recommendedState*/,
__inout BOOTSTRAPPER_REQUEST_STATE* /*pRequestedState*/,
__inout BOOL* /*pfCancel*/
)
{
return S_OK;
}
virtual STDMETHODIMP OnPlanMsiFeature(
__in_z LPCWSTR /*wzPackageId*/,
__in_z LPCWSTR /*wzFeatureId*/,
__in BOOTSTRAPPER_FEATURE_STATE /*recommendedState*/,
__inout BOOTSTRAPPER_FEATURE_STATE* /*pRequestedState*/,
__inout BOOL* /*pfCancel*/
)
{
return S_OK;
}
virtual STDMETHODIMP OnPlanPackageComplete(
__in_z LPCWSTR /*wzPackageId*/,
__in HRESULT /*hrStatus*/,
__in BOOTSTRAPPER_PACKAGE_STATE /*state*/,
__in BOOTSTRAPPER_REQUEST_STATE /*requested*/,
__in BOOTSTRAPPER_ACTION_STATE /*execute*/,
__in BOOTSTRAPPER_ACTION_STATE /*rollback*/
)
{
return S_OK;
}
virtual STDMETHODIMP OnPlanComplete(
__in HRESULT /*hrStatus*/
)
{
return S_OK;
}
virtual STDMETHODIMP OnApplyBegin(
__in DWORD /*dwPhaseCount*/,
__inout BOOL* /*pfCancel*/
)
{
return S_OK;
}
virtual STDMETHODIMP OnElevateBegin(
__inout BOOL* /*pfCancel*/
)
{
return S_OK;
}
virtual STDMETHODIMP OnElevateComplete(
__in HRESULT /*hrStatus*/
)
{
return S_OK;
}
virtual STDMETHODIMP OnProgress(
__in DWORD /*dwProgressPercentage*/,
__in DWORD /*dwOverallProgressPercentage*/,
__inout BOOL* /*pfCancel*/
)
{
return IDNOACTION;
}
virtual STDMETHODIMP OnError(
__in BOOTSTRAPPER_ERROR_TYPE /*errorType*/,
__in_z LPCWSTR /*wzPackageId*/,
__in DWORD /*dwCode*/,
__in_z LPCWSTR /*wzError*/,
__in DWORD /*dwUIHint*/,
__in DWORD /*cData*/,
__in_ecount_z_opt(cData) LPCWSTR* /*rgwzData*/,
__in int /*nRecommendation*/,
__inout int* /*pResult*/
)
{
return S_OK;
}
virtual STDMETHODIMP OnRegisterBegin(
__inout BOOL* /*pfCancel*/
)
{
return S_OK;
}
virtual STDMETHODIMP OnRegisterComplete(
__in HRESULT /*hrStatus*/
)
{
return S_OK;
}
virtual STDMETHODIMP OnCacheBegin(
__inout BOOL* /*pfCancel*/
)
{
return S_OK;
}
virtual STDMETHODIMP OnCachePackageBegin(
__in_z LPCWSTR /*wzPackageId*/,
__in DWORD /*cCachePayloads*/,
__in DWORD64 /*dw64PackageCacheSize*/,
__inout BOOL* /*pfCancel*/
)
{
return S_OK;
}
virtual STDMETHODIMP OnCacheAcquireBegin(
__in_z LPCWSTR /*wzPackageOrContainerId*/,
__in_z_opt LPCWSTR /*wzPayloadId*/,
__in BOOTSTRAPPER_CACHE_OPERATION /*operation*/,
__in_z LPCWSTR /*wzSource*/,
__inout BOOL* /*pfCancel*/
)
{
return S_OK;
}
virtual STDMETHODIMP OnCacheAcquireProgress(
__in_z LPCWSTR /*wzPackageOrContainerId*/,
__in_z_opt LPCWSTR /*wzPayloadId*/,
__in DWORD64 /*dw64Progress*/,
__in DWORD64 /*dw64Total*/,
__in DWORD /*dwOverallPercentage*/,
__inout BOOL* /*pfCancel*/
)
{
return S_OK;
}
virtual STDMETHODIMP OnResolveSource(
__in_z LPCWSTR /*wzPackageOrContainerId*/,
__in_z_opt LPCWSTR /*wzPayloadId*/,
__in_z LPCWSTR /*wzLocalSource*/,
__in_z_opt LPCWSTR /*wzDownloadSource*/,
__in BOOTSTRAPPER_RESOLVESOURCE_ACTION /*recommendation*/,
__inout BOOTSTRAPPER_RESOLVESOURCE_ACTION* /*pAction*/,
__inout BOOL* /*pfCancel*/
)
{
return S_OK;
}
virtual STDMETHODIMP OnCacheAcquireComplete(
__in_z LPCWSTR /*wzPackageOrContainerId*/,
__in_z_opt LPCWSTR /*wzPayloadId*/,
__in HRESULT /*hrStatus*/,
__in BOOTSTRAPPER_CACHEACQUIRECOMPLETE_ACTION /*recommendation*/,
__inout BOOTSTRAPPER_CACHEACQUIRECOMPLETE_ACTION* /*pAction*/
)
{
return S_OK;
}
virtual STDMETHODIMP OnCacheVerifyBegin(
__in_z LPCWSTR /*wzPackageId*/,
__in_z LPCWSTR /*wzPayloadId*/,
__inout BOOL* /*pfCancel*/
)
{
return S_OK;
}
virtual STDMETHODIMP OnCacheVerifyComplete(
__in_z LPCWSTR /*wzPackageId*/,
__in_z LPCWSTR /*wzPayloadId*/,
__in HRESULT /*hrStatus*/,
__in BOOTSTRAPPER_CACHEVERIFYCOMPLETE_ACTION /*recommendation*/,
__inout BOOTSTRAPPER_CACHEVERIFYCOMPLETE_ACTION* /*pAction*/
)
{
return S_OK;
}
virtual STDMETHODIMP OnCachePackageComplete(
__in_z LPCWSTR /*wzPackageId*/,
__in HRESULT /*hrStatus*/,
__in BOOTSTRAPPER_CACHEPACKAGECOMPLETE_ACTION /*recommendation*/,
__inout BOOTSTRAPPER_CACHEPACKAGECOMPLETE_ACTION* /*pAction*/
)
{
return S_OK;
}
virtual STDMETHODIMP OnCacheComplete(
__in HRESULT /*hrStatus*/
)
{
return S_OK;
}
virtual STDMETHODIMP OnExecuteBegin(
__in DWORD /*cExecutingPackages*/,
__inout BOOL* /*pfCancel*/
)
{
return S_OK;
}
virtual STDMETHODIMP OnExecutePackageBegin(
__in_z LPCWSTR /*wzPackageId*/,
__in BOOL /*fExecute*/,
__inout BOOL* /*pfCancel*/
)
{
return S_OK;
}
virtual STDMETHODIMP OnExecutePatchTarget(
__in_z LPCWSTR /*wzPackageId*/,
__in_z LPCWSTR /*wzTargetProductCode*/,
__inout BOOL* /*pfCancel*/
)
{
return S_OK;
}
virtual STDMETHODIMP OnExecuteProgress(
__in_z LPCWSTR /*wzPackageId*/,
__in DWORD /*dwProgressPercentage*/,
__in DWORD /*dwOverallProgressPercentage*/,
__inout BOOL* /*pfCancel*/
)
{
return S_OK;
}
virtual STDMETHODIMP OnExecuteMsiMessage(
__in_z LPCWSTR /*wzPackageId*/,
__in INSTALLMESSAGE /*messageType*/,
__in DWORD /*dwUIHint*/,
__in_z LPCWSTR /*wzMessage*/,
__in DWORD /*cData*/,
__in_ecount_z_opt(cData) LPCWSTR* /*rgwzData*/,
__in int /*nRecommendation*/,
__inout int* /*pResult*/
)
{
return S_OK;
}
virtual STDMETHODIMP OnExecuteFilesInUse(
__in_z LPCWSTR /*wzPackageId*/,
__in DWORD /*cFiles*/,
__in_ecount_z(cFiles) LPCWSTR* /*rgwzFiles*/,
__in int /*nRecommendation*/,
__inout int* /*pResult*/
)
{
return S_OK;
}
virtual STDMETHODIMP OnExecutePackageComplete(
__in_z LPCWSTR /*wzPackageId*/,
__in HRESULT /*hrStatus*/,
__in BOOTSTRAPPER_APPLY_RESTART /*restart*/,
__in BOOTSTRAPPER_EXECUTEPACKAGECOMPLETE_ACTION /*recommendation*/,
__inout BOOTSTRAPPER_EXECUTEPACKAGECOMPLETE_ACTION* /*pAction*/
)
{
return S_OK;
}
virtual STDMETHODIMP OnExecuteComplete(
__in HRESULT /*hrStatus*/
)
{
return S_OK;
}
virtual STDMETHODIMP OnUnregisterBegin(
__inout BOOL* /*pfCancel*/
)
{
return S_OK;
}
virtual STDMETHODIMP OnUnregisterComplete(
__in HRESULT /*hrStatus*/
)
{
return S_OK;
}
virtual STDMETHODIMP OnApplyComplete(
__in HRESULT /*hrStatus*/,
__in BOOTSTRAPPER_APPLY_RESTART /*restart*/,
__in BOOTSTRAPPER_APPLYCOMPLETE_ACTION /*recommendation*/,
__inout BOOTSTRAPPER_APPLYCOMPLETE_ACTION* /*pAction*/
)
{
return S_OK;
}
virtual STDMETHODIMP OnLaunchApprovedExeBegin(
__inout BOOL* /*pfCancel*/
)
{
return S_OK;
}
virtual STDMETHODIMP OnLaunchApprovedExeComplete(
__in HRESULT /*hrStatus*/,
__in DWORD /*dwProcessId*/
)
{
return S_OK;
}
virtual STDMETHODIMP_(HRESULT) BAProc(
__in BOOTSTRAPPER_APPLICATION_MESSAGE /*message*/,
__in const LPVOID /*pvArgs*/,
__inout LPVOID /*pvResults*/,
__in_opt LPVOID /*pvContext*/
)
{
return E_NOTIMPL;
}
virtual STDMETHODIMP_(void) BAProcFallback(
__in BOOTSTRAPPER_APPLICATION_MESSAGE /*message*/,
__in const LPVOID /*pvArgs*/,
__inout LPVOID /*pvResults*/,
__inout HRESULT* /*phr*/,
__in_opt LPVOID /*pvContext*/
)
{
}
public: // IBAFunctions
virtual STDMETHODIMP OnPlan(
)
{
return S_OK;
}
virtual STDMETHODIMP OnThemeLoaded(
THEME* pTheme,
WIX_LOCALIZATION* pWixLoc
)
{
HRESULT hr = S_OK;
m_pTheme = pTheme;
m_pWixLoc = pWixLoc;
return hr;
}
virtual STDMETHODIMP WndProc(
__in THEME* pTheme,
__in HWND hWnd,
__in UINT uMsg,
__in WPARAM wParam,
__in LPARAM lParam,
__inout LRESULT* plRes
)
{
HRESULT hr = S_OK;
*plRes = ThemeDefWindowProc(pTheme, hWnd, uMsg, wParam, lParam);
return hr;
}
virtual STDMETHODIMP BAFunctionsProc(
__in BA_FUNCTIONS_MESSAGE /*message*/,
__in const LPVOID /*pvArgs*/,
__inout LPVOID /*pvResults*/,
__in_opt LPVOID /*pvContext*/
)
{
return E_NOTIMPL;
}
protected:
CBalBaseBAFunctions(
__in HMODULE hModule,
__in IBootstrapperEngine* pEngine,
__in const BA_FUNCTIONS_CREATE_ARGS* pArgs
)
{
m_cReferences = 1;
m_hModule = hModule;
pEngine->AddRef();
m_pEngine = pEngine;
memcpy_s(&m_command, sizeof(m_command), pArgs->pBootstrapperCreateArgs->pCommand, sizeof(BOOTSTRAPPER_COMMAND));
memcpy_s(&m_baCreateArgs, sizeof(m_baCreateArgs), pArgs->pBootstrapperCreateArgs, sizeof(BOOTSTRAPPER_CREATE_ARGS));
memcpy_s(&m_bafCreateArgs, sizeof(m_bafCreateArgs), pArgs, sizeof(BA_FUNCTIONS_CREATE_ARGS));
m_baCreateArgs.pCommand = &m_command;
m_bafCreateArgs.pBootstrapperCreateArgs = &m_baCreateArgs;
}
virtual ~CBalBaseBAFunctions()
{
ReleaseNullObject(m_pEngine);
}
private:
long m_cReferences;
protected:
IBootstrapperEngine* m_pEngine;
HMODULE m_hModule;
BA_FUNCTIONS_CREATE_ARGS m_bafCreateArgs;
BOOTSTRAPPER_CREATE_ARGS m_baCreateArgs;
BOOTSTRAPPER_COMMAND m_command;
THEME* m_pTheme;
WIX_LOCALIZATION* m_pWixLoc;
};

Просмотреть файл

@ -0,0 +1,114 @@
#pragma once
// Copyright (c) .NET Foundation and contributors. All rights reserved. Licensed under the Microsoft Reciprocal License. See LICENSE.TXT file in the project root for full license information.
#include "BalBaseBootstrapperApplicationProc.h"
#include "BAFunctions.h"
#include "IBAFunctions.h"
static HRESULT BalBaseBAFunctionsProcOnThemeLoaded(
__in IBAFunctions* pBAFunctions,
__in BA_FUNCTIONS_ONTHEMELOADED_ARGS* pArgs,
__inout BA_FUNCTIONS_ONTHEMELOADED_RESULTS* /*pResults*/
)
{
return pBAFunctions->OnThemeLoaded(pArgs->pTheme, pArgs->pWixLoc);
}
static HRESULT BalBaseBAFunctionsProcWndProc(
__in IBAFunctions* pBAFunctions,
__in BA_FUNCTIONS_WNDPROC_ARGS* pArgs,
__inout BA_FUNCTIONS_WNDPROC_RESULTS* pResults
)
{
return pBAFunctions->WndProc(pArgs->pTheme, pArgs->hWnd, pArgs->uMsg, pArgs->wParam, pArgs->lParam, &pResults->lres);
}
/*******************************************************************
BalBaseBAFunctionsProc - requires pvContext to be of type IBAFunctions.
Provides a default mapping between the message based BAFunctions interface and
the COM-based BAFunctions interface.
*******************************************************************/
static HRESULT WINAPI BalBaseBAFunctionsProc(
__in BA_FUNCTIONS_MESSAGE message,
__in const LPVOID pvArgs,
__inout LPVOID pvResults,
__in_opt LPVOID pvContext
)
{
IBAFunctions* pBAFunctions = reinterpret_cast<IBAFunctions*>(pvContext);
HRESULT hr = pBAFunctions->BAFunctionsProc(message, pvArgs, pvResults, pvContext);
if (E_NOTIMPL == hr)
{
switch (message)
{
case BA_FUNCTIONS_MESSAGE_ONDETECTBEGIN:
case BA_FUNCTIONS_MESSAGE_ONDETECTCOMPLETE:
case BA_FUNCTIONS_MESSAGE_ONPLANBEGIN:
case BA_FUNCTIONS_MESSAGE_ONPLANCOMPLETE:
case BA_FUNCTIONS_MESSAGE_ONSTARTUP:
case BA_FUNCTIONS_MESSAGE_ONSHUTDOWN:
case BA_FUNCTIONS_MESSAGE_ONSYSTEMSHUTDOWN:
case BA_FUNCTIONS_MESSAGE_ONDETECTFORWARDCOMPATIBLEBUNDLE:
case BA_FUNCTIONS_MESSAGE_ONDETECTUPDATEBEGIN:
case BA_FUNCTIONS_MESSAGE_ONDETECTUPDATE:
case BA_FUNCTIONS_MESSAGE_ONDETECTUPDATECOMPLETE:
case BA_FUNCTIONS_MESSAGE_ONDETECTRELATEDBUNDLE:
case BA_FUNCTIONS_MESSAGE_ONDETECTPACKAGEBEGIN:
case BA_FUNCTIONS_MESSAGE_ONDETECTCOMPATIBLEMSIPACKAGE:
case BA_FUNCTIONS_MESSAGE_ONDETECTRELATEDMSIPACKAGE:
case BA_FUNCTIONS_MESSAGE_ONDETECTTARGETMSIPACKAGE:
case BA_FUNCTIONS_MESSAGE_ONDETECTMSIFEATURE:
case BA_FUNCTIONS_MESSAGE_ONDETECTPACKAGECOMPLETE:
case BA_FUNCTIONS_MESSAGE_ONPLANRELATEDBUNDLE:
case BA_FUNCTIONS_MESSAGE_ONPLANPACKAGEBEGIN:
case BA_FUNCTIONS_MESSAGE_ONPLANCOMPATIBLEMSIPACKAGEBEGIN:
case BA_FUNCTIONS_MESSAGE_ONPLANCOMPATIBLEMSIPACKAGECOMPLETE:
case BA_FUNCTIONS_MESSAGE_ONPLANTARGETMSIPACKAGE:
case BA_FUNCTIONS_MESSAGE_ONPLANMSIFEATURE:
case BA_FUNCTIONS_MESSAGE_ONPLANPACKAGECOMPLETE:
case BA_FUNCTIONS_MESSAGE_ONAPPLYBEGIN:
case BA_FUNCTIONS_MESSAGE_ONELEVATEBEGIN:
case BA_FUNCTIONS_MESSAGE_ONELEVATECOMPLETE:
case BA_FUNCTIONS_MESSAGE_ONPROGRESS:
case BA_FUNCTIONS_MESSAGE_ONERROR:
case BA_FUNCTIONS_MESSAGE_ONREGISTERBEGIN:
case BA_FUNCTIONS_MESSAGE_ONREGISTERCOMPLETE:
case BA_FUNCTIONS_MESSAGE_ONCACHEBEGIN:
case BA_FUNCTIONS_MESSAGE_ONCACHEPACKAGEBEGIN:
case BA_FUNCTIONS_MESSAGE_ONCACHEACQUIREBEGIN:
case BA_FUNCTIONS_MESSAGE_ONCACHEACQUIREPROGRESS:
case BA_FUNCTIONS_MESSAGE_ONRESOLVESOURCE:
case BA_FUNCTIONS_MESSAGE_ONCACHEACQUIRECOMPLETE:
case BA_FUNCTIONS_MESSAGE_ONCACHEVERIFYBEGIN:
case BA_FUNCTIONS_MESSAGE_ONCACHEVERIFYCOMPLETE:
case BA_FUNCTIONS_MESSAGE_ONCACHEPACKAGECOMPLETE:
case BA_FUNCTIONS_MESSAGE_ONCACHECOMPLETE:
case BA_FUNCTIONS_MESSAGE_ONEXECUTEBEGIN:
case BA_FUNCTIONS_MESSAGE_ONEXECUTEPACKAGEBEGIN:
case BA_FUNCTIONS_MESSAGE_ONEXECUTEPATCHTARGET:
case BA_FUNCTIONS_MESSAGE_ONEXECUTEPROGRESS:
case BA_FUNCTIONS_MESSAGE_ONEXECUTEMSIMESSAGE:
case BA_FUNCTIONS_MESSAGE_ONEXECUTEFILESINUSE:
case BA_FUNCTIONS_MESSAGE_ONEXECUTEPACKAGECOMPLETE:
case BA_FUNCTIONS_MESSAGE_ONEXECUTECOMPLETE:
case BA_FUNCTIONS_MESSAGE_ONUNREGISTERBEGIN:
case BA_FUNCTIONS_MESSAGE_ONUNREGISTERCOMPLETE:
case BA_FUNCTIONS_MESSAGE_ONAPPLYCOMPLETE:
case BA_FUNCTIONS_MESSAGE_ONLAUNCHAPPROVEDEXEBEGIN:
case BA_FUNCTIONS_MESSAGE_ONLAUNCHAPPROVEDEXECOMPLETE:
hr = BalBaseBootstrapperApplicationProc((BOOTSTRAPPER_APPLICATION_MESSAGE)message, pvArgs, pvResults, pvContext);
break;
case BA_FUNCTIONS_MESSAGE_ONTHEMELOADED:
hr = BalBaseBAFunctionsProcOnThemeLoaded(pBAFunctions, reinterpret_cast<BA_FUNCTIONS_ONTHEMELOADED_ARGS*>(pvArgs), reinterpret_cast<BA_FUNCTIONS_ONTHEMELOADED_RESULTS*>(pvResults));
break;
case BA_FUNCTIONS_MESSAGE_WNDPROC:
hr = BalBaseBAFunctionsProcWndProc(pBAFunctions, reinterpret_cast<BA_FUNCTIONS_WNDPROC_ARGS*>(pvArgs), reinterpret_cast<BA_FUNCTIONS_WNDPROC_RESULTS*>(pvResults));
break;
}
}
return hr;
}

Просмотреть файл

@ -0,0 +1,900 @@
// Copyright (c) .NET Foundation and contributors. All rights reserved. Licensed under the Microsoft Reciprocal License. See LICENSE.TXT file in the project root for full license information.
#include <windows.h>
#include <msiquery.h>
#include "BootstrapperEngine.h"
#include "BootstrapperApplication.h"
#include "IBootstrapperEngine.h"
#include "IBootstrapperApplication.h"
#include "balutil.h"
#include "balretry.h"
class CBalBaseBootstrapperApplication : public IBootstrapperApplication
{
public: // IUnknown
virtual STDMETHODIMP QueryInterface(
__in REFIID riid,
__out LPVOID *ppvObject
)
{
if (!ppvObject)
{
return E_INVALIDARG;
}
*ppvObject = NULL;
if (::IsEqualIID(__uuidof(IBootstrapperApplication), riid))
{
*ppvObject = static_cast<IBootstrapperApplication*>(this);
}
else if (::IsEqualIID(IID_IUnknown, riid))
{
*ppvObject = static_cast<IUnknown*>(this);
}
else // no interface for requested iid
{
return E_NOINTERFACE;
}
AddRef();
return S_OK;
}
virtual STDMETHODIMP_(ULONG) AddRef()
{
return ::InterlockedIncrement(&this->m_cReferences);
}
virtual STDMETHODIMP_(ULONG) Release()
{
long l = ::InterlockedDecrement(&this->m_cReferences);
if (0 < l)
{
return l;
}
delete this;
return 0;
}
public: // IBootstrapperApplication
virtual STDMETHODIMP OnStartup()
{
return S_OK;
}
virtual STDMETHODIMP OnShutdown(
__inout BOOTSTRAPPER_SHUTDOWN_ACTION* /*pAction*/
)
{
return S_OK;
}
virtual STDMETHODIMP OnSystemShutdown(
__in DWORD dwEndSession,
__inout BOOL* pfCancel
)
{
HRESULT hr = S_OK;
// Allow requests to shut down when critical or not applying.
*pfCancel = !(ENDSESSION_CRITICAL & dwEndSession || !m_fApplying);
return hr;
}
virtual STDMETHODIMP OnDetectBegin(
__in BOOL /*fInstalled*/,
__in DWORD /*cPackages*/,
__inout BOOL* pfCancel
)
{
*pfCancel |= CheckCanceled();
return S_OK;
}
virtual STDMETHODIMP OnDetectForwardCompatibleBundle(
__in_z LPCWSTR /*wzBundleId*/,
__in BOOTSTRAPPER_RELATION_TYPE /*relationType*/,
__in_z LPCWSTR /*wzBundleTag*/,
__in BOOL /*fPerMachine*/,
__in DWORD64 /*dw64Version*/,
__inout BOOL* pfCancel,
__inout BOOL* /*pfIgnoreBundle*/
)
{
*pfCancel |= CheckCanceled();
return S_OK;
}
virtual STDMETHODIMP OnDetectUpdateBegin(
__in_z LPCWSTR /*wzUpdateLocation*/,
__inout BOOL* pfCancel,
__inout BOOL* /*pfSkip*/
)
{
*pfCancel |= CheckCanceled();
return S_OK;
}
virtual STDMETHODIMP OnDetectUpdate(
__in_z LPCWSTR /*wzUpdateLocation*/,
__in DWORD64 /*dw64Size*/,
__in DWORD64 /*dw64Version*/,
__in_z LPCWSTR /*wzTitle*/,
__in_z LPCWSTR /*wzSummary*/,
__in_z LPCWSTR /*wzContentType*/,
__in_z LPCWSTR /*wzContent*/,
__inout BOOL* pfCancel,
__inout BOOL* /*pfStopProcessingUpdates*/
)
{
*pfCancel |= CheckCanceled();
return S_OK;
}
virtual STDMETHODIMP OnDetectUpdateComplete(
__in HRESULT /*hrStatus*/,
__inout BOOL* /*pfIgnoreError*/
)
{
return S_OK;
}
virtual STDMETHODIMP OnDetectRelatedBundle(
__in_z LPCWSTR /*wzBundleId*/,
__in BOOTSTRAPPER_RELATION_TYPE /*relationType*/,
__in_z LPCWSTR /*wzBundleTag*/,
__in BOOL /*fPerMachine*/,
__in DWORD64 /*dw64Version*/,
__in BOOTSTRAPPER_RELATED_OPERATION /*operation*/,
__inout BOOL* pfCancel
)
{
*pfCancel |= CheckCanceled();
return S_OK;
}
virtual STDMETHODIMP OnDetectPackageBegin(
__in_z LPCWSTR /*wzPackageId*/,
__inout BOOL* pfCancel
)
{
*pfCancel |= CheckCanceled();
return S_OK;
}
virtual STDMETHODIMP OnDetectCompatibleMsiPackage(
__in_z LPCWSTR /*wzPackageId*/,
__in_z LPCWSTR /*wzCompatiblePackageId*/,
__in DWORD64 /*dw64CompatiblePackageVersion*/,
__inout BOOL* pfCancel
)
{
*pfCancel |= CheckCanceled();
return S_OK;
}
virtual STDMETHODIMP OnDetectRelatedMsiPackage(
__in_z LPCWSTR /*wzPackageId*/,
__in_z LPCWSTR /*wzUpgradeCode*/,
__in_z LPCWSTR /*wzProductCode*/,
__in BOOL /*fPerMachine*/,
__in DWORD64 /*dw64Version*/,
__in BOOTSTRAPPER_RELATED_OPERATION /*operation*/,
__inout BOOL* pfCancel
)
{
*pfCancel |= CheckCanceled();
return S_OK;
}
virtual STDMETHODIMP OnDetectTargetMsiPackage(
__in_z LPCWSTR /*wzPackageId*/,
__in_z LPCWSTR /*wzProductCode*/,
__in BOOTSTRAPPER_PACKAGE_STATE /*patchState*/,
__inout BOOL* pfCancel
)
{
*pfCancel |= CheckCanceled();
return S_OK;
}
virtual STDMETHODIMP OnDetectMsiFeature(
__in_z LPCWSTR /*wzPackageId*/,
__in_z LPCWSTR /*wzFeatureId*/,
__in BOOTSTRAPPER_FEATURE_STATE /*state*/,
__inout BOOL* pfCancel
)
{
*pfCancel |= CheckCanceled();
return S_OK;
}
virtual STDMETHODIMP OnDetectPackageComplete(
__in_z LPCWSTR /*wzPackageId*/,
__in HRESULT /*hrStatus*/,
__in BOOTSTRAPPER_PACKAGE_STATE /*state*/
)
{
return S_OK;
}
virtual STDMETHODIMP OnDetectComplete(
__in HRESULT /*hrStatus*/
)
{
return S_OK;
}
virtual STDMETHODIMP OnPlanBegin(
__in DWORD /*cPackages*/,
__inout BOOL* pfCancel
)
{
*pfCancel |= CheckCanceled();
return S_OK;
}
virtual STDMETHODIMP OnPlanRelatedBundle(
__in_z LPCWSTR /*wzBundleId*/,
__in BOOTSTRAPPER_REQUEST_STATE /*recommendedState*/,
__inout BOOTSTRAPPER_REQUEST_STATE* /*pRequestedState*/,
__inout BOOL* pfCancel
)
{
*pfCancel |= CheckCanceled();
return S_OK;
}
virtual STDMETHODIMP OnPlanPackageBegin(
__in_z LPCWSTR /*wzPackageId*/,
__in BOOTSTRAPPER_REQUEST_STATE /*recommendedState*/,
__inout BOOTSTRAPPER_REQUEST_STATE* /*pRequestState*/,
__inout BOOL* pfCancel
)
{
*pfCancel |= CheckCanceled();
return S_OK;
}
virtual STDMETHODIMP OnPlanCompatibleMsiPackageBegin(
__in_z LPCWSTR /*wzPackageId*/,
__in_z LPCWSTR /*wzCompatiblePackageId*/,
__in DWORD64 /*dw64CompatiblePackageVersion*/,
__in BOOTSTRAPPER_REQUEST_STATE /*recommendedState*/,
__inout BOOTSTRAPPER_REQUEST_STATE* /*pRequestedState*/,
__inout BOOL* pfCancel
)
{
*pfCancel |= CheckCanceled();
return S_OK;
}
virtual STDMETHODIMP OnPlanCompatibleMsiPackageComplete(
__in_z LPCWSTR /*wzPackageId*/,
__in_z LPCWSTR /*wzCompatiblePackageId*/,
__in HRESULT /*hrStatus*/,
__in BOOTSTRAPPER_PACKAGE_STATE /*state*/,
__in BOOTSTRAPPER_REQUEST_STATE /*requested*/,
__in BOOTSTRAPPER_ACTION_STATE /*execute*/,
__in BOOTSTRAPPER_ACTION_STATE /*rollback*/
)
{
return S_OK;
}
virtual STDMETHODIMP OnPlanTargetMsiPackage(
__in_z LPCWSTR /*wzPackageId*/,
__in_z LPCWSTR /*wzProductCode*/,
__in BOOTSTRAPPER_REQUEST_STATE /*recommendedState*/,
__inout BOOTSTRAPPER_REQUEST_STATE* /*pRequestedState*/,
__inout BOOL* pfCancel
)
{
*pfCancel |= CheckCanceled();
return S_OK;
}
virtual STDMETHODIMP OnPlanMsiFeature(
__in_z LPCWSTR /*wzPackageId*/,
__in_z LPCWSTR /*wzFeatureId*/,
__in BOOTSTRAPPER_FEATURE_STATE /*recommendedState*/,
__inout BOOTSTRAPPER_FEATURE_STATE* /*pRequestedState*/,
__inout BOOL* pfCancel
)
{
*pfCancel |= CheckCanceled();
return S_OK;
}
virtual STDMETHODIMP OnPlanPackageComplete(
__in_z LPCWSTR /*wzPackageId*/,
__in HRESULT /*hrStatus*/,
__in BOOTSTRAPPER_PACKAGE_STATE /*state*/,
__in BOOTSTRAPPER_REQUEST_STATE /*requested*/,
__in BOOTSTRAPPER_ACTION_STATE /*execute*/,
__in BOOTSTRAPPER_ACTION_STATE /*rollback*/
)
{
return S_OK;
}
virtual STDMETHODIMP OnPlanComplete(
__in HRESULT /*hrStatus*/
)
{
return S_OK;
}
virtual STDMETHODIMP OnApplyBegin(
__in DWORD /*dwPhaseCount*/,
__inout BOOL* pfCancel
)
{
m_fApplying = TRUE;
m_dwProgressPercentage = 0;
m_dwOverallProgressPercentage = 0;
*pfCancel |= CheckCanceled();
return S_OK;
}
virtual STDMETHODIMP OnElevateBegin(
__inout BOOL* pfCancel
)
{
*pfCancel |= CheckCanceled();
return S_OK;
}
virtual STDMETHODIMP OnElevateComplete(
__in HRESULT /*hrStatus*/
)
{
return S_OK;
}
virtual STDMETHODIMP OnProgress(
__in DWORD dwProgressPercentage,
__in DWORD dwOverallProgressPercentage,
__inout BOOL* pfCancel
)
{
HRESULT hr = S_OK;
int nResult = IDNOACTION;
m_dwProgressPercentage = dwProgressPercentage;
m_dwOverallProgressPercentage = dwOverallProgressPercentage;
if (BOOTSTRAPPER_DISPLAY_EMBEDDED == m_display)
{
hr = m_pEngine->SendEmbeddedProgress(m_dwProgressPercentage, m_dwOverallProgressPercentage, &nResult);
BalExitOnFailure(hr, "Failed to send embedded overall progress.");
if (IDERROR == nResult)
{
hr = E_FAIL;
}
else if (IDCANCEL == nResult)
{
*pfCancel = TRUE;
}
}
LExit:
*pfCancel |= CheckCanceled();
return hr;
}
virtual STDMETHODIMP OnError(
__in BOOTSTRAPPER_ERROR_TYPE errorType,
__in_z LPCWSTR wzPackageId,
__in DWORD dwCode,
__in_z LPCWSTR /*wzError*/,
__in DWORD /*dwUIHint*/,
__in DWORD /*cData*/,
__in_ecount_z_opt(cData) LPCWSTR* /*rgwzData*/,
__in int /*nRecommendation*/,
__inout int* pResult
)
{
BalRetryErrorOccurred(wzPackageId, dwCode);
if (CheckCanceled())
{
*pResult = IDCANCEL;
}
else if (BOOTSTRAPPER_DISPLAY_FULL == m_display)
{
if (BOOTSTRAPPER_ERROR_TYPE_HTTP_AUTH_SERVER == errorType || BOOTSTRAPPER_ERROR_TYPE_HTTP_AUTH_PROXY == errorType)
{
*pResult = IDTRYAGAIN;
}
}
return S_OK;
}
virtual STDMETHODIMP OnRegisterBegin(
__inout BOOL* pfCancel
)
{
*pfCancel |= CheckCanceled();
return S_OK;
}
virtual STDMETHODIMP OnRegisterComplete(
__in HRESULT /*hrStatus*/
)
{
return S_OK;
}
virtual STDMETHODIMP OnCacheBegin(
__inout BOOL* pfCancel
)
{
*pfCancel |= CheckCanceled();
return S_OK;
}
virtual STDMETHODIMP OnCachePackageBegin(
__in_z LPCWSTR /*wzPackageId*/,
__in DWORD /*cCachePayloads*/,
__in DWORD64 /*dw64PackageCacheSize*/,
__inout BOOL* pfCancel
)
{
*pfCancel |= CheckCanceled();
return S_OK;
}
virtual STDMETHODIMP OnCacheAcquireBegin(
__in_z LPCWSTR wzPackageOrContainerId,
__in_z_opt LPCWSTR wzPayloadId,
__in BOOTSTRAPPER_CACHE_OPERATION /*operation*/,
__in_z LPCWSTR /*wzSource*/,
__inout BOOL* pfCancel
)
{
BalRetryStartPackage(BALRETRY_TYPE_CACHE, wzPackageOrContainerId, wzPayloadId);
*pfCancel |= CheckCanceled();
return S_OK;
}
virtual STDMETHODIMP OnCacheAcquireProgress(
__in_z LPCWSTR /*wzPackageOrContainerId*/,
__in_z_opt LPCWSTR /*wzPayloadId*/,
__in DWORD64 /*dw64Progress*/,
__in DWORD64 /*dw64Total*/,
__in DWORD /*dwOverallPercentage*/,
__inout BOOL* pfCancel
)
{
HRESULT hr = S_OK;
int nResult = IDNOACTION;
// Send progress even though we don't update the numbers to at least give the caller an opportunity
// to cancel.
if (BOOTSTRAPPER_DISPLAY_EMBEDDED == m_display)
{
hr = m_pEngine->SendEmbeddedProgress(m_dwProgressPercentage, m_dwOverallProgressPercentage, &nResult);
BalExitOnFailure(hr, "Failed to send embedded cache progress.");
if (IDERROR == nResult)
{
hr = E_FAIL;
}
else if (IDCANCEL == nResult)
{
*pfCancel = TRUE;
}
}
LExit:
*pfCancel |= CheckCanceled();
return hr;
}
virtual STDMETHODIMP OnResolveSource(
__in_z LPCWSTR /*wzPackageOrContainerId*/,
__in_z_opt LPCWSTR /*wzPayloadId*/,
__in_z LPCWSTR /*wzLocalSource*/,
__in_z_opt LPCWSTR /*wzDownloadSource*/,
__in BOOTSTRAPPER_RESOLVESOURCE_ACTION /*recommendation*/,
__inout BOOTSTRAPPER_RESOLVESOURCE_ACTION* /*pAction*/,
__inout BOOL* pfCancel
)
{
*pfCancel |= CheckCanceled();
return S_OK;
}
virtual STDMETHODIMP OnCacheAcquireComplete(
__in_z LPCWSTR wzPackageOrContainerId,
__in_z_opt LPCWSTR wzPayloadId,
__in HRESULT hrStatus,
__in BOOTSTRAPPER_CACHEACQUIRECOMPLETE_ACTION /*recommendation*/,
__inout BOOTSTRAPPER_CACHEACQUIRECOMPLETE_ACTION* pAction
)
{
HRESULT hr = S_OK;
BOOL fRetry = FALSE;
if (CheckCanceled())
{
ExitFunction1(hr = HRESULT_FROM_WIN32(ERROR_INSTALL_USEREXIT));
}
hr = BalRetryEndPackage(BALRETRY_TYPE_CACHE, wzPackageOrContainerId, wzPayloadId, hrStatus, &fRetry);
ExitOnFailure(hr, "BalRetryEndPackage for cache failed");
if (fRetry)
{
*pAction = BOOTSTRAPPER_CACHEACQUIRECOMPLETE_ACTION_RETRY;
}
LExit:
return hr;
}
virtual STDMETHODIMP OnCacheVerifyBegin(
__in_z LPCWSTR /*wzPackageId*/,
__in_z LPCWSTR /*wzPayloadId*/,
__inout BOOL* pfCancel
)
{
*pfCancel |= CheckCanceled();
return S_OK;
}
virtual STDMETHODIMP OnCacheVerifyComplete(
__in_z LPCWSTR /*wzPackageId*/,
__in_z LPCWSTR /*wzPayloadId*/,
__in HRESULT /*hrStatus*/,
__in BOOTSTRAPPER_CACHEVERIFYCOMPLETE_ACTION /*recommendation*/,
__inout BOOTSTRAPPER_CACHEVERIFYCOMPLETE_ACTION* pAction
)
{
if (CheckCanceled())
{
*pAction = BOOTSTRAPPER_CACHEVERIFYCOMPLETE_ACTION_NONE;
}
return S_OK;
}
virtual STDMETHODIMP OnCachePackageComplete(
__in_z LPCWSTR /*wzPackageId*/,
__in HRESULT /*hrStatus*/,
__in BOOTSTRAPPER_CACHEPACKAGECOMPLETE_ACTION /*recommendation*/,
__inout BOOTSTRAPPER_CACHEPACKAGECOMPLETE_ACTION* pAction
)
{
if (CheckCanceled())
{
*pAction = BOOTSTRAPPER_CACHEPACKAGECOMPLETE_ACTION_NONE;
}
return S_OK;
}
virtual STDMETHODIMP OnCacheComplete(
__in HRESULT /*hrStatus*/
)
{
return S_OK;
}
virtual STDMETHODIMP OnExecuteBegin(
__in DWORD /*cExecutingPackages*/,
__inout BOOL* pfCancel
)
{
*pfCancel |= CheckCanceled();
return S_OK;
}
virtual STDMETHODIMP OnExecutePackageBegin(
__in_z LPCWSTR wzPackageId,
__in BOOL fExecute,
__inout BOOL* pfCancel
)
{
// Only track retry on execution (not rollback).
if (fExecute)
{
BalRetryStartPackage(BALRETRY_TYPE_EXECUTE, wzPackageId, NULL);
}
m_fRollingBack = !fExecute;
*pfCancel |= CheckCanceled();
return S_OK;
}
virtual STDMETHODIMP OnExecutePatchTarget(
__in_z LPCWSTR /*wzPackageId*/,
__in_z LPCWSTR /*wzTargetProductCode*/,
__inout BOOL* pfCancel
)
{
*pfCancel |= CheckCanceled();
return S_OK;
}
virtual STDMETHODIMP OnExecuteProgress(
__in_z LPCWSTR /*wzPackageId*/,
__in DWORD /*dwProgressPercentage*/,
__in DWORD /*dwOverallProgressPercentage*/,
__inout BOOL* pfCancel
)
{
HRESULT hr = S_OK;
int nResult = IDNOACTION;
// Send progress even though we don't update the numbers to at least give the caller an opportunity
// to cancel.
if (BOOTSTRAPPER_DISPLAY_EMBEDDED == m_display)
{
hr = m_pEngine->SendEmbeddedProgress(m_dwProgressPercentage, m_dwOverallProgressPercentage, &nResult);
BalExitOnFailure(hr, "Failed to send embedded execute progress.");
if (IDERROR == nResult)
{
hr = E_FAIL;
}
else if (IDCANCEL == nResult)
{
*pfCancel = TRUE;
}
}
LExit:
*pfCancel |= CheckCanceled();
return hr;
}
virtual STDMETHODIMP OnExecuteMsiMessage(
__in_z LPCWSTR /*wzPackageId*/,
__in INSTALLMESSAGE /*messageType*/,
__in DWORD /*dwUIHint*/,
__in_z LPCWSTR /*wzMessage*/,
__in DWORD /*cData*/,
__in_ecount_z_opt(cData) LPCWSTR* /*rgwzData*/,
__in int /*nRecommendation*/,
__inout int* pResult
)
{
if (CheckCanceled())
{
*pResult = IDCANCEL;
}
return S_OK;
}
virtual STDMETHODIMP OnExecuteFilesInUse(
__in_z LPCWSTR /*wzPackageId*/,
__in DWORD /*cFiles*/,
__in_ecount_z(cFiles) LPCWSTR* /*rgwzFiles*/,
__in int /*nRecommendation*/,
__inout int* pResult
)
{
if (CheckCanceled())
{
*pResult = IDCANCEL;
}
return S_OK;
}
virtual STDMETHODIMP OnExecutePackageComplete(
__in_z LPCWSTR wzPackageId,
__in HRESULT hrStatus,
__in BOOTSTRAPPER_APPLY_RESTART /*restart*/,
__in BOOTSTRAPPER_EXECUTEPACKAGECOMPLETE_ACTION /*recommendation*/,
__inout BOOTSTRAPPER_EXECUTEPACKAGECOMPLETE_ACTION* pAction
)
{
HRESULT hr = S_OK;
BOOL fRetry = FALSE;
if (CheckCanceled())
{
ExitFunction1(hr = HRESULT_FROM_WIN32(ERROR_INSTALL_USEREXIT));
}
hr = BalRetryEndPackage(BALRETRY_TYPE_EXECUTE, wzPackageId, NULL, hrStatus, &fRetry);
ExitOnFailure(hr, "BalRetryEndPackage for execute failed");
if (fRetry)
{
*pAction = BOOTSTRAPPER_EXECUTEPACKAGECOMPLETE_ACTION_RETRY;
}
LExit:
return hr;
}
virtual STDMETHODIMP OnExecuteComplete(
__in HRESULT /*hrStatus*/
)
{
return S_OK;
}
virtual STDMETHODIMP OnUnregisterBegin(
__inout BOOL* pfCancel
)
{
*pfCancel |= CheckCanceled();
return S_OK;
}
virtual STDMETHODIMP OnUnregisterComplete(
__in HRESULT /*hrStatus*/
)
{
return S_OK;
}
virtual STDMETHODIMP OnApplyComplete(
__in HRESULT /*hrStatus*/,
__in BOOTSTRAPPER_APPLY_RESTART restart,
__in BOOTSTRAPPER_APPLYCOMPLETE_ACTION /*recommendation*/,
__inout BOOTSTRAPPER_APPLYCOMPLETE_ACTION* pAction
)
{
HRESULT hr = S_OK;
BOOL fRestartRequired = BOOTSTRAPPER_APPLY_RESTART_REQUIRED == restart;
BOOL fShouldBlockRestart = BOOTSTRAPPER_DISPLAY_FULL <= m_display && BOOTSTRAPPER_RESTART_PROMPT >= m_restart;
if (fRestartRequired && !fShouldBlockRestart)
{
*pAction = BOOTSTRAPPER_APPLYCOMPLETE_ACTION_RESTART;
}
m_fApplying = FALSE;
return hr;
}
virtual STDMETHODIMP OnLaunchApprovedExeBegin(
__inout BOOL* pfCancel
)
{
*pfCancel |= CheckCanceled();
return S_OK;
}
virtual STDMETHODIMP OnLaunchApprovedExeComplete(
__in HRESULT /*hrStatus*/,
__in DWORD /*dwProcessId*/
)
{
return S_OK;
}
virtual STDMETHODIMP_(HRESULT) BAProc(
__in BOOTSTRAPPER_APPLICATION_MESSAGE /*message*/,
__in const LPVOID /*pvArgs*/,
__inout LPVOID /*pvResults*/,
__in_opt LPVOID /*pvContext*/
)
{
return E_NOTIMPL;
}
virtual STDMETHODIMP_(void) BAProcFallback(
__in BOOTSTRAPPER_APPLICATION_MESSAGE /*message*/,
__in const LPVOID /*pvArgs*/,
__inout LPVOID /*pvResults*/,
__inout HRESULT* /*phr*/,
__in_opt LPVOID /*pvContext*/
)
{
}
protected:
//
// PromptCancel - prompts the user to close (if not forced).
//
virtual BOOL PromptCancel(
__in HWND hWnd,
__in BOOL fForceCancel,
__in_z_opt LPCWSTR wzMessage,
__in_z_opt LPCWSTR wzCaption
)
{
::EnterCriticalSection(&m_csCanceled);
// Only prompt the user to close if we have not canceled already.
if (!m_fCanceled)
{
if (fForceCancel)
{
m_fCanceled = TRUE;
}
else
{
m_fCanceled = (IDYES == ::MessageBoxW(hWnd, wzMessage, wzCaption, MB_YESNO | MB_ICONEXCLAMATION));
}
}
::LeaveCriticalSection(&m_csCanceled);
return m_fCanceled;
}
//
// CheckCanceled - waits if the cancel dialog is up and checks to see if the user canceled the operation.
//
BOOL CheckCanceled()
{
::EnterCriticalSection(&m_csCanceled);
::LeaveCriticalSection(&m_csCanceled);
return m_fRollingBack ? FALSE : m_fCanceled;
}
BOOL IsRollingBack()
{
return m_fRollingBack;
}
BOOL IsCanceled()
{
return m_fCanceled;
}
CBalBaseBootstrapperApplication(
__in IBootstrapperEngine* pEngine,
__in const BOOTSTRAPPER_CREATE_ARGS* pArgs,
__in DWORD dwRetryCount = 0,
__in DWORD dwRetryTimeout = 1000
)
{
m_cReferences = 1;
m_display = pArgs->pCommand->display;
m_restart = pArgs->pCommand->restart;
pEngine->AddRef();
m_pEngine = pEngine;
::InitializeCriticalSection(&m_csCanceled);
m_fCanceled = FALSE;
m_fApplying = FALSE;
m_fRollingBack = FALSE;
BalRetryInitialize(dwRetryCount, dwRetryTimeout);
}
virtual ~CBalBaseBootstrapperApplication()
{
BalRetryUninitialize();
::DeleteCriticalSection(&m_csCanceled);
ReleaseNullObject(m_pEngine);
}
protected:
CRITICAL_SECTION m_csCanceled;
BOOL m_fCanceled;
private:
long m_cReferences;
BOOTSTRAPPER_DISPLAY m_display;
BOOTSTRAPPER_RESTART m_restart;
IBootstrapperEngine* m_pEngine;
BOOL m_fApplying;
BOOL m_fRollingBack;
DWORD m_dwProgressPercentage;
DWORD m_dwOverallProgressPercentage;
};

Просмотреть файл

@ -0,0 +1,698 @@
#pragma once
// Copyright (c) .NET Foundation and contributors. All rights reserved. Licensed under the Microsoft Reciprocal License. See LICENSE.TXT file in the project root for full license information.
#include <windows.h>
#include "BootstrapperEngine.h"
#include "BootstrapperApplication.h"
#include "IBootstrapperEngine.h"
#include "IBootstrapperApplication.h"
static HRESULT BalBaseBAProcOnDetectBegin(
__in IBootstrapperApplication* pBA,
__in BA_ONDETECTBEGIN_ARGS* pArgs,
__inout BA_ONDETECTBEGIN_RESULTS* pResults
)
{
return pBA->OnDetectBegin(pArgs->fInstalled, pArgs->cPackages, &pResults->fCancel);
}
static HRESULT BalBaseBAProcOnDetectComplete(
__in IBootstrapperApplication* pBA,
__in BA_ONDETECTCOMPLETE_ARGS* pArgs,
__inout BA_ONDETECTCOMPLETE_RESULTS* /*pResults*/
)
{
return pBA->OnDetectComplete(pArgs->hrStatus);
}
static HRESULT BalBaseBAProcOnPlanBegin(
__in IBootstrapperApplication* pBA,
__in BA_ONPLANBEGIN_ARGS* pArgs,
__inout BA_ONPLANBEGIN_RESULTS* pResults
)
{
return pBA->OnPlanBegin(pArgs->cPackages, &pResults->fCancel);
}
static HRESULT BalBaseBAProcOnPlanComplete(
__in IBootstrapperApplication* pBA,
__in BA_ONPLANCOMPLETE_ARGS* pArgs,
__inout BA_ONPLANCOMPLETE_RESULTS* /*pResults*/
)
{
return pBA->OnPlanComplete(pArgs->hrStatus);
}
static HRESULT BalBaseBAProcOnStartup(
__in IBootstrapperApplication* pBA,
__in BA_ONSTARTUP_ARGS* /*pArgs*/,
__inout BA_ONSTARTUP_RESULTS* /*pResults*/
)
{
return pBA->OnStartup();
}
static HRESULT BalBaseBAProcOnShutdown(
__in IBootstrapperApplication* pBA,
__in BA_ONSHUTDOWN_ARGS* /*pArgs*/,
__inout BA_ONSHUTDOWN_RESULTS* pResults
)
{
return pBA->OnShutdown(&pResults->action);
}
static HRESULT BalBaseBAProcOnSystemShutdown(
__in IBootstrapperApplication* pBA,
__in BA_ONSYSTEMSHUTDOWN_ARGS* pArgs,
__inout BA_ONSYSTEMSHUTDOWN_RESULTS* pResults
)
{
return pBA->OnSystemShutdown(pArgs->dwEndSession, &pResults->fCancel);
}
static HRESULT BalBaseBAProcOnDetectForwardCompatibleBundle(
__in IBootstrapperApplication* pBA,
__in BA_ONDETECTFORWARDCOMPATIBLEBUNDLE_ARGS* pArgs,
__inout BA_ONDETECTFORWARDCOMPATIBLEBUNDLE_RESULTS* pResults
)
{
return pBA->OnDetectForwardCompatibleBundle(pArgs->wzBundleId, pArgs->relationType, pArgs->wzBundleTag, pArgs->fPerMachine, pArgs->dw64Version, &pResults->fCancel, &pResults->fIgnoreBundle);
}
static HRESULT BalBaseBAProcOnDetectUpdateBegin(
__in IBootstrapperApplication* pBA,
__in BA_ONDETECTUPDATEBEGIN_ARGS* pArgs,
__inout BA_ONDETECTUPDATEBEGIN_RESULTS* pResults
)
{
return pBA->OnDetectUpdateBegin(pArgs->wzUpdateLocation, &pResults->fCancel, &pResults->fSkip);
}
static HRESULT BalBaseBAProcOnDetectUpdate(
__in IBootstrapperApplication* pBA,
__in BA_ONDETECTUPDATE_ARGS* pArgs,
__inout BA_ONDETECTUPDATE_RESULTS* pResults
)
{
return pBA->OnDetectUpdate(pArgs->wzUpdateLocation, pArgs->dw64Size, pArgs->dw64Version, pArgs->wzTitle, pArgs->wzSummary, pArgs->wzContentType, pArgs->wzContent, &pResults->fCancel, &pResults->fStopProcessingUpdates);
}
static HRESULT BalBaseBAProcOnDetectUpdateComplete(
__in IBootstrapperApplication* pBA,
__in BA_ONDETECTUPDATECOMPLETE_ARGS* pArgs,
__inout BA_ONDETECTUPDATECOMPLETE_RESULTS* pResults
)
{
return pBA->OnDetectUpdateComplete(pArgs->hrStatus, &pResults->fIgnoreError);
}
static HRESULT BalBaseBAProcOnDetectRelatedBundle(
__in IBootstrapperApplication* pBA,
__in BA_ONDETECTRELATEDBUNDLE_ARGS* pArgs,
__inout BA_ONDETECTRELATEDBUNDLE_RESULTS* pResults
)
{
return pBA->OnDetectRelatedBundle(pArgs->wzBundleId, pArgs->relationType, pArgs->wzBundleTag, pArgs->fPerMachine, pArgs->dw64Version, pArgs->operation, &pResults->fCancel);
}
static HRESULT BalBaseBAProcOnDetectPackageBegin(
__in IBootstrapperApplication* pBA,
__in BA_ONDETECTPACKAGEBEGIN_ARGS* pArgs,
__inout BA_ONDETECTPACKAGEBEGIN_RESULTS* pResults
)
{
return pBA->OnDetectPackageBegin(pArgs->wzPackageId, &pResults->fCancel);
}
static HRESULT BalBaseBAProcOnDetectCompatiblePackage(
__in IBootstrapperApplication* pBA,
__in BA_ONDETECTCOMPATIBLEMSIPACKAGE_ARGS* pArgs,
__inout BA_ONDETECTCOMPATIBLEMSIPACKAGE_RESULTS* pResults
)
{
return pBA->OnDetectCompatibleMsiPackage(pArgs->wzPackageId, pArgs->wzCompatiblePackageId, pArgs->dw64CompatiblePackageVersion, &pResults->fCancel);
}
static HRESULT BalBaseBAProcOnDetectRelatedMsiPackage(
__in IBootstrapperApplication* pBA,
__in BA_ONDETECTRELATEDMSIPACKAGE_ARGS* pArgs,
__inout BA_ONDETECTRELATEDMSIPACKAGE_RESULTS* pResults
)
{
return pBA->OnDetectRelatedMsiPackage(pArgs->wzPackageId, pArgs->wzUpgradeCode, pArgs->wzProductCode, pArgs->fPerMachine, pArgs->dw64Version, pArgs->operation, &pResults->fCancel);
}
static HRESULT BalBaseBAProcOnDetectTargetMsiPackage(
__in IBootstrapperApplication* pBA,
__in BA_ONDETECTTARGETMSIPACKAGE_ARGS* pArgs,
__inout BA_ONDETECTTARGETMSIPACKAGE_RESULTS* pResults
)
{
return pBA->OnDetectTargetMsiPackage(pArgs->wzPackageId, pArgs->wzProductCode, pArgs->patchState, &pResults->fCancel);
}
static HRESULT BalBaseBAProcOnDetectMsiFeature(
__in IBootstrapperApplication* pBA,
__in BA_ONDETECTMSIFEATURE_ARGS* pArgs,
__inout BA_ONDETECTMSIFEATURE_RESULTS* pResults
)
{
return pBA->OnDetectMsiFeature(pArgs->wzPackageId, pArgs->wzFeatureId, pArgs->state, &pResults->fCancel);
}
static HRESULT BalBaseBAProcOnDetectPackageComplete(
__in IBootstrapperApplication* pBA,
__in BA_ONDETECTPACKAGECOMPLETE_ARGS* pArgs,
__inout BA_ONDETECTPACKAGECOMPLETE_RESULTS* /*pResults*/
)
{
return pBA->OnDetectPackageComplete(pArgs->wzPackageId, pArgs->hrStatus, pArgs->state);
}
static HRESULT BalBaseBAProcOnPlanRelatedBundle(
__in IBootstrapperApplication* pBA,
__in BA_ONPLANRELATEDBUNDLE_ARGS* pArgs,
__inout BA_ONPLANRELATEDBUNDLE_RESULTS* pResults
)
{
return pBA->OnPlanRelatedBundle(pArgs->wzBundleId, pArgs->recommendedState, &pResults->requestedState, &pResults->fCancel);
}
static HRESULT BalBaseBAProcOnPlanPackageBegin(
__in IBootstrapperApplication* pBA,
__in BA_ONPLANPACKAGEBEGIN_ARGS* pArgs,
__inout BA_ONPLANPACKAGEBEGIN_RESULTS* pResults
)
{
return pBA->OnPlanPackageBegin(pArgs->wzPackageId, pArgs->recommendedState, &pResults->requestedState, &pResults->fCancel);
}
static HRESULT BalBaseBAProcOnPlanCompatibleMsiPackageBegin(
__in IBootstrapperApplication* pBA,
__in BA_ONPLANCOMPATIBLEMSIPACKAGEBEGIN_ARGS* pArgs,
__inout BA_ONPLANCOMPATIBLEMSIPACKAGEBEGIN_RESULTS* pResults
)
{
return pBA->OnPlanCompatibleMsiPackageBegin(pArgs->wzPackageId, pArgs->wzCompatiblePackageId, pArgs->dw64CompatiblePackageVersion, pArgs->recommendedState, &pResults->requestedState, &pResults->fCancel);
}
static HRESULT BalBaseBAProcOnPlanCompatibleMsiPackageComplete(
__in IBootstrapperApplication* pBA,
__in BA_ONPLANCOMPATIBLEMSIPACKAGECOMPLETE_ARGS* pArgs,
__inout BA_ONPLANCOMPATIBLEMSIPACKAGECOMPLETE_RESULTS* /*pResults*/
)
{
return pBA->OnPlanCompatibleMsiPackageComplete(pArgs->wzPackageId, pArgs->wzCompatiblePackageId, pArgs->hrStatus, pArgs->state, pArgs->requested, pArgs->execute, pArgs->rollback);
}
static HRESULT BalBaseBAProcOnPlanTargetMsiPackage(
__in IBootstrapperApplication* pBA,
__in BA_ONPLANTARGETMSIPACKAGE_ARGS* pArgs,
__inout BA_ONPLANTARGETMSIPACKAGE_RESULTS* pResults
)
{
return pBA->OnPlanTargetMsiPackage(pArgs->wzPackageId, pArgs->wzProductCode, pArgs->recommendedState, &pResults->requestedState, &pResults->fCancel);
}
static HRESULT BalBaseBAProcOnPlanMsiFeature(
__in IBootstrapperApplication* pBA,
__in BA_ONPLANMSIFEATURE_ARGS* pArgs,
__inout BA_ONPLANMSIFEATURE_RESULTS* pResults
)
{
return pBA->OnPlanMsiFeature(pArgs->wzPackageId, pArgs->wzFeatureId, pArgs->recommendedState, &pResults->requestedState, &pResults->fCancel);
}
static HRESULT BalBaseBAProcOnPlanPackageComplete(
__in IBootstrapperApplication* pBA,
__in BA_ONPLANPACKAGECOMPLETE_ARGS* pArgs,
__inout BA_ONPLANPACKAGECOMPLETE_RESULTS* /*pResults*/
)
{
return pBA->OnPlanPackageComplete(pArgs->wzPackageId, pArgs->hrStatus, pArgs->state, pArgs->requested, pArgs->execute, pArgs->rollback);
}
static HRESULT BalBaseBAProcOnApplyBegin(
__in IBootstrapperApplication* pBA,
__in BA_ONAPPLYBEGIN_ARGS* pArgs,
__inout BA_ONAPPLYBEGIN_RESULTS* pResults
)
{
return pBA->OnApplyBegin(pArgs->dwPhaseCount, &pResults->fCancel);
}
static HRESULT BalBaseBAProcOnElevateBegin(
__in IBootstrapperApplication* pBA,
__in BA_ONELEVATEBEGIN_ARGS* /*pArgs*/,
__inout BA_ONELEVATEBEGIN_RESULTS* pResults
)
{
return pBA->OnElevateBegin(&pResults->fCancel);
}
static HRESULT BalBaseBAProcOnElevateComplete(
__in IBootstrapperApplication* pBA,
__in BA_ONELEVATECOMPLETE_ARGS* pArgs,
__inout BA_ONELEVATECOMPLETE_RESULTS* /*pResults*/
)
{
return pBA->OnElevateComplete(pArgs->hrStatus);
}
static HRESULT BalBaseBAProcOnProgress(
__in IBootstrapperApplication* pBA,
__in BA_ONPROGRESS_ARGS* pArgs,
__inout BA_ONPROGRESS_RESULTS* pResults
)
{
return pBA->OnProgress(pArgs->dwProgressPercentage, pArgs->dwOverallPercentage, &pResults->fCancel);
}
static HRESULT BalBaseBAProcOnError(
__in IBootstrapperApplication* pBA,
__in BA_ONERROR_ARGS* pArgs,
__inout BA_ONERROR_RESULTS* pResults
)
{
return pBA->OnError(pArgs->errorType, pArgs->wzPackageId, pArgs->dwCode, pArgs->wzError, pArgs->dwUIHint, pArgs->cData, pArgs->rgwzData, pArgs->nRecommendation, &pResults->nResult);
}
static HRESULT BalBaseBAProcOnRegisterBegin(
__in IBootstrapperApplication* pBA,
__in BA_ONREGISTERBEGIN_ARGS* /*pArgs*/,
__inout BA_ONREGISTERBEGIN_RESULTS* pResults
)
{
return pBA->OnRegisterBegin(&pResults->fCancel);
}
static HRESULT BalBaseBAProcOnRegisterComplete(
__in IBootstrapperApplication* pBA,
__in BA_ONREGISTERCOMPLETE_ARGS* pArgs,
__inout BA_ONREGISTERCOMPLETE_RESULTS* /*pResults*/
)
{
return pBA->OnRegisterComplete(pArgs->hrStatus);
}
static HRESULT BalBaseBAProcOnCacheBegin(
__in IBootstrapperApplication* pBA,
__in BA_ONCACHEBEGIN_ARGS* /*pArgs*/,
__inout BA_ONCACHEBEGIN_RESULTS* pResults
)
{
return pBA->OnCacheBegin(&pResults->fCancel);
}
static HRESULT BalBaseBAProcOnCachePackageBegin(
__in IBootstrapperApplication* pBA,
__in BA_ONCACHEPACKAGEBEGIN_ARGS* pArgs,
__inout BA_ONCACHEPACKAGEBEGIN_RESULTS* pResults
)
{
return pBA->OnCachePackageBegin(pArgs->wzPackageId, pArgs->cCachePayloads, pArgs->dw64PackageCacheSize, &pResults->fCancel);
}
static HRESULT BalBaseBAProcOnCacheAcquireBegin(
__in IBootstrapperApplication* pBA,
__in BA_ONCACHEACQUIREBEGIN_ARGS* pArgs,
__inout BA_ONCACHEACQUIREBEGIN_RESULTS* pResults
)
{
return pBA->OnCacheAcquireBegin(pArgs->wzPackageOrContainerId, pArgs->wzPayloadId, pArgs->operation, pArgs->wzSource, &pResults->fCancel);
}
static HRESULT BalBaseBAProcOnCacheAcquireProgress(
__in IBootstrapperApplication* pBA,
__in BA_ONCACHEACQUIREPROGRESS_ARGS* pArgs,
__inout BA_ONCACHEACQUIREPROGRESS_RESULTS* pResults
)
{
return pBA->OnCacheAcquireProgress(pArgs->wzPackageOrContainerId, pArgs->wzPayloadId, pArgs->dw64Progress, pArgs->dw64Total, pArgs->dwOverallPercentage, &pResults->fCancel);
}
static HRESULT BalBaseBAProcOnResolveSource(
__in IBootstrapperApplication* pBA,
__in BA_ONRESOLVESOURCE_ARGS* pArgs,
__inout BA_ONRESOLVESOURCE_RESULTS* pResults
)
{
return pBA->OnResolveSource(pArgs->wzPackageOrContainerId, pArgs->wzPayloadId, pArgs->wzLocalSource, pArgs->wzDownloadSource, pArgs->recommendation, &pResults->action, &pResults->fCancel);
}
static HRESULT BalBaseBAProcOnCacheAcquireComplete(
__in IBootstrapperApplication* pBA,
__in BA_ONCACHEACQUIRECOMPLETE_ARGS* pArgs,
__inout BA_ONCACHEACQUIRECOMPLETE_RESULTS* pResults
)
{
return pBA->OnCacheAcquireComplete(pArgs->wzPackageOrContainerId, pArgs->wzPayloadId, pArgs->hrStatus, pArgs->recommendation, &pResults->action);
}
static HRESULT BalBaseBAProcOnCacheVerifyBegin(
__in IBootstrapperApplication* pBA,
__in BA_ONCACHEVERIFYBEGIN_ARGS* pArgs,
__inout BA_ONCACHEVERIFYBEGIN_RESULTS* pResults
)
{
return pBA->OnCacheVerifyBegin(pArgs->wzPackageOrContainerId, pArgs->wzPayloadId, &pResults->fCancel);
}
static HRESULT BalBaseBAProcOnCacheVerifyComplete(
__in IBootstrapperApplication* pBA,
__in BA_ONCACHEVERIFYCOMPLETE_ARGS* pArgs,
__inout BA_ONCACHEVERIFYCOMPLETE_RESULTS* pResults
)
{
return pBA->OnCacheVerifyComplete(pArgs->wzPackageOrContainerId, pArgs->wzPayloadId, pArgs->hrStatus, pArgs->recommendation, &pResults->action);
}
static HRESULT BalBaseBAProcOnCachePackageComplete(
__in IBootstrapperApplication* pBA,
__in BA_ONCACHEPACKAGECOMPLETE_ARGS* pArgs,
__inout BA_ONCACHEPACKAGECOMPLETE_RESULTS* pResults
)
{
return pBA->OnCachePackageComplete(pArgs->wzPackageId, pArgs->hrStatus, pArgs->recommendation, &pResults->action);
}
static HRESULT BalBaseBAProcOnCacheComplete(
__in IBootstrapperApplication* pBA,
__in BA_ONCACHECOMPLETE_ARGS* pArgs,
__inout BA_ONCACHECOMPLETE_RESULTS* /*pResults*/
)
{
return pBA->OnCacheComplete(pArgs->hrStatus);
}
static HRESULT BalBaseBAProcOnExecuteBegin(
__in IBootstrapperApplication* pBA,
__in BA_ONEXECUTEBEGIN_ARGS* pArgs,
__inout BA_ONEXECUTEBEGIN_RESULTS* pResults
)
{
return pBA->OnExecuteBegin(pArgs->cExecutingPackages, &pResults->fCancel);
}
static HRESULT BalBaseBAProcOnExecutePackageBegin(
__in IBootstrapperApplication* pBA,
__in BA_ONEXECUTEPACKAGEBEGIN_ARGS* pArgs,
__inout BA_ONEXECUTEPACKAGEBEGIN_RESULTS* pResults
)
{
return pBA->OnExecutePackageBegin(pArgs->wzPackageId, pArgs->fExecute, &pResults->fCancel);
}
static HRESULT BalBaseBAProcOnExecutePatchTarget(
__in IBootstrapperApplication* pBA,
__in BA_ONEXECUTEPATCHTARGET_ARGS* pArgs,
__inout BA_ONEXECUTEPATCHTARGET_RESULTS* pResults
)
{
return pBA->OnExecutePatchTarget(pArgs->wzPackageId, pArgs->wzTargetProductCode, &pResults->fCancel);
}
static HRESULT BalBaseBAProcOnExecuteProgress(
__in IBootstrapperApplication* pBA,
__in BA_ONEXECUTEPROGRESS_ARGS* pArgs,
__inout BA_ONEXECUTEPROGRESS_RESULTS* pResults
)
{
return pBA->OnExecuteProgress(pArgs->wzPackageId, pArgs->dwProgressPercentage, pArgs->dwOverallPercentage, &pResults->fCancel);
}
static HRESULT BalBaseBAProcOnExecuteMsiMessage(
__in IBootstrapperApplication* pBA,
__in BA_ONEXECUTEMSIMESSAGE_ARGS* pArgs,
__inout BA_ONEXECUTEMSIMESSAGE_RESULTS* pResults
)
{
return pBA->OnExecuteMsiMessage(pArgs->wzPackageId, pArgs->messageType, pArgs->dwUIHint, pArgs->wzMessage, pArgs->cData, pArgs->rgwzData, pArgs->nRecommendation, &pResults->nResult);
}
static HRESULT BalBaseBAProcOnExecuteFilesInUse(
__in IBootstrapperApplication* pBA,
__in BA_ONEXECUTEFILESINUSE_ARGS* pArgs,
__inout BA_ONEXECUTEFILESINUSE_RESULTS* pResults
)
{
return pBA->OnExecuteFilesInUse(pArgs->wzPackageId, pArgs->cFiles, pArgs->rgwzFiles, pArgs->nRecommendation, &pResults->nResult);
}
static HRESULT BalBaseBAProcOnExecutePackageComplete(
__in IBootstrapperApplication* pBA,
__in BA_ONEXECUTEPACKAGECOMPLETE_ARGS* pArgs,
__inout BA_ONEXECUTEPACKAGECOMPLETE_RESULTS* pResults
)
{
return pBA->OnExecutePackageComplete(pArgs->wzPackageId, pArgs->hrStatus, pArgs->restart, pArgs->recommendation, &pResults->action);
}
static HRESULT BalBaseBAProcOnExecuteComplete(
__in IBootstrapperApplication* pBA,
__in BA_ONEXECUTECOMPLETE_ARGS* pArgs,
__inout BA_ONEXECUTECOMPLETE_RESULTS* /*pResults*/
)
{
return pBA->OnExecuteComplete(pArgs->hrStatus);
}
static HRESULT BalBaseBAProcOnUnregisterBegin(
__in IBootstrapperApplication* pBA,
__in BA_ONUNREGISTERBEGIN_ARGS* /*pArgs*/,
__inout BA_ONUNREGISTERBEGIN_RESULTS* pResults
)
{
return pBA->OnUnregisterBegin(&pResults->fCancel);
}
static HRESULT BalBaseBAProcOnUnregisterComplete(
__in IBootstrapperApplication* pBA,
__in BA_ONUNREGISTERCOMPLETE_ARGS* pArgs,
__inout BA_ONUNREGISTERCOMPLETE_RESULTS* /*pResults*/
)
{
return pBA->OnUnregisterComplete(pArgs->hrStatus);
}
static HRESULT BalBaseBAProcOnApplyComplete(
__in IBootstrapperApplication* pBA,
__in BA_ONAPPLYCOMPLETE_ARGS* pArgs,
__inout BA_ONAPPLYCOMPLETE_RESULTS* pResults
)
{
return pBA->OnApplyComplete(pArgs->hrStatus, pArgs->restart, pArgs->recommendation, &pResults->action);
}
static HRESULT BalBaseBAProcOnLaunchApprovedExeBegin(
__in IBootstrapperApplication* pBA,
__in BA_ONLAUNCHAPPROVEDEXEBEGIN_ARGS* /*pArgs*/,
__inout BA_ONLAUNCHAPPROVEDEXEBEGIN_RESULTS* pResults
)
{
return pBA->OnLaunchApprovedExeBegin(&pResults->fCancel);
}
static HRESULT BalBaseBAProcOnLaunchApprovedExeComplete(
__in IBootstrapperApplication* pBA,
__in BA_ONLAUNCHAPPROVEDEXECOMPLETE_ARGS* pArgs,
__inout BA_ONLAUNCHAPPROVEDEXECOMPLETE_RESULTS* /*pResults*/
)
{
return pBA->OnLaunchApprovedExeComplete(pArgs->hrStatus, pArgs->dwProcessId);
}
/*******************************************************************
BalBaseBootstrapperApplicationProc - requires pvContext to be of type IBootstrapperApplication.
Provides a default mapping between the new message based BA interface and
the old COM-based BA interface.
*******************************************************************/
static HRESULT WINAPI BalBaseBootstrapperApplicationProc(
__in BOOTSTRAPPER_APPLICATION_MESSAGE message,
__in const LPVOID pvArgs,
__inout LPVOID pvResults,
__in_opt LPVOID pvContext
)
{
IBootstrapperApplication* pBA = reinterpret_cast<IBootstrapperApplication*>(pvContext);
HRESULT hr = pBA->BAProc(message, pvArgs, pvResults, pvContext);
if (E_NOTIMPL == hr)
{
switch (message)
{
case BOOTSTRAPPER_APPLICATION_MESSAGE_ONDETECTBEGIN:
hr = BalBaseBAProcOnDetectBegin(pBA, reinterpret_cast<BA_ONDETECTBEGIN_ARGS*>(pvArgs), reinterpret_cast<BA_ONDETECTBEGIN_RESULTS*>(pvResults));
break;
case BOOTSTRAPPER_APPLICATION_MESSAGE_ONDETECTCOMPLETE:
hr = BalBaseBAProcOnDetectComplete(pBA, reinterpret_cast<BA_ONDETECTCOMPLETE_ARGS*>(pvArgs), reinterpret_cast<BA_ONDETECTCOMPLETE_RESULTS*>(pvResults));
break;
case BOOTSTRAPPER_APPLICATION_MESSAGE_ONPLANBEGIN:
hr = BalBaseBAProcOnPlanBegin(pBA, reinterpret_cast<BA_ONPLANBEGIN_ARGS*>(pvArgs), reinterpret_cast<BA_ONPLANBEGIN_RESULTS*>(pvResults));
break;
case BOOTSTRAPPER_APPLICATION_MESSAGE_ONPLANCOMPLETE:
hr = BalBaseBAProcOnPlanComplete(pBA, reinterpret_cast<BA_ONPLANCOMPLETE_ARGS*>(pvArgs), reinterpret_cast<BA_ONPLANCOMPLETE_RESULTS*>(pvResults));
break;
case BOOTSTRAPPER_APPLICATION_MESSAGE_ONSTARTUP:
hr = BalBaseBAProcOnStartup(pBA, reinterpret_cast<BA_ONSTARTUP_ARGS*>(pvArgs), reinterpret_cast<BA_ONSTARTUP_RESULTS*>(pvResults));
break;
case BOOTSTRAPPER_APPLICATION_MESSAGE_ONSHUTDOWN:
hr = BalBaseBAProcOnShutdown(pBA, reinterpret_cast<BA_ONSHUTDOWN_ARGS*>(pvArgs), reinterpret_cast<BA_ONSHUTDOWN_RESULTS*>(pvResults));
break;
case BOOTSTRAPPER_APPLICATION_MESSAGE_ONSYSTEMSHUTDOWN:
hr = BalBaseBAProcOnSystemShutdown(pBA, reinterpret_cast<BA_ONSYSTEMSHUTDOWN_ARGS*>(pvArgs), reinterpret_cast<BA_ONSYSTEMSHUTDOWN_RESULTS*>(pvResults));
break;
case BOOTSTRAPPER_APPLICATION_MESSAGE_ONDETECTFORWARDCOMPATIBLEBUNDLE:
hr = BalBaseBAProcOnDetectForwardCompatibleBundle(pBA, reinterpret_cast<BA_ONDETECTFORWARDCOMPATIBLEBUNDLE_ARGS*>(pvArgs), reinterpret_cast<BA_ONDETECTFORWARDCOMPATIBLEBUNDLE_RESULTS*>(pvResults));
break;
case BOOTSTRAPPER_APPLICATION_MESSAGE_ONDETECTUPDATEBEGIN:
hr = BalBaseBAProcOnDetectUpdateBegin(pBA, reinterpret_cast<BA_ONDETECTUPDATEBEGIN_ARGS*>(pvArgs), reinterpret_cast<BA_ONDETECTUPDATEBEGIN_RESULTS*>(pvResults));
break;
case BOOTSTRAPPER_APPLICATION_MESSAGE_ONDETECTUPDATE:
hr = BalBaseBAProcOnDetectUpdate(pBA, reinterpret_cast<BA_ONDETECTUPDATE_ARGS*>(pvArgs), reinterpret_cast<BA_ONDETECTUPDATE_RESULTS*>(pvResults));
break;
case BOOTSTRAPPER_APPLICATION_MESSAGE_ONDETECTUPDATECOMPLETE:
hr = BalBaseBAProcOnDetectUpdateComplete(pBA, reinterpret_cast<BA_ONDETECTUPDATECOMPLETE_ARGS*>(pvArgs), reinterpret_cast<BA_ONDETECTUPDATECOMPLETE_RESULTS*>(pvResults));
break;
case BOOTSTRAPPER_APPLICATION_MESSAGE_ONDETECTRELATEDBUNDLE:
hr = BalBaseBAProcOnDetectRelatedBundle(pBA, reinterpret_cast<BA_ONDETECTRELATEDBUNDLE_ARGS*>(pvArgs), reinterpret_cast<BA_ONDETECTRELATEDBUNDLE_RESULTS*>(pvResults));
break;
case BOOTSTRAPPER_APPLICATION_MESSAGE_ONDETECTPACKAGEBEGIN:
hr = BalBaseBAProcOnDetectPackageBegin(pBA, reinterpret_cast<BA_ONDETECTPACKAGEBEGIN_ARGS*>(pvArgs), reinterpret_cast<BA_ONDETECTPACKAGEBEGIN_RESULTS*>(pvResults));
break;
case BOOTSTRAPPER_APPLICATION_MESSAGE_ONDETECTCOMPATIBLEMSIPACKAGE:
hr = BalBaseBAProcOnDetectCompatiblePackage(pBA, reinterpret_cast<BA_ONDETECTCOMPATIBLEMSIPACKAGE_ARGS*>(pvArgs), reinterpret_cast<BA_ONDETECTCOMPATIBLEMSIPACKAGE_RESULTS*>(pvResults));
break;
case BOOTSTRAPPER_APPLICATION_MESSAGE_ONDETECTRELATEDMSIPACKAGE:
hr = BalBaseBAProcOnDetectRelatedMsiPackage(pBA, reinterpret_cast<BA_ONDETECTRELATEDMSIPACKAGE_ARGS*>(pvArgs), reinterpret_cast<BA_ONDETECTRELATEDMSIPACKAGE_RESULTS*>(pvResults));
break;
case BOOTSTRAPPER_APPLICATION_MESSAGE_ONDETECTTARGETMSIPACKAGE:
hr = BalBaseBAProcOnDetectTargetMsiPackage(pBA, reinterpret_cast<BA_ONDETECTTARGETMSIPACKAGE_ARGS*>(pvArgs), reinterpret_cast<BA_ONDETECTTARGETMSIPACKAGE_RESULTS*>(pvResults));
break;
case BOOTSTRAPPER_APPLICATION_MESSAGE_ONDETECTMSIFEATURE:
hr = BalBaseBAProcOnDetectMsiFeature(pBA, reinterpret_cast<BA_ONDETECTMSIFEATURE_ARGS*>(pvArgs), reinterpret_cast<BA_ONDETECTMSIFEATURE_RESULTS*>(pvResults));
break;
case BOOTSTRAPPER_APPLICATION_MESSAGE_ONDETECTPACKAGECOMPLETE:
hr = BalBaseBAProcOnDetectPackageComplete(pBA, reinterpret_cast<BA_ONDETECTPACKAGECOMPLETE_ARGS*>(pvArgs), reinterpret_cast<BA_ONDETECTPACKAGECOMPLETE_RESULTS*>(pvResults));
break;
case BOOTSTRAPPER_APPLICATION_MESSAGE_ONPLANRELATEDBUNDLE:
hr = BalBaseBAProcOnPlanRelatedBundle(pBA, reinterpret_cast<BA_ONPLANRELATEDBUNDLE_ARGS*>(pvArgs), reinterpret_cast<BA_ONPLANRELATEDBUNDLE_RESULTS*>(pvResults));
break;
case BOOTSTRAPPER_APPLICATION_MESSAGE_ONPLANPACKAGEBEGIN:
hr = BalBaseBAProcOnPlanPackageBegin(pBA, reinterpret_cast<BA_ONPLANPACKAGEBEGIN_ARGS*>(pvArgs), reinterpret_cast<BA_ONPLANPACKAGEBEGIN_RESULTS*>(pvResults));
break;
case BOOTSTRAPPER_APPLICATION_MESSAGE_ONPLANCOMPATIBLEMSIPACKAGEBEGIN:
hr = BalBaseBAProcOnPlanCompatibleMsiPackageBegin(pBA, reinterpret_cast<BA_ONPLANCOMPATIBLEMSIPACKAGEBEGIN_ARGS*>(pvArgs), reinterpret_cast<BA_ONPLANCOMPATIBLEMSIPACKAGEBEGIN_RESULTS*>(pvResults));
break;
case BOOTSTRAPPER_APPLICATION_MESSAGE_ONPLANCOMPATIBLEMSIPACKAGECOMPLETE:
hr = BalBaseBAProcOnPlanCompatibleMsiPackageComplete(pBA, reinterpret_cast<BA_ONPLANCOMPATIBLEMSIPACKAGECOMPLETE_ARGS*>(pvArgs), reinterpret_cast<BA_ONPLANCOMPATIBLEMSIPACKAGECOMPLETE_RESULTS*>(pvResults));
break;
case BOOTSTRAPPER_APPLICATION_MESSAGE_ONPLANTARGETMSIPACKAGE:
hr = BalBaseBAProcOnPlanTargetMsiPackage(pBA, reinterpret_cast<BA_ONPLANTARGETMSIPACKAGE_ARGS*>(pvArgs), reinterpret_cast<BA_ONPLANTARGETMSIPACKAGE_RESULTS*>(pvResults));
break;
case BOOTSTRAPPER_APPLICATION_MESSAGE_ONPLANMSIFEATURE:
hr = BalBaseBAProcOnPlanMsiFeature(pBA, reinterpret_cast<BA_ONPLANMSIFEATURE_ARGS*>(pvArgs), reinterpret_cast<BA_ONPLANMSIFEATURE_RESULTS*>(pvResults));
break;
case BOOTSTRAPPER_APPLICATION_MESSAGE_ONPLANPACKAGECOMPLETE:
hr = BalBaseBAProcOnPlanPackageComplete(pBA, reinterpret_cast<BA_ONPLANPACKAGECOMPLETE_ARGS*>(pvArgs), reinterpret_cast<BA_ONPLANPACKAGECOMPLETE_RESULTS*>(pvResults));
break;
case BOOTSTRAPPER_APPLICATION_MESSAGE_ONAPPLYBEGIN:
hr = BalBaseBAProcOnApplyBegin(pBA, reinterpret_cast<BA_ONAPPLYBEGIN_ARGS*>(pvArgs), reinterpret_cast<BA_ONAPPLYBEGIN_RESULTS*>(pvResults));
break;
case BOOTSTRAPPER_APPLICATION_MESSAGE_ONELEVATEBEGIN:
hr = BalBaseBAProcOnElevateBegin(pBA, reinterpret_cast<BA_ONELEVATEBEGIN_ARGS*>(pvArgs), reinterpret_cast<BA_ONELEVATEBEGIN_RESULTS*>(pvResults));
break;
case BOOTSTRAPPER_APPLICATION_MESSAGE_ONELEVATECOMPLETE:
hr = BalBaseBAProcOnElevateComplete(pBA, reinterpret_cast<BA_ONELEVATECOMPLETE_ARGS*>(pvArgs), reinterpret_cast<BA_ONELEVATECOMPLETE_RESULTS*>(pvResults));
break;
case BOOTSTRAPPER_APPLICATION_MESSAGE_ONPROGRESS:
hr = BalBaseBAProcOnProgress(pBA, reinterpret_cast<BA_ONPROGRESS_ARGS*>(pvArgs), reinterpret_cast<BA_ONPROGRESS_RESULTS*>(pvResults));
break;
case BOOTSTRAPPER_APPLICATION_MESSAGE_ONERROR:
hr = BalBaseBAProcOnError(pBA, reinterpret_cast<BA_ONERROR_ARGS*>(pvArgs), reinterpret_cast<BA_ONERROR_RESULTS*>(pvResults));
break;
case BOOTSTRAPPER_APPLICATION_MESSAGE_ONREGISTERBEGIN:
hr = BalBaseBAProcOnRegisterBegin(pBA, reinterpret_cast<BA_ONREGISTERBEGIN_ARGS*>(pvArgs), reinterpret_cast<BA_ONREGISTERBEGIN_RESULTS*>(pvResults));
break;
case BOOTSTRAPPER_APPLICATION_MESSAGE_ONREGISTERCOMPLETE:
hr = BalBaseBAProcOnRegisterComplete(pBA, reinterpret_cast<BA_ONREGISTERCOMPLETE_ARGS*>(pvArgs), reinterpret_cast<BA_ONREGISTERCOMPLETE_RESULTS*>(pvResults));
break;
case BOOTSTRAPPER_APPLICATION_MESSAGE_ONCACHEBEGIN:
hr = BalBaseBAProcOnCacheBegin(pBA, reinterpret_cast<BA_ONCACHEBEGIN_ARGS*>(pvArgs), reinterpret_cast<BA_ONCACHEBEGIN_RESULTS*>(pvResults));
break;
case BOOTSTRAPPER_APPLICATION_MESSAGE_ONCACHEPACKAGEBEGIN:
hr = BalBaseBAProcOnCachePackageBegin(pBA, reinterpret_cast<BA_ONCACHEPACKAGEBEGIN_ARGS*>(pvArgs), reinterpret_cast<BA_ONCACHEPACKAGEBEGIN_RESULTS*>(pvResults));
break;
case BOOTSTRAPPER_APPLICATION_MESSAGE_ONCACHEACQUIREBEGIN:
hr = BalBaseBAProcOnCacheAcquireBegin(pBA, reinterpret_cast<BA_ONCACHEACQUIREBEGIN_ARGS*>(pvArgs), reinterpret_cast<BA_ONCACHEACQUIREBEGIN_RESULTS*>(pvResults));
break;
case BOOTSTRAPPER_APPLICATION_MESSAGE_ONCACHEACQUIREPROGRESS:
hr = BalBaseBAProcOnCacheAcquireProgress(pBA, reinterpret_cast<BA_ONCACHEACQUIREPROGRESS_ARGS*>(pvArgs), reinterpret_cast<BA_ONCACHEACQUIREPROGRESS_RESULTS*>(pvResults));
break;
case BOOTSTRAPPER_APPLICATION_MESSAGE_ONRESOLVESOURCE:
hr = BalBaseBAProcOnResolveSource(pBA, reinterpret_cast<BA_ONRESOLVESOURCE_ARGS*>(pvArgs), reinterpret_cast<BA_ONRESOLVESOURCE_RESULTS*>(pvResults));
break;
case BOOTSTRAPPER_APPLICATION_MESSAGE_ONCACHEACQUIRECOMPLETE:
hr = BalBaseBAProcOnCacheAcquireComplete(pBA, reinterpret_cast<BA_ONCACHEACQUIRECOMPLETE_ARGS*>(pvArgs), reinterpret_cast<BA_ONCACHEACQUIRECOMPLETE_RESULTS*>(pvResults));
break;
case BOOTSTRAPPER_APPLICATION_MESSAGE_ONCACHEVERIFYBEGIN:
hr = BalBaseBAProcOnCacheVerifyBegin(pBA, reinterpret_cast<BA_ONCACHEVERIFYBEGIN_ARGS*>(pvArgs), reinterpret_cast<BA_ONCACHEVERIFYBEGIN_RESULTS*>(pvResults));
break;
case BOOTSTRAPPER_APPLICATION_MESSAGE_ONCACHEVERIFYCOMPLETE:
hr = BalBaseBAProcOnCacheVerifyComplete(pBA, reinterpret_cast<BA_ONCACHEVERIFYCOMPLETE_ARGS*>(pvArgs), reinterpret_cast<BA_ONCACHEVERIFYCOMPLETE_RESULTS*>(pvResults));
break;
case BOOTSTRAPPER_APPLICATION_MESSAGE_ONCACHEPACKAGECOMPLETE:
hr = BalBaseBAProcOnCachePackageComplete(pBA, reinterpret_cast<BA_ONCACHEPACKAGECOMPLETE_ARGS*>(pvArgs), reinterpret_cast<BA_ONCACHEPACKAGECOMPLETE_RESULTS*>(pvResults));
break;
case BOOTSTRAPPER_APPLICATION_MESSAGE_ONCACHECOMPLETE:
hr = BalBaseBAProcOnCacheComplete(pBA, reinterpret_cast<BA_ONCACHECOMPLETE_ARGS*>(pvArgs), reinterpret_cast<BA_ONCACHECOMPLETE_RESULTS*>(pvResults));
break;
case BOOTSTRAPPER_APPLICATION_MESSAGE_ONEXECUTEBEGIN:
hr = BalBaseBAProcOnExecuteBegin(pBA, reinterpret_cast<BA_ONEXECUTEBEGIN_ARGS*>(pvArgs), reinterpret_cast<BA_ONEXECUTEBEGIN_RESULTS*>(pvResults));
break;
case BOOTSTRAPPER_APPLICATION_MESSAGE_ONEXECUTEPACKAGEBEGIN:
hr = BalBaseBAProcOnExecutePackageBegin(pBA, reinterpret_cast<BA_ONEXECUTEPACKAGEBEGIN_ARGS*>(pvArgs), reinterpret_cast<BA_ONEXECUTEPACKAGEBEGIN_RESULTS*>(pvResults));
break;
case BOOTSTRAPPER_APPLICATION_MESSAGE_ONEXECUTEPATCHTARGET:
hr = BalBaseBAProcOnExecutePatchTarget(pBA, reinterpret_cast<BA_ONEXECUTEPATCHTARGET_ARGS*>(pvArgs), reinterpret_cast<BA_ONEXECUTEPATCHTARGET_RESULTS*>(pvResults));
break;
case BOOTSTRAPPER_APPLICATION_MESSAGE_ONEXECUTEPROGRESS:
hr = BalBaseBAProcOnExecuteProgress(pBA, reinterpret_cast<BA_ONEXECUTEPROGRESS_ARGS*>(pvArgs), reinterpret_cast<BA_ONEXECUTEPROGRESS_RESULTS*>(pvResults));
break;
case BOOTSTRAPPER_APPLICATION_MESSAGE_ONEXECUTEMSIMESSAGE:
hr = BalBaseBAProcOnExecuteMsiMessage(pBA, reinterpret_cast<BA_ONEXECUTEMSIMESSAGE_ARGS*>(pvArgs), reinterpret_cast<BA_ONEXECUTEMSIMESSAGE_RESULTS*>(pvResults));
break;
case BOOTSTRAPPER_APPLICATION_MESSAGE_ONEXECUTEFILESINUSE:
hr = BalBaseBAProcOnExecuteFilesInUse(pBA, reinterpret_cast<BA_ONEXECUTEFILESINUSE_ARGS*>(pvArgs), reinterpret_cast<BA_ONEXECUTEFILESINUSE_RESULTS*>(pvResults));
break;
case BOOTSTRAPPER_APPLICATION_MESSAGE_ONEXECUTEPACKAGECOMPLETE:
hr = BalBaseBAProcOnExecutePackageComplete(pBA, reinterpret_cast<BA_ONEXECUTEPACKAGECOMPLETE_ARGS*>(pvArgs), reinterpret_cast<BA_ONEXECUTEPACKAGECOMPLETE_RESULTS*>(pvResults));
break;
case BOOTSTRAPPER_APPLICATION_MESSAGE_ONEXECUTECOMPLETE:
hr = BalBaseBAProcOnExecuteComplete(pBA, reinterpret_cast<BA_ONEXECUTECOMPLETE_ARGS*>(pvArgs), reinterpret_cast<BA_ONEXECUTECOMPLETE_RESULTS*>(pvResults));
break;
case BOOTSTRAPPER_APPLICATION_MESSAGE_ONUNREGISTERBEGIN:
hr = BalBaseBAProcOnUnregisterBegin(pBA, reinterpret_cast<BA_ONUNREGISTERBEGIN_ARGS*>(pvArgs), reinterpret_cast<BA_ONUNREGISTERBEGIN_RESULTS*>(pvResults));
break;
case BOOTSTRAPPER_APPLICATION_MESSAGE_ONUNREGISTERCOMPLETE:
hr = BalBaseBAProcOnUnregisterComplete(pBA, reinterpret_cast<BA_ONUNREGISTERCOMPLETE_ARGS*>(pvArgs), reinterpret_cast<BA_ONUNREGISTERCOMPLETE_RESULTS*>(pvResults));
break;
case BOOTSTRAPPER_APPLICATION_MESSAGE_ONAPPLYCOMPLETE:
hr = BalBaseBAProcOnApplyComplete(pBA, reinterpret_cast<BA_ONAPPLYCOMPLETE_ARGS*>(pvArgs), reinterpret_cast<BA_ONAPPLYCOMPLETE_RESULTS*>(pvResults));
break;
case BOOTSTRAPPER_APPLICATION_MESSAGE_ONLAUNCHAPPROVEDEXEBEGIN:
hr = BalBaseBAProcOnLaunchApprovedExeBegin(pBA, reinterpret_cast<BA_ONLAUNCHAPPROVEDEXEBEGIN_ARGS*>(pvArgs), reinterpret_cast<BA_ONLAUNCHAPPROVEDEXEBEGIN_RESULTS*>(pvResults));
break;
case BOOTSTRAPPER_APPLICATION_MESSAGE_ONLAUNCHAPPROVEDEXECOMPLETE:
hr = BalBaseBAProcOnLaunchApprovedExeComplete(pBA, reinterpret_cast<BA_ONLAUNCHAPPROVEDEXECOMPLETE_ARGS*>(pvArgs), reinterpret_cast<BA_ONLAUNCHAPPROVEDEXECOMPLETE_RESULTS*>(pvResults));
break;
}
}
pBA->BAProcFallback(message, pvArgs, pvResults, &hr, pvContext);
return hr;
}

Просмотреть файл

@ -0,0 +1,17 @@
// Copyright (c) .NET Foundation and contributors. All rights reserved. Licensed under the Microsoft Reciprocal License. See LICENSE.TXT file in the project root for full license information.
#ifdef __cplusplus
extern "C" {
#endif
// function declarations
HRESULT BalBootstrapperEngineCreate(
__in PFN_BOOTSTRAPPER_ENGINE_PROC pfnBAEngineProc,
__in_opt LPVOID pvBAEngineProcContext,
__out IBootstrapperEngine** ppEngineForApplication
);
#ifdef __cplusplus
}
#endif

Просмотреть файл

@ -0,0 +1,34 @@
#pragma once
// Copyright (c) .NET Foundation and contributors. All rights reserved. Licensed under the Microsoft Reciprocal License. See LICENSE.TXT file in the project root for full license information.
DECLARE_INTERFACE_IID_(IBAFunctions, IBootstrapperApplication, "0FB445ED-17BD-49C7-BE19-479776F8AE96")
{
// OnThemeLoaded - Called after the BA finished loading all the controls for the theme.
//
STDMETHOD(OnThemeLoaded)(
THEME* pTheme,
WIX_LOCALIZATION* pWixLoc
) = 0;
// WndProc - Called if the BA hasn't handled the message.
// The implementation must either return E_NOTIMPL or call ThemeDefWindowProc for unhandled messages.
//
STDMETHOD(WndProc)(
__in THEME* pTheme,
__in HWND hWnd,
__in UINT uMsg,
__in WPARAM wParam,
__in LPARAM lParam,
__inout LRESULT* plRes
) = 0;
// BAFunctionsProc - The PFN_BA_FUNCTIONS_PROC can call this method to give the BAFunctions raw access to the callback from WixStdBA.
// This might be used to help the BAFunctions support more than one version of the engine/WixStdBA.
STDMETHOD(BAFunctionsProc)(
__in BA_FUNCTIONS_MESSAGE message,
__in const LPVOID pvArgs,
__inout LPVOID pvResults,
__in_opt LPVOID pvContext
) = 0;
};

Просмотреть файл

@ -0,0 +1,58 @@
#pragma once
// Copyright (c) .NET Foundation and contributors. All rights reserved. Licensed under the Microsoft Reciprocal License. See LICENSE.TXT file in the project root for full license information.
#ifdef __cplusplus
extern "C" {
#endif
typedef struct _BAL_CONDITION
{
LPWSTR sczCondition;
LPWSTR sczMessage;
} BAL_CONDITION;
typedef struct _BAL_CONDITIONS
{
BAL_CONDITION* rgConditions;
DWORD cConditions;
} BAL_CONDITIONS;
/*******************************************************************
BalConditionsParseFromXml - loads the conditions from the UX manifest.
********************************************************************/
DAPI_(HRESULT) BalConditionsParseFromXml(
__in BAL_CONDITIONS* pConditions,
__in IXMLDOMDocument* pixdManifest,
__in_opt WIX_LOCALIZATION* pWixLoc
);
/*******************************************************************
BalConditionEvaluate - evaluates condition against the provided IBurnCore.
NOTE: psczMessage is optional.
********************************************************************/
DAPI_(HRESULT) BalConditionEvaluate(
__in BAL_CONDITION* pCondition,
__in IBootstrapperEngine* pEngine,
__out BOOL* pfResult,
__out_z_opt LPWSTR* psczMessage
);
/*******************************************************************
BalConditionsUninitialize - uninitializes any conditions previously loaded.
********************************************************************/
DAPI_(void) BalConditionsUninitialize(
__in BAL_CONDITIONS* pConditions
);
#ifdef __cplusplus
}
#endif

107
src/balutil/inc/balinfo.h Normal file
Просмотреть файл

@ -0,0 +1,107 @@
#pragma once
// Copyright (c) .NET Foundation and contributors. All rights reserved. Licensed under the Microsoft Reciprocal License. See LICENSE.TXT file in the project root for full license information.
#ifdef __cplusplus
extern "C" {
#endif
typedef enum BAL_INFO_PACKAGE_TYPE
{
BAL_INFO_PACKAGE_TYPE_UNKNOWN,
BAL_INFO_PACKAGE_TYPE_EXE,
BAL_INFO_PACKAGE_TYPE_MSI,
BAL_INFO_PACKAGE_TYPE_MSP,
BAL_INFO_PACKAGE_TYPE_MSU,
BAL_INFO_PACKAGE_TYPE_BUNDLE_UPGRADE,
BAL_INFO_PACKAGE_TYPE_BUNDLE_ADDON,
BAL_INFO_PACKAGE_TYPE_BUNDLE_PATCH,
} BAL_INFO_PACKAGE_TYPE;
typedef enum BAL_INFO_CACHE_TYPE
{
BAL_INFO_CACHE_TYPE_NO,
BAL_INFO_CACHE_TYPE_YES,
BAL_INFO_CACHE_TYPE_ALWAYS,
} BAL_INFO_CACHE_TYPE;
typedef struct _BAL_INFO_PACKAGE
{
LPWSTR sczId;
LPWSTR sczDisplayName;
LPWSTR sczDescription;
BAL_INFO_PACKAGE_TYPE type;
BOOL fPermanent;
BOOL fVital;
BOOL fDisplayInternalUI;
LPWSTR sczProductCode;
LPWSTR sczUpgradeCode;
LPWSTR sczVersion;
LPWSTR sczInstallCondition;
BAL_INFO_CACHE_TYPE cacheType;
} BAL_INFO_PACKAGE;
typedef struct _BAL_INFO_PACKAGES
{
BAL_INFO_PACKAGE* rgPackages;
DWORD cPackages;
} BAL_INFO_PACKAGES;
typedef struct _BAL_INFO_BUNDLE
{
BOOL fPerMachine;
LPWSTR sczName;
LPWSTR sczLogVariable;
BAL_INFO_PACKAGES packages;
} BAL_INFO_BUNDLE;
/*******************************************************************
BalInfoParseFromXml - loads the bundle and package info from the UX
manifest.
********************************************************************/
DAPI_(HRESULT) BalInfoParseFromXml(
__in BAL_INFO_BUNDLE* pBundle,
__in IXMLDOMDocument* pixdManifest
);
/*******************************************************************
BalInfoAddRelatedBundleAsPackage - adds a related bundle as a package.
********************************************************************/
DAPI_(HRESULT) BalInfoAddRelatedBundleAsPackage(
__in BAL_INFO_PACKAGES* pPackages,
__in LPCWSTR wzId,
__in BOOTSTRAPPER_RELATION_TYPE relationType,
__in BOOL fPerMachine
);
/*******************************************************************
BalInfoFindPackageById - finds a package by its id.
********************************************************************/
DAPI_(HRESULT) BalInfoFindPackageById(
__in BAL_INFO_PACKAGES* pPackages,
__in LPCWSTR wzId,
__out BAL_INFO_PACKAGE** ppPackage
);
/*******************************************************************
BalInfoUninitialize - uninitializes any info previously loaded.
********************************************************************/
DAPI_(void) BalInfoUninitialize(
__in BAL_INFO_BUNDLE* pBundle
);
#ifdef __cplusplus
}
#endif

Просмотреть файл

@ -0,0 +1,65 @@
#pragma once
// Copyright (c) .NET Foundation and contributors. All rights reserved. Licensed under the Microsoft Reciprocal License. See LICENSE.TXT file in the project root for full license information.
#ifdef __cplusplus
extern "C" {
#endif
typedef enum BALRETRY_TYPE
{
BALRETRY_TYPE_CACHE,
BALRETRY_TYPE_EXECUTE,
} BALRETRY_TYPE;
/*******************************************************************
BalRetryInitialize - initialize the retry count and timeout between
retries (in milliseconds).
********************************************************************/
DAPI_(void) BalRetryInitialize(
__in DWORD dwMaxRetries,
__in DWORD dwTimeout
);
/*******************************************************************
BalRetryUninitialize - call to cleanup any memory allocated during
use of the retry utility.
********************************************************************/
DAPI_(void) BalRetryUninitialize();
/*******************************************************************
BalRetryStartPackage - call when a package begins to be modified. If
the package is being retried, the function will
wait the specified timeout.
********************************************************************/
DAPI_(void) BalRetryStartPackage(
__in BALRETRY_TYPE type,
__in_z_opt LPCWSTR wzPackageId,
__in_z_opt LPCWSTR wzPayloadId
);
/*******************************************************************
BalRetryErrorOccured - call when an error occurs for the retry utility
to consider.
********************************************************************/
DAPI_(void) BalRetryErrorOccurred(
__in_z_opt LPCWSTR wzPackageId,
__in DWORD dwError
);
/*******************************************************************
BalRetryEndPackage - returns IDRETRY is a retry is recommended or
IDNOACTION if a retry is not recommended.
********************************************************************/
DAPI_(HRESULT) BalRetryEndPackage(
__in BALRETRY_TYPE type,
__in_z_opt LPCWSTR wzPackageId,
__in_z_opt LPCWSTR wzPayloadId,
__in HRESULT hrError,
__inout BOOL* pfRetry
);
#ifdef __cplusplus
}
#endif

165
src/balutil/inc/balutil.h Normal file
Просмотреть файл

@ -0,0 +1,165 @@
#pragma once
// Copyright (c) .NET Foundation and contributors. All rights reserved. Licensed under the Microsoft Reciprocal License. See LICENSE.TXT file in the project root for full license information.
#include "dutil.h"
#ifdef __cplusplus
extern "C" {
#endif
#define BalExitOnFailure(x, f, ...) if (FAILED(x)) { BalLogError(x, f, __VA_ARGS__); ExitTrace(x, f, __VA_ARGS__); goto LExit; }
#define BalExitOnRootFailure(x, f, ...) if (FAILED(x)) { BalLogError(x, f, __VA_ARGS__); Dutil_RootFailure(__FILE__, __LINE__, x); ExitTrace(x, f, __VA_ARGS__); goto LExit; }
#define BalExitOnNullWithLastError(p, x, f, ...) if (NULL == p) { DWORD Dutil_er = ::GetLastError(); x = HRESULT_FROM_WIN32(Dutil_er); if (!FAILED(x)) { x = E_FAIL; } BalLogError(x, f, __VA_ARGS__); ExitTrace(x, f, __VA_ARGS__); goto LExit; }
#define FACILITY_WIX 500
const LPCWSTR BAL_MANIFEST_FILENAME = L"BootstrapperApplicationData.xml";
static const HRESULT E_WIXSTDBA_CONDITION_FAILED = MAKE_HRESULT(SEVERITY_ERROR, FACILITY_WIX, 1);
static const HRESULT E_MBAHOST_NET452_ON_WIN7RTM = MAKE_HRESULT(SEVERITY_ERROR, FACILITY_WIX, 1000);
/*******************************************************************
BalInitialize - remembers the engine interface to enable logging and
other functions.
********************************************************************/
DAPI_(void) BalInitialize(
__in IBootstrapperEngine* pEngine
);
/*******************************************************************
BalInitializeFromCreateArgs - convenience function to call BalBootstrapperEngineCreate
then pass it along to BalInitialize.
********************************************************************/
DAPI_(HRESULT) BalInitializeFromCreateArgs(
__in const BOOTSTRAPPER_CREATE_ARGS* pArgs,
__out IBootstrapperEngine** ppEngine
);
/*******************************************************************
BalUninitialize - cleans up utility layer internals.
********************************************************************/
DAPI_(void) BalUninitialize();
/*******************************************************************
BalManifestLoad - loads the Application manifest into an XML document.
********************************************************************/
DAPI_(HRESULT) BalManifestLoad(
__in HMODULE hUXModule,
__out IXMLDOMDocument** ppixdManifest
);
/*******************************************************************
BalEvaluateCondition - evaluates a condition using variables in the engine.
********************************************************************/
DAPI_(HRESULT) BalEvaluateCondition(
__in_z LPCWSTR wzCondition,
__out BOOL* pf
);
/*******************************************************************
BalFormatString - formats a string using variables in the engine.
Note: Use StrFree() to release psczOut.
********************************************************************/
DAPI_(HRESULT) BalFormatString(
__in_z LPCWSTR wzFormat,
__inout LPWSTR* psczOut
);
/*******************************************************************
BalGetNumericVariable - gets a number from a variable in the engine.
Note: Returns E_NOTFOUND if variable does not exist.
********************************************************************/
DAPI_(HRESULT) BalGetNumericVariable(
__in_z LPCWSTR wzVariable,
__out LONGLONG* pllValue
);
/*******************************************************************
BalSetNumericVariable - sets a numeric variable in the engine.
********************************************************************/
DAPI_(HRESULT) BalSetNumericVariable(
__in_z LPCWSTR wzVariable,
__in LONGLONG llValue
);
/*******************************************************************
BalStringVariableExists - checks if a string variable exists in the engine.
********************************************************************/
DAPI_(BOOL) BalStringVariableExists(
__in_z LPCWSTR wzVariable
);
/*******************************************************************
BalGetStringVariable - gets a string from a variable in the engine.
Note: Use StrFree() to release psczValue.
********************************************************************/
DAPI_(HRESULT) BalGetStringVariable(
__in_z LPCWSTR wzVariable,
__inout LPWSTR* psczValue
);
/*******************************************************************
BalSetStringVariable - sets a string variable in the engine.
********************************************************************/
DAPI_(HRESULT) BalSetStringVariable(
__in_z LPCWSTR wzVariable,
__in_z_opt LPCWSTR wzValue
);
/*******************************************************************
BalLog - logs a message with the engine.
********************************************************************/
DAPIV_(HRESULT) BalLog(
__in BOOTSTRAPPER_LOG_LEVEL level,
__in_z __format_string LPCSTR szFormat,
...
);
/*******************************************************************
BalLogError - logs an error message with the engine.
********************************************************************/
DAPIV_(HRESULT) BalLogError(
__in HRESULT hr,
__in_z __format_string LPCSTR szFormat,
...
);
/*******************************************************************
BalLogId - logs a message with the engine with a string embedded in a
MESSAGETABLE resource.
********************************************************************/
DAPIV_(HRESULT) BalLogId(
__in BOOTSTRAPPER_LOG_LEVEL level,
__in DWORD dwLogId,
__in HMODULE hModule,
...
);
DAPI_(HRESULT) BalLogIdArgs(
__in BOOTSTRAPPER_LOG_LEVEL level,
__in DWORD dwLogId,
__in HMODULE hModule,
__in va_list args
);
#ifdef __cplusplus
}
#endif

31
src/balutil/precomp.h Normal file
Просмотреть файл

@ -0,0 +1,31 @@
#pragma once
// Copyright (c) .NET Foundation and contributors. All rights reserved. Licensed under the Microsoft Reciprocal License. See LICENSE.TXT file in the project root for full license information.
#include <windows.h>
#include <bitsmsg.h>
#include <msi.h>
#include <wininet.h>
#include <CommCtrl.h>
#include <dutil.h>
#include <pathutil.h>
#include <locutil.h>
#include <memutil.h>
#include <strutil.h>
#include <thmutil.h>
#include <xmlutil.h>
#include "BootstrapperEngine.h"
#include "BootstrapperApplication.h"
#include "IBootstrapperEngine.h"
#include "IBootstrapperApplication.h"
#include "BAFunctions.h"
#include "IBAFunctions.h"
#include "balutil.h"
#include "BalBootstrapperEngine.h"
#include "balcondition.h"
#include "balinfo.h"
#include "balretry.h"