diff options
| author | Sean Hall <r.sean.hall@gmail.com> | 2021-06-29 19:14:02 -0500 |
|---|---|---|
| committer | Sean Hall <r.sean.hall@gmail.com> | 2021-07-02 12:50:09 -0500 |
| commit | 8cbfc326cccf8d9b3b63cb6f752fc770f7dee0fc (patch) | |
| tree | 639f70e7327cdfade62271da04aaaaae2e85cc05 /src/ext | |
| parent | e844f12f7d7247a1e9ba4eef2a388e614001bb24 (diff) | |
| download | wix-8cbfc326cccf8d9b3b63cb6f752fc770f7dee0fc.tar.gz wix-8cbfc326cccf8d9b3b63cb6f752fc770f7dee0fc.tar.bz2 wix-8cbfc326cccf8d9b3b63cb6f752fc770f7dee0fc.zip | |
Expose overridable variable APIs in balutil and Mba.Core.
Fixes #4777
Diffstat (limited to 'src/ext')
| -rw-r--r-- | src/ext/Bal/wixstdba/WixStandardBootstrapperApplication.cpp | 131 |
1 files changed, 30 insertions, 101 deletions
diff --git a/src/ext/Bal/wixstdba/WixStandardBootstrapperApplication.cpp b/src/ext/Bal/wixstdba/WixStandardBootstrapperApplication.cpp index 62cdc70a..9f0b0082 100644 --- a/src/ext/Bal/wixstdba/WixStandardBootstrapperApplication.cpp +++ b/src/ext/Bal/wixstdba/WixStandardBootstrapperApplication.cpp | |||
| @@ -2095,8 +2095,8 @@ private: // privates | |||
| 2095 | hr = BalManifestLoad(m_hModule, &pixdManifest); | 2095 | hr = BalManifestLoad(m_hModule, &pixdManifest); |
| 2096 | BalExitOnFailure(hr, "Failed to load bootstrapper application manifest."); | 2096 | BalExitOnFailure(hr, "Failed to load bootstrapper application manifest."); |
| 2097 | 2097 | ||
| 2098 | hr = ParseOverridableVariablesFromXml(pixdManifest); | 2098 | hr = BalInfoParseFromXml(&m_Bundle, pixdManifest); |
| 2099 | BalExitOnFailure(hr, "Failed to read overridable variables."); | 2099 | BalExitOnFailure(hr, "Failed to load bundle information."); |
| 2100 | 2100 | ||
| 2101 | hr = ProcessCommandLine(&m_sczLanguage); | 2101 | hr = ProcessCommandLine(&m_sczLanguage); |
| 2102 | ExitOnFailure(hr, "Unknown commandline parameters."); | 2102 | ExitOnFailure(hr, "Unknown commandline parameters."); |
| @@ -2110,9 +2110,6 @@ private: // privates | |||
| 2110 | hr = LoadTheme(sczModulePath, m_sczLanguage); | 2110 | hr = LoadTheme(sczModulePath, m_sczLanguage); |
| 2111 | ExitOnFailure(hr, "Failed to load theme."); | 2111 | ExitOnFailure(hr, "Failed to load theme."); |
| 2112 | 2112 | ||
| 2113 | hr = BalInfoParseFromXml(&m_Bundle, pixdManifest); | ||
| 2114 | BalExitOnFailure(hr, "Failed to load bundle information."); | ||
| 2115 | |||
| 2116 | hr = BalConditionsParseFromXml(&m_Conditions, pixdManifest, m_pWixLoc); | 2113 | hr = BalConditionsParseFromXml(&m_Conditions, pixdManifest, m_pWixLoc); |
| 2117 | BalExitOnFailure(hr, "Failed to load conditions from XML."); | 2114 | BalExitOnFailure(hr, "Failed to load conditions from XML."); |
| 2118 | 2115 | ||
| @@ -2173,16 +2170,20 @@ private: // privates | |||
| 2173 | HRESULT hr = S_OK; | 2170 | HRESULT hr = S_OK; |
| 2174 | int argc = 0; | 2171 | int argc = 0; |
| 2175 | LPWSTR* argv = NULL; | 2172 | LPWSTR* argv = NULL; |
| 2176 | LPWSTR sczVariableName = NULL; | 2173 | BOOL fUnknownArg = FALSE; |
| 2177 | LPWSTR sczVariableValue = NULL; | ||
| 2178 | 2174 | ||
| 2179 | if (m_command.wzCommandLine && *m_command.wzCommandLine) | 2175 | hr = BalInfoParseCommandLine(&m_BalInfoCommand, m_command.wzCommandLine); |
| 2180 | { | 2176 | BalExitOnFailure(hr, "Failed to parse command line with balutil."); |
| 2181 | hr = AppParseCommandLine(m_command.wzCommandLine, &argc, &argv); | 2177 | |
| 2182 | ExitOnFailure(hr, "Failed to parse command line."); | 2178 | argc = m_BalInfoCommand.cUnknownArgs; |
| 2179 | argv = m_BalInfoCommand.rgUnknownArgs; | ||
| 2183 | 2180 | ||
| 2181 | if (argc) | ||
| 2182 | { | ||
| 2184 | for (int i = 0; i < argc; ++i) | 2183 | for (int i = 0; i < argc; ++i) |
| 2185 | { | 2184 | { |
| 2185 | fUnknownArg = FALSE; | ||
| 2186 | |||
| 2186 | if (argv[i][0] == L'-' || argv[i][0] == L'/') | 2187 | if (argv[i][0] == L'-' || argv[i][0] == L'/') |
| 2187 | { | 2188 | { |
| 2188 | if (CSTR_EQUAL == ::CompareStringW(LOCALE_INVARIANT, NORM_IGNORECASE, &argv[i][1], -1, L"lang", -1)) | 2189 | if (CSTR_EQUAL == ::CompareStringW(LOCALE_INVARIANT, NORM_IGNORECASE, &argv[i][1], -1, L"lang", -1)) |
| @@ -2198,51 +2199,31 @@ private: // privates | |||
| 2198 | hr = StrAllocString(psczLanguage, &argv[i][0], 0); | 2199 | hr = StrAllocString(psczLanguage, &argv[i][0], 0); |
| 2199 | BalExitOnFailure(hr, "Failed to copy language."); | 2200 | BalExitOnFailure(hr, "Failed to copy language."); |
| 2200 | } | 2201 | } |
| 2201 | } | 2202 | else if (CSTR_EQUAL == ::CompareStringW(LOCALE_INVARIANT, NORM_IGNORECASE, &argv[i][1], -1, L"cache", -1)) |
| 2202 | else if (CSTR_EQUAL == ::CompareStringW(LOCALE_INVARIANT, NORM_IGNORECASE, &argv[i][1], -1, L"cache", -1)) | ||
| 2203 | { | ||
| 2204 | m_plannedAction = BOOTSTRAPPER_ACTION_CACHE; | ||
| 2205 | } | ||
| 2206 | else if (m_sdOverridableVariables) | ||
| 2207 | { | ||
| 2208 | const wchar_t* pwc = wcschr(argv[i], L'='); | ||
| 2209 | if (pwc) | ||
| 2210 | { | 2203 | { |
| 2211 | hr = StrAllocString(&sczVariableName, argv[i], pwc - argv[i]); | 2204 | m_plannedAction = BOOTSTRAPPER_ACTION_CACHE; |
| 2212 | BalExitOnFailure(hr, "Failed to copy variable name."); | ||
| 2213 | |||
| 2214 | hr = DictKeyExists(m_sdOverridableVariables, sczVariableName); | ||
| 2215 | if (E_NOTFOUND == hr) | ||
| 2216 | { | ||
| 2217 | BalLog(BOOTSTRAPPER_LOG_LEVEL_ERROR, "Ignoring attempt to set non-overridable variable: '%ls'.", sczVariableName); | ||
| 2218 | hr = S_OK; | ||
| 2219 | continue; | ||
| 2220 | } | ||
| 2221 | ExitOnFailure(hr, "Failed to check the dictionary of overridable variables."); | ||
| 2222 | |||
| 2223 | hr = StrAllocString(&sczVariableValue, ++pwc, 0); | ||
| 2224 | BalExitOnFailure(hr, "Failed to copy variable value."); | ||
| 2225 | |||
| 2226 | hr = m_pEngine->SetVariableString(sczVariableName, sczVariableValue, FALSE); | ||
| 2227 | BalExitOnFailure(hr, "Failed to set variable."); | ||
| 2228 | } | 2205 | } |
| 2229 | else | 2206 | else |
| 2230 | { | 2207 | { |
| 2231 | BalLog(BOOTSTRAPPER_LOG_LEVEL_STANDARD, "Ignoring unknown argument: %ls", argv[i]); | 2208 | fUnknownArg = TRUE; |
| 2232 | } | 2209 | } |
| 2233 | } | 2210 | } |
| 2234 | } | 2211 | else |
| 2235 | } | 2212 | { |
| 2213 | fUnknownArg = TRUE; | ||
| 2214 | } | ||
| 2236 | 2215 | ||
| 2237 | LExit: | 2216 | if (fUnknownArg) |
| 2238 | if (argv) | 2217 | { |
| 2239 | { | 2218 | BalLog(BOOTSTRAPPER_LOG_LEVEL_STANDARD, "Ignoring unknown argument: %ls", argv[i]); |
| 2240 | AppFreeCommandLineArgs(argv); | 2219 | } |
| 2220 | } | ||
| 2241 | } | 2221 | } |
| 2242 | 2222 | ||
| 2243 | ReleaseStr(sczVariableName); | 2223 | hr = BalSetOverridableVariablesFromEngine(&m_Bundle.overridableVariables, &m_BalInfoCommand, m_pEngine); |
| 2244 | ReleaseStr(sczVariableValue); | 2224 | BalExitOnFailure(hr, "Failed to set overridable variables from the command line."); |
| 2245 | 2225 | ||
| 2226 | LExit: | ||
| 2246 | return hr; | 2227 | return hr; |
| 2247 | } | 2228 | } |
| 2248 | 2229 | ||
| @@ -2323,57 +2304,6 @@ private: // privates | |||
| 2323 | } | 2304 | } |
| 2324 | 2305 | ||
| 2325 | 2306 | ||
| 2326 | HRESULT ParseOverridableVariablesFromXml( | ||
| 2327 | __in IXMLDOMDocument* pixdManifest | ||
| 2328 | ) | ||
| 2329 | { | ||
| 2330 | HRESULT hr = S_OK; | ||
| 2331 | IXMLDOMNode* pNode = NULL; | ||
| 2332 | IXMLDOMNodeList* pNodes = NULL; | ||
| 2333 | DWORD cNodes = 0; | ||
| 2334 | LPWSTR scz = NULL; | ||
| 2335 | |||
| 2336 | // Get the list of variables users can override on the command line. | ||
| 2337 | hr = XmlSelectNodes(pixdManifest, L"/BootstrapperApplicationData/WixStdbaOverridableVariable", &pNodes); | ||
| 2338 | if (S_FALSE == hr) | ||
| 2339 | { | ||
| 2340 | ExitFunction1(hr = S_OK); | ||
| 2341 | } | ||
| 2342 | ExitOnFailure(hr, "Failed to select overridable variable nodes."); | ||
| 2343 | |||
| 2344 | hr = pNodes->get_length((long*)&cNodes); | ||
| 2345 | ExitOnFailure(hr, "Failed to get overridable variable node count."); | ||
| 2346 | |||
| 2347 | if (cNodes) | ||
| 2348 | { | ||
| 2349 | hr = DictCreateStringList(&m_sdOverridableVariables, 32, DICT_FLAG_NONE); | ||
| 2350 | ExitOnFailure(hr, "Failed to create the string dictionary."); | ||
| 2351 | |||
| 2352 | for (DWORD i = 0; i < cNodes; ++i) | ||
| 2353 | { | ||
| 2354 | hr = XmlNextElement(pNodes, &pNode, NULL); | ||
| 2355 | ExitOnFailure(hr, "Failed to get next node."); | ||
| 2356 | |||
| 2357 | // @Name | ||
| 2358 | hr = XmlGetAttributeEx(pNode, L"Name", &scz); | ||
| 2359 | ExitOnFailure(hr, "Failed to get @Name."); | ||
| 2360 | |||
| 2361 | hr = DictAddKey(m_sdOverridableVariables, scz); | ||
| 2362 | ExitOnFailure(hr, "Failed to add \"%ls\" to the string dictionary.", scz); | ||
| 2363 | |||
| 2364 | // prepare next iteration | ||
| 2365 | ReleaseNullObject(pNode); | ||
| 2366 | } | ||
| 2367 | } | ||
| 2368 | |||
| 2369 | LExit: | ||
| 2370 | ReleaseObject(pNode); | ||
| 2371 | ReleaseObject(pNodes); | ||
| 2372 | ReleaseStr(scz); | ||
| 2373 | return hr; | ||
| 2374 | } | ||
| 2375 | |||
| 2376 | |||
| 2377 | HRESULT InitializePackageInfo() | 2307 | HRESULT InitializePackageInfo() |
| 2378 | { | 2308 | { |
| 2379 | HRESULT hr = S_OK; | 2309 | HRESULT hr = S_OK; |
| @@ -3951,6 +3881,7 @@ public: | |||
| 3951 | 3881 | ||
| 3952 | m_pWixLoc = NULL; | 3882 | m_pWixLoc = NULL; |
| 3953 | memset(&m_Bundle, 0, sizeof(m_Bundle)); | 3883 | memset(&m_Bundle, 0, sizeof(m_Bundle)); |
| 3884 | memset(&m_BalInfoCommand, 0, sizeof(m_BalInfoCommand)); | ||
| 3954 | memset(&m_Conditions, 0, sizeof(m_Conditions)); | 3885 | memset(&m_Conditions, 0, sizeof(m_Conditions)); |
| 3955 | m_sczConfirmCloseMessage = NULL; | 3886 | m_sczConfirmCloseMessage = NULL; |
| 3956 | m_sczFailedMessage = NULL; | 3887 | m_sczFailedMessage = NULL; |
| @@ -3977,7 +3908,6 @@ public: | |||
| 3977 | m_fSuppressRepair = FALSE; | 3908 | m_fSuppressRepair = FALSE; |
| 3978 | m_fSupportCacheOnly = FALSE; | 3909 | m_fSupportCacheOnly = FALSE; |
| 3979 | 3910 | ||
| 3980 | m_sdOverridableVariables = NULL; | ||
| 3981 | m_pTaskbarList = NULL; | 3911 | m_pTaskbarList = NULL; |
| 3982 | m_uTaskbarButtonCreatedMessage = UINT_MAX; | 3912 | m_uTaskbarButtonCreatedMessage = UINT_MAX; |
| 3983 | m_fTaskbarButtonOK = FALSE; | 3913 | m_fTaskbarButtonOK = FALSE; |
| @@ -4013,11 +3943,11 @@ public: | |||
| 4013 | } | 3943 | } |
| 4014 | 3944 | ||
| 4015 | ::DeleteCriticalSection(&m_csShowingInternalUiThisPackage); | 3945 | ::DeleteCriticalSection(&m_csShowingInternalUiThisPackage); |
| 4016 | ReleaseDict(m_sdOverridableVariables); | ||
| 4017 | ReleaseStr(m_sczFailedMessage); | 3946 | ReleaseStr(m_sczFailedMessage); |
| 4018 | ReleaseStr(m_sczConfirmCloseMessage); | 3947 | ReleaseStr(m_sczConfirmCloseMessage); |
| 4019 | BalConditionsUninitialize(&m_Conditions); | 3948 | BalConditionsUninitialize(&m_Conditions); |
| 4020 | BalInfoUninitialize(&m_Bundle); | 3949 | BalInfoUninitialize(&m_Bundle); |
| 3950 | BalInfoUninitializeCommandLine(&m_BalInfoCommand); | ||
| 4021 | LocFree(m_pWixLoc); | 3951 | LocFree(m_pWixLoc); |
| 4022 | 3952 | ||
| 4023 | ReleaseStr(m_sczLanguage); | 3953 | ReleaseStr(m_sczLanguage); |
| @@ -4050,6 +3980,7 @@ private: | |||
| 4050 | 3980 | ||
| 4051 | WIX_LOCALIZATION* m_pWixLoc; | 3981 | WIX_LOCALIZATION* m_pWixLoc; |
| 4052 | BAL_INFO_BUNDLE m_Bundle; | 3982 | BAL_INFO_BUNDLE m_Bundle; |
| 3983 | BAL_INFO_COMMAND m_BalInfoCommand; | ||
| 4053 | BAL_CONDITIONS m_Conditions; | 3984 | BAL_CONDITIONS m_Conditions; |
| 4054 | LPWSTR m_sczFailedMessage; | 3985 | LPWSTR m_sczFailedMessage; |
| 4055 | LPWSTR m_sczConfirmCloseMessage; | 3986 | LPWSTR m_sczConfirmCloseMessage; |
| @@ -4080,8 +4011,6 @@ private: | |||
| 4080 | BOOL m_fSuppressRepair; | 4011 | BOOL m_fSuppressRepair; |
| 4081 | BOOL m_fSupportCacheOnly; | 4012 | BOOL m_fSupportCacheOnly; |
| 4082 | 4013 | ||
| 4083 | STRINGDICT_HANDLE m_sdOverridableVariables; | ||
| 4084 | |||
| 4085 | BOOL m_fPrereq; | 4014 | BOOL m_fPrereq; |
| 4086 | BOOL m_fPrereqInstalled; | 4015 | BOOL m_fPrereqInstalled; |
| 4087 | BOOL m_fPrereqAlreadyInstalled; | 4016 | BOOL m_fPrereqAlreadyInstalled; |
