diff options
Diffstat (limited to 'src/engine/EngineForExtension.cpp')
-rw-r--r-- | src/engine/EngineForExtension.cpp | 405 |
1 files changed, 405 insertions, 0 deletions
diff --git a/src/engine/EngineForExtension.cpp b/src/engine/EngineForExtension.cpp new file mode 100644 index 00000000..9667dd18 --- /dev/null +++ b/src/engine/EngineForExtension.cpp | |||
@@ -0,0 +1,405 @@ | |||
1 | // 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. | ||
2 | |||
3 | #include "precomp.h" | ||
4 | |||
5 | static HRESULT BEEngineEscapeString( | ||
6 | __in BURN_EXTENSION_ENGINE_CONTEXT* /*pContext*/, | ||
7 | __in BUNDLE_EXTENSION_ENGINE_ESCAPESTRING_ARGS* pArgs, | ||
8 | __in BUNDLE_EXTENSION_ENGINE_ESCAPESTRING_RESULTS* pResults | ||
9 | ) | ||
10 | { | ||
11 | HRESULT hr = S_OK; | ||
12 | LPWSTR sczValue = NULL; | ||
13 | size_t cchRemaining = 0; | ||
14 | LPCWSTR wzIn = pArgs->wzIn; | ||
15 | LPWSTR wzOut = pResults->wzOut; | ||
16 | DWORD* pcchOut = &pResults->cchOut; | ||
17 | |||
18 | if (wzIn && *wzIn) | ||
19 | { | ||
20 | hr = VariableEscapeString(wzIn, &sczValue); | ||
21 | if (SUCCEEDED(hr)) | ||
22 | { | ||
23 | if (wzOut) | ||
24 | { | ||
25 | hr = ::StringCchCopyExW(wzOut, *pcchOut, sczValue, NULL, &cchRemaining, STRSAFE_FILL_BEHIND_NULL); | ||
26 | if (STRSAFE_E_INSUFFICIENT_BUFFER == hr) | ||
27 | { | ||
28 | hr = E_MOREDATA; | ||
29 | ::StringCchLengthW(sczValue, STRSAFE_MAX_CCH, &cchRemaining); | ||
30 | *pcchOut = cchRemaining; | ||
31 | } | ||
32 | } | ||
33 | else | ||
34 | { | ||
35 | ::StringCchLengthW(sczValue, STRSAFE_MAX_CCH, &cchRemaining); | ||
36 | *pcchOut = cchRemaining; | ||
37 | } | ||
38 | } | ||
39 | } | ||
40 | else | ||
41 | { | ||
42 | hr = E_INVALIDARG; | ||
43 | } | ||
44 | |||
45 | StrSecureZeroFreeString(sczValue); | ||
46 | return hr; | ||
47 | } | ||
48 | |||
49 | static HRESULT BEEngineEvaluateCondition( | ||
50 | __in BURN_EXTENSION_ENGINE_CONTEXT* pContext, | ||
51 | __in BUNDLE_EXTENSION_ENGINE_EVALUATECONDITION_ARGS* pArgs, | ||
52 | __in BUNDLE_EXTENSION_ENGINE_EVALUATECONDITION_RESULTS* pResults | ||
53 | ) | ||
54 | { | ||
55 | HRESULT hr = S_OK; | ||
56 | LPCWSTR wzCondition = pArgs->wzCondition; | ||
57 | BOOL* pf = &pResults->f; | ||
58 | |||
59 | if (wzCondition && *wzCondition) | ||
60 | { | ||
61 | hr = ConditionEvaluate(&pContext->pEngineState->variables, wzCondition, pf); | ||
62 | } | ||
63 | else | ||
64 | { | ||
65 | hr = E_INVALIDARG; | ||
66 | } | ||
67 | |||
68 | return hr; | ||
69 | } | ||
70 | |||
71 | static HRESULT BEEngineFormatString( | ||
72 | __in BURN_EXTENSION_ENGINE_CONTEXT* pContext, | ||
73 | __in BUNDLE_EXTENSION_ENGINE_FORMATSTRING_ARGS* pArgs, | ||
74 | __in BUNDLE_EXTENSION_ENGINE_FORMATSTRING_RESULTS* pResults | ||
75 | ) | ||
76 | { | ||
77 | HRESULT hr = S_OK; | ||
78 | LPWSTR sczValue = NULL; | ||
79 | DWORD cchValue = 0; | ||
80 | LPCWSTR wzIn = pArgs->wzIn; | ||
81 | LPWSTR wzOut = pResults->wzOut; | ||
82 | DWORD* pcchOut = &pResults->cchOut; | ||
83 | |||
84 | if (wzIn && *wzIn) | ||
85 | { | ||
86 | hr = VariableFormatString(&pContext->pEngineState->variables, wzIn, &sczValue, &cchValue); | ||
87 | if (SUCCEEDED(hr)) | ||
88 | { | ||
89 | if (wzOut) | ||
90 | { | ||
91 | hr = ::StringCchCopyExW(wzOut, *pcchOut, sczValue, NULL, NULL, STRSAFE_FILL_BEHIND_NULL); | ||
92 | if (FAILED(hr)) | ||
93 | { | ||
94 | *pcchOut = cchValue; | ||
95 | if (STRSAFE_E_INSUFFICIENT_BUFFER == hr) | ||
96 | { | ||
97 | hr = E_MOREDATA; | ||
98 | } | ||
99 | } | ||
100 | } | ||
101 | else | ||
102 | { | ||
103 | hr = E_MOREDATA; | ||
104 | *pcchOut = cchValue; | ||
105 | } | ||
106 | } | ||
107 | } | ||
108 | else | ||
109 | { | ||
110 | hr = E_INVALIDARG; | ||
111 | } | ||
112 | |||
113 | StrSecureZeroFreeString(sczValue); | ||
114 | return hr; | ||
115 | } | ||
116 | |||
117 | static HRESULT BEEngineGetVariableNumeric( | ||
118 | __in BURN_EXTENSION_ENGINE_CONTEXT* pContext, | ||
119 | __in BUNDLE_EXTENSION_ENGINE_GETVARIABLENUMERIC_ARGS* pArgs, | ||
120 | __in BUNDLE_EXTENSION_ENGINE_GETVARIABLENUMERIC_RESULTS* pResults | ||
121 | ) | ||
122 | { | ||
123 | HRESULT hr = S_OK; | ||
124 | LPCWSTR wzVariable = pArgs->wzVariable; | ||
125 | LONGLONG* pllValue = &pResults->llValue; | ||
126 | |||
127 | if (wzVariable && *wzVariable) | ||
128 | { | ||
129 | hr = VariableGetNumeric(&pContext->pEngineState->variables, wzVariable, pllValue); | ||
130 | } | ||
131 | else | ||
132 | { | ||
133 | hr = E_INVALIDARG; | ||
134 | } | ||
135 | |||
136 | return hr; | ||
137 | } | ||
138 | |||
139 | static HRESULT BEEngineGetVariableString( | ||
140 | __in BURN_EXTENSION_ENGINE_CONTEXT* pContext, | ||
141 | __in BUNDLE_EXTENSION_ENGINE_GETVARIABLESTRING_ARGS* pArgs, | ||
142 | __in BUNDLE_EXTENSION_ENGINE_GETVARIABLESTRING_RESULTS* pResults | ||
143 | ) | ||
144 | { | ||
145 | HRESULT hr = S_OK; | ||
146 | LPWSTR sczValue = NULL; | ||
147 | size_t cchRemaining = 0; | ||
148 | LPCWSTR wzVariable = pArgs->wzVariable; | ||
149 | LPWSTR wzValue = pResults->wzValue; | ||
150 | DWORD* pcchValue = &pResults->cchValue; | ||
151 | |||
152 | if (wzVariable && *wzVariable) | ||
153 | { | ||
154 | hr = VariableGetString(&pContext->pEngineState->variables, wzVariable, &sczValue); | ||
155 | if (SUCCEEDED(hr)) | ||
156 | { | ||
157 | if (wzValue) | ||
158 | { | ||
159 | hr = ::StringCchCopyExW(wzValue, *pcchValue, sczValue, NULL, &cchRemaining, STRSAFE_FILL_BEHIND_NULL); | ||
160 | if (STRSAFE_E_INSUFFICIENT_BUFFER == hr) | ||
161 | { | ||
162 | hr = E_MOREDATA; | ||
163 | |||
164 | ::StringCchLengthW(sczValue, STRSAFE_MAX_CCH, &cchRemaining); | ||
165 | *pcchValue = cchRemaining + 1; | ||
166 | } | ||
167 | } | ||
168 | else | ||
169 | { | ||
170 | hr = E_MOREDATA; | ||
171 | |||
172 | ::StringCchLengthW(sczValue, STRSAFE_MAX_CCH, &cchRemaining); | ||
173 | *pcchValue = cchRemaining + 1; | ||
174 | } | ||
175 | } | ||
176 | } | ||
177 | else | ||
178 | { | ||
179 | hr = E_INVALIDARG; | ||
180 | } | ||
181 | |||
182 | StrSecureZeroFreeString(sczValue); | ||
183 | return hr; | ||
184 | } | ||
185 | |||
186 | static HRESULT BEEngineGetVariableVersion( | ||
187 | __in BURN_EXTENSION_ENGINE_CONTEXT* pContext, | ||
188 | __in BUNDLE_EXTENSION_ENGINE_GETVARIABLEVERSION_ARGS* pArgs, | ||
189 | __in BUNDLE_EXTENSION_ENGINE_GETVARIABLEVERSION_RESULTS* pResults | ||
190 | ) | ||
191 | { | ||
192 | HRESULT hr = S_OK; | ||
193 | LPCWSTR wzVariable = pArgs->wzVariable; | ||
194 | DWORD64* pqwValue = &pResults->qwValue; | ||
195 | |||
196 | if (wzVariable && *wzVariable) | ||
197 | { | ||
198 | hr = VariableGetVersion(&pContext->pEngineState->variables, wzVariable, pqwValue); | ||
199 | } | ||
200 | else | ||
201 | { | ||
202 | hr = E_INVALIDARG; | ||
203 | } | ||
204 | |||
205 | return hr; | ||
206 | } | ||
207 | |||
208 | static HRESULT BEEngineLog( | ||
209 | __in BURN_EXTENSION_ENGINE_CONTEXT* /*pContext*/, | ||
210 | __in BUNDLE_EXTENSION_ENGINE_LOG_ARGS* pArgs, | ||
211 | __in BUNDLE_EXTENSION_ENGINE_LOG_RESULTS* /*pResults*/ | ||
212 | ) | ||
213 | { | ||
214 | HRESULT hr = S_OK; | ||
215 | REPORT_LEVEL rl = REPORT_NONE; | ||
216 | BUNDLE_EXTENSION_LOG_LEVEL level = pArgs->level; | ||
217 | LPCWSTR wzMessage = pArgs->wzMessage; | ||
218 | |||
219 | switch (level) | ||
220 | { | ||
221 | case BUNDLE_EXTENSION_LOG_LEVEL_STANDARD: | ||
222 | rl = REPORT_STANDARD; | ||
223 | break; | ||
224 | |||
225 | case BUNDLE_EXTENSION_LOG_LEVEL_VERBOSE: | ||
226 | rl = REPORT_VERBOSE; | ||
227 | break; | ||
228 | |||
229 | case BUNDLE_EXTENSION_LOG_LEVEL_DEBUG: | ||
230 | rl = REPORT_DEBUG; | ||
231 | break; | ||
232 | |||
233 | case BUNDLE_EXTENSION_LOG_LEVEL_ERROR: | ||
234 | rl = REPORT_ERROR; | ||
235 | break; | ||
236 | |||
237 | default: | ||
238 | ExitFunction1(hr = E_INVALIDARG); | ||
239 | } | ||
240 | |||
241 | hr = LogStringLine(rl, "%ls", wzMessage); | ||
242 | ExitOnFailure(hr, "Failed to log Bundle Extension message."); | ||
243 | |||
244 | LExit: | ||
245 | return hr; | ||
246 | } | ||
247 | |||
248 | static HRESULT BEEngineSetVariableLiteralString( | ||
249 | __in BURN_EXTENSION_ENGINE_CONTEXT* pContext, | ||
250 | __in const BUNDLE_EXTENSION_ENGINE_SETVARIABLELITERALSTRING_ARGS* pArgs, | ||
251 | __in BUNDLE_EXTENSION_ENGINE_SETVARIABLELITERALSTRING_RESULTS* /*pResults*/ | ||
252 | ) | ||
253 | { | ||
254 | HRESULT hr = S_OK; | ||
255 | LPCWSTR wzVariable = pArgs->wzVariable; | ||
256 | LPCWSTR wzValue = pArgs->wzValue; | ||
257 | |||
258 | if (wzVariable && *wzVariable) | ||
259 | { | ||
260 | hr = VariableSetLiteralString(&pContext->pEngineState->variables, wzVariable, wzValue, FALSE); | ||
261 | ExitOnFailure(hr, "Failed to set literal string variable."); | ||
262 | } | ||
263 | else | ||
264 | { | ||
265 | hr = E_INVALIDARG; | ||
266 | ExitOnFailure(hr, "Bundle Extension did not provide variable name."); | ||
267 | } | ||
268 | |||
269 | LExit: | ||
270 | return hr; | ||
271 | } | ||
272 | |||
273 | static HRESULT BEEngineSetVariableNumeric( | ||
274 | __in BURN_EXTENSION_ENGINE_CONTEXT* pContext, | ||
275 | __in const BUNDLE_EXTENSION_ENGINE_SETVARIABLENUMERIC_ARGS* pArgs, | ||
276 | __in BUNDLE_EXTENSION_ENGINE_SETVARIABLENUMERIC_RESULTS* /*pResults*/ | ||
277 | ) | ||
278 | { | ||
279 | HRESULT hr = S_OK; | ||
280 | LPCWSTR wzVariable = pArgs->wzVariable; | ||
281 | LONGLONG llValue = pArgs->llValue; | ||
282 | |||
283 | if (wzVariable && *wzVariable) | ||
284 | { | ||
285 | hr = VariableSetNumeric(&pContext->pEngineState->variables, wzVariable, llValue, FALSE); | ||
286 | ExitOnFailure(hr, "Failed to set numeric variable."); | ||
287 | } | ||
288 | else | ||
289 | { | ||
290 | hr = E_INVALIDARG; | ||
291 | ExitOnFailure(hr, "Bundle Extension did not provide variable name."); | ||
292 | } | ||
293 | |||
294 | LExit: | ||
295 | return hr; | ||
296 | } | ||
297 | |||
298 | static HRESULT BEEngineSetVariableString( | ||
299 | __in BURN_EXTENSION_ENGINE_CONTEXT* pContext, | ||
300 | __in const BUNDLE_EXTENSION_ENGINE_SETVARIABLESTRING_ARGS* pArgs, | ||
301 | __in BUNDLE_EXTENSION_ENGINE_SETVARIABLESTRING_RESULTS* /*pResults*/ | ||
302 | ) | ||
303 | { | ||
304 | HRESULT hr = S_OK; | ||
305 | LPCWSTR wzVariable = pArgs->wzVariable; | ||
306 | LPCWSTR wzValue = pArgs->wzValue; | ||
307 | |||
308 | if (wzVariable && *wzVariable) | ||
309 | { | ||
310 | hr = VariableSetString(&pContext->pEngineState->variables, wzVariable, wzValue, FALSE); | ||
311 | ExitOnFailure(hr, "Failed to set string variable."); | ||
312 | } | ||
313 | else | ||
314 | { | ||
315 | hr = E_INVALIDARG; | ||
316 | ExitOnFailure(hr, "Bundle Extension did not provide variable name."); | ||
317 | } | ||
318 | |||
319 | LExit: | ||
320 | return hr; | ||
321 | } | ||
322 | |||
323 | static HRESULT BEEngineSetVariableVersion( | ||
324 | __in BURN_EXTENSION_ENGINE_CONTEXT* pContext, | ||
325 | __in const BUNDLE_EXTENSION_ENGINE_SETVARIABLEVERSION_ARGS* pArgs, | ||
326 | __in BUNDLE_EXTENSION_ENGINE_SETVARIABLEVERSION_RESULTS* /*pResults*/ | ||
327 | ) | ||
328 | { | ||
329 | HRESULT hr = S_OK; | ||
330 | LPCWSTR wzVariable = pArgs->wzVariable; | ||
331 | DWORD64 qwValue = pArgs->qwValue; | ||
332 | |||
333 | if (wzVariable && *wzVariable) | ||
334 | { | ||
335 | hr = VariableSetVersion(&pContext->pEngineState->variables, wzVariable, qwValue, FALSE); | ||
336 | ExitOnFailure(hr, "Failed to set version variable."); | ||
337 | } | ||
338 | else | ||
339 | { | ||
340 | hr = E_INVALIDARG; | ||
341 | ExitOnFailure(hr, "Bundle Extension did not provide variable name."); | ||
342 | } | ||
343 | |||
344 | LExit: | ||
345 | return hr; | ||
346 | } | ||
347 | |||
348 | HRESULT WINAPI EngineForExtensionProc( | ||
349 | __in BUNDLE_EXTENSION_ENGINE_MESSAGE message, | ||
350 | __in const LPVOID pvArgs, | ||
351 | __inout LPVOID pvResults, | ||
352 | __in_opt LPVOID pvContext | ||
353 | ) | ||
354 | { | ||
355 | HRESULT hr = S_OK; | ||
356 | BURN_EXTENSION_ENGINE_CONTEXT* pContext = reinterpret_cast<BURN_EXTENSION_ENGINE_CONTEXT*>(pvContext); | ||
357 | |||
358 | if (!pContext || !pvArgs || !pvResults) | ||
359 | { | ||
360 | ExitFunction1(hr = E_INVALIDARG); | ||
361 | } | ||
362 | |||
363 | switch (message) | ||
364 | { | ||
365 | case BUNDLE_EXTENSION_ENGINE_MESSAGE_ESCAPESTRING: | ||
366 | hr = BEEngineEscapeString(pContext, reinterpret_cast<BUNDLE_EXTENSION_ENGINE_ESCAPESTRING_ARGS*>(pvArgs), reinterpret_cast<BUNDLE_EXTENSION_ENGINE_ESCAPESTRING_RESULTS*>(pvResults)); | ||
367 | break; | ||
368 | case BUNDLE_EXTENSION_ENGINE_MESSAGE_EVALUATECONDITION: | ||
369 | hr = BEEngineEvaluateCondition(pContext, reinterpret_cast<BUNDLE_EXTENSION_ENGINE_EVALUATECONDITION_ARGS*>(pvArgs), reinterpret_cast<BUNDLE_EXTENSION_ENGINE_EVALUATECONDITION_RESULTS*>(pvResults)); | ||
370 | break; | ||
371 | case BUNDLE_EXTENSION_ENGINE_MESSAGE_FORMATSTRING: | ||
372 | hr = BEEngineFormatString(pContext, reinterpret_cast<BUNDLE_EXTENSION_ENGINE_FORMATSTRING_ARGS*>(pvArgs), reinterpret_cast<BUNDLE_EXTENSION_ENGINE_FORMATSTRING_RESULTS*>(pvResults)); | ||
373 | break; | ||
374 | case BUNDLE_EXTENSION_ENGINE_MESSAGE_GETVARIABLENUMERIC: | ||
375 | hr = BEEngineGetVariableNumeric(pContext, reinterpret_cast<BUNDLE_EXTENSION_ENGINE_GETVARIABLENUMERIC_ARGS*>(pvArgs), reinterpret_cast<BUNDLE_EXTENSION_ENGINE_GETVARIABLENUMERIC_RESULTS*>(pvResults)); | ||
376 | break; | ||
377 | case BUNDLE_EXTENSION_ENGINE_MESSAGE_GETVARIABLESTRING: | ||
378 | hr = BEEngineGetVariableString(pContext, reinterpret_cast<BUNDLE_EXTENSION_ENGINE_GETVARIABLESTRING_ARGS*>(pvArgs), reinterpret_cast<BUNDLE_EXTENSION_ENGINE_GETVARIABLESTRING_RESULTS*>(pvResults)); | ||
379 | break; | ||
380 | case BUNDLE_EXTENSION_ENGINE_MESSAGE_GETVARIABLEVERSION: | ||
381 | hr = BEEngineGetVariableVersion(pContext, reinterpret_cast<BUNDLE_EXTENSION_ENGINE_GETVARIABLEVERSION_ARGS*>(pvArgs), reinterpret_cast<BUNDLE_EXTENSION_ENGINE_GETVARIABLEVERSION_RESULTS*>(pvResults)); | ||
382 | break; | ||
383 | case BUNDLE_EXTENSION_ENGINE_MESSAGE_LOG: | ||
384 | hr = BEEngineLog(pContext, reinterpret_cast<BUNDLE_EXTENSION_ENGINE_LOG_ARGS*>(pvArgs), reinterpret_cast<BUNDLE_EXTENSION_ENGINE_LOG_RESULTS*>(pvResults)); | ||
385 | break; | ||
386 | case BUNDLE_EXTENSION_ENGINE_MESSAGE_SETVARIABLELITERALSTRING: | ||
387 | hr = BEEngineSetVariableLiteralString(pContext, reinterpret_cast<BUNDLE_EXTENSION_ENGINE_SETVARIABLELITERALSTRING_ARGS*>(pvArgs), reinterpret_cast<BUNDLE_EXTENSION_ENGINE_SETVARIABLELITERALSTRING_RESULTS*>(pvResults)); | ||
388 | break; | ||
389 | case BUNDLE_EXTENSION_ENGINE_MESSAGE_SETVARIABLENUMERIC: | ||
390 | hr = BEEngineSetVariableNumeric(pContext, reinterpret_cast<BUNDLE_EXTENSION_ENGINE_SETVARIABLENUMERIC_ARGS*>(pvArgs), reinterpret_cast<BUNDLE_EXTENSION_ENGINE_SETVARIABLENUMERIC_RESULTS*>(pvResults)); | ||
391 | break; | ||
392 | case BUNDLE_EXTENSION_ENGINE_MESSAGE_SETVARIABLESTRING: | ||
393 | hr = BEEngineSetVariableString(pContext, reinterpret_cast<BUNDLE_EXTENSION_ENGINE_SETVARIABLESTRING_ARGS*>(pvArgs), reinterpret_cast<BUNDLE_EXTENSION_ENGINE_SETVARIABLESTRING_RESULTS*>(pvResults)); | ||
394 | break; | ||
395 | case BUNDLE_EXTENSION_ENGINE_MESSAGE_SETVARIABLEVERSION: | ||
396 | hr = BEEngineSetVariableVersion(pContext, reinterpret_cast<BUNDLE_EXTENSION_ENGINE_SETVARIABLEVERSION_ARGS*>(pvArgs), reinterpret_cast<BUNDLE_EXTENSION_ENGINE_SETVARIABLEVERSION_RESULTS*>(pvResults)); | ||
397 | break; | ||
398 | default: | ||
399 | hr = E_NOTIMPL; | ||
400 | break; | ||
401 | } | ||
402 | |||
403 | LExit: | ||
404 | return hr; | ||
405 | } | ||