aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorSean Hall <r.sean.hall@gmail.com>2020-04-06 12:30:56 +1000
committerSean Hall <r.sean.hall@gmail.com>2020-04-06 14:23:09 +1000
commit18752ee7da742d0219e7b882315e03ad888f5725 (patch)
treef52b7b8be007f2e6c880666e10e4eee3ab0d5835 /src
parent9969392ff7024d2f1e257c2f6c5ce31fa0e839d3 (diff)
downloadwix-18752ee7da742d0219e7b882315e03ad888f5725.tar.gz
wix-18752ee7da742d0219e7b882315e03ad888f5725.tar.bz2
wix-18752ee7da742d0219e7b882315e03ad888f5725.zip
Modernize BalCompiler and BalBurnBackendExtension.
Diffstat (limited to 'src')
-rw-r--r--src/test/WixToolsetTest.Bal/BalExtensionFixture.cs5
-rw-r--r--src/wixext/BalBurnBackendExtension.cs71
-rw-r--r--src/wixext/BalCompiler.cs203
3 files changed, 150 insertions, 129 deletions
diff --git a/src/test/WixToolsetTest.Bal/BalExtensionFixture.cs b/src/test/WixToolsetTest.Bal/BalExtensionFixture.cs
index 06727afd..e798063e 100644
--- a/src/test/WixToolsetTest.Bal/BalExtensionFixture.cs
+++ b/src/test/WixToolsetTest.Bal/BalExtensionFixture.cs
@@ -3,6 +3,7 @@
3namespace WixToolsetTest.Bal 3namespace WixToolsetTest.Bal
4{ 4{
5 using System.IO; 5 using System.IO;
6 using System.Linq;
6 using WixBuildTools.TestSupport; 7 using WixBuildTools.TestSupport;
7 using WixToolset.Core.TestPackage; 8 using WixToolset.Core.TestPackage;
8 using Xunit; 9 using Xunit;
@@ -29,6 +30,10 @@ namespace WixToolsetTest.Bal
29 "-o", bundleFile, 30 "-o", bundleFile,
30 }); 31 });
31 compileResult.AssertSuccess(); 32 compileResult.AssertSuccess();
33 Assert.Equal(new[]
34 {
35 "BurnBackend didn't provide Wixout so skipping BalExtension PostBind verification."
36 }, compileResult.Messages.Select(x => x.ToString()).ToArray());
32 37
33 Assert.True(File.Exists(bundleFile)); 38 Assert.True(File.Exists(bundleFile));
34 } 39 }
diff --git a/src/wixext/BalBurnBackendExtension.cs b/src/wixext/BalBurnBackendExtension.cs
index 20609964..e1082889 100644
--- a/src/wixext/BalBurnBackendExtension.cs
+++ b/src/wixext/BalBurnBackendExtension.cs
@@ -4,10 +4,10 @@ namespace WixToolset.Bal
4{ 4{
5 using System; 5 using System;
6 using System.Linq; 6 using System.Linq;
7 using WixToolset.Bal.Tuples;
7 using WixToolset.Data; 8 using WixToolset.Data;
8 using WixToolset.Data.Burn; 9 using WixToolset.Data.Burn;
9 using WixToolset.Data.WindowsInstaller; 10 using WixToolset.Data.Tuples;
10 using WixToolset.Data.WindowsInstaller.Rows;
11 using WixToolset.Extensibility; 11 using WixToolset.Extensibility;
12 using WixToolset.Extensibility.Data; 12 using WixToolset.Extensibility.Data;
13 13
@@ -17,17 +17,17 @@ namespace WixToolset.Bal
17 { 17 {
18 base.PostBackendBind(result); 18 base.PostBackendBind(result);
19 19
20 var output = WindowsInstallerData.Load(result.Wixout, false); 20 if (result.Wixout == null)
21
22 // Only process Bundles.
23 if (OutputType.Bundle != output.Type)
24 { 21 {
22 this.Messaging.Write(new Message(null, MessageLevel.Warning, 1, "BurnBackend didn't provide Wixout so skipping BalExtension PostBind verification."));
25 return; 23 return;
26 } 24 }
27 25
28 var baTable = output.Tables["WixBootstrapperApplication"]; 26 var intermediate = Intermediate.Load(result.Wixout);
29 var baRow = baTable.Rows[0]; 27 var section = intermediate.Sections.Single();
30 var baId = (string)baRow[0]; 28
29 var baTuple = section.Tuples.OfType<WixBootstrapperApplicationTuple>().SingleOrDefault();
30 var baId = baTuple?.Id?.Id;
31 if (null == baId) 31 if (null == baId)
32 { 32 {
33 return; 33 return;
@@ -38,60 +38,57 @@ namespace WixToolset.Bal
38 38
39 if (isStdBA || isMBA) 39 if (isStdBA || isMBA)
40 { 40 {
41 this.VerifyBAFunctions(output); 41 this.VerifyBAFunctions(section);
42 } 42 }
43 43
44 if (isMBA) 44 if (isMBA)
45 { 45 {
46 this.VerifyPrereqPackages(output); 46 this.VerifyPrereqPackages(section);
47 } 47 }
48 } 48 }
49 49
50 private void VerifyBAFunctions(WindowsInstallerData output) 50 private void VerifyBAFunctions(IntermediateSection section)
51 { 51 {
52 Row baFunctionsRow = null; 52 WixBalBAFunctionsTuple baFunctionsTuple = null;
53 var baFunctionsTable = output.Tables["WixBalBAFunctions"]; 53 foreach (var tuple in section.Tuples.OfType<WixBalBAFunctionsTuple>())
54 foreach (var row in baFunctionsTable.Rows)
55 { 54 {
56 if (null == baFunctionsRow) 55 if (null == baFunctionsTuple)
57 { 56 {
58 baFunctionsRow = row; 57 baFunctionsTuple = tuple;
59 } 58 }
60 else 59 else
61 { 60 {
62 this.Messaging.Write(BalErrors.MultipleBAFunctions(row.SourceLineNumbers)); 61 this.Messaging.Write(BalErrors.MultipleBAFunctions(tuple.SourceLineNumbers));
63 } 62 }
64 } 63 }
65 64
66 var payloadPropertiesTable = output.Tables["WixPayloadProperties"]; 65 var payloadPropertiesTuples = section.Tuples.OfType<WixBundlePayloadTuple>().ToList();
67 var payloadPropertiesRows = payloadPropertiesTable.Rows.Cast<WixPayloadPropertiesRow>(); 66 if (null == baFunctionsTuple)
68 if (null == baFunctionsRow)
69 { 67 {
70 foreach (var payloadPropertiesRow in payloadPropertiesRows) 68 foreach (var payloadPropertiesTuple in payloadPropertiesTuples)
71 { 69 {
72 // TODO: Make core WiX canonicalize Name (this won't catch '.\bafunctions.dll'). 70 // TODO: Make core WiX canonicalize Name (this won't catch '.\bafunctions.dll').
73 if (string.Equals(payloadPropertiesRow.Name, "bafunctions.dll", StringComparison.OrdinalIgnoreCase)) 71 if (string.Equals(payloadPropertiesTuple.Name, "bafunctions.dll", StringComparison.OrdinalIgnoreCase))
74 { 72 {
75 this.Messaging.Write(BalWarnings.UnmarkedBAFunctionsDLL(payloadPropertiesRow.SourceLineNumbers)); 73 this.Messaging.Write(BalWarnings.UnmarkedBAFunctionsDLL(payloadPropertiesTuple.SourceLineNumbers));
76 } 74 }
77 } 75 }
78 } 76 }
79 else 77 else
80 { 78 {
81 // TODO: May need to revisit this depending on the outcome of #5273. 79 var payloadId = baFunctionsTuple.Id;
82 var payloadId = (string)baFunctionsRow[0]; 80 var bundlePayloadTuple = payloadPropertiesTuples.Single(x => payloadId == x.Id);
83 var bundlePayloadRow = payloadPropertiesRows.Single(x => payloadId == x.Id); 81 if (BurnConstants.BurnUXContainerName != bundlePayloadTuple.ContainerRef)
84 if (BurnConstants.BurnUXContainerName != bundlePayloadRow.Container)
85 { 82 {
86 this.Messaging.Write(BalErrors.BAFunctionsPayloadRequiredInUXContainer(baFunctionsRow.SourceLineNumbers)); 83 this.Messaging.Write(BalErrors.BAFunctionsPayloadRequiredInUXContainer(baFunctionsTuple.SourceLineNumbers));
87 } 84 }
88 } 85 }
89 } 86 }
90 87
91 private void VerifyPrereqPackages(WindowsInstallerData output) 88 private void VerifyPrereqPackages(IntermediateSection section)
92 { 89 {
93 var prereqInfoTable = output.Tables["WixMbaPrereqInformation"]; 90 var prereqInfoTuples = section.Tuples.OfType<WixMbaPrereqInformationTuple>().ToList();
94 if (null == prereqInfoTable || prereqInfoTable.Rows.Count == 0) 91 if (prereqInfoTuples.Count == 0)
95 { 92 {
96 this.Messaging.Write(BalErrors.MissingPrereq()); 93 this.Messaging.Write(BalErrors.MissingPrereq());
97 return; 94 return;
@@ -100,24 +97,24 @@ namespace WixToolset.Bal
100 var foundLicenseFile = false; 97 var foundLicenseFile = false;
101 var foundLicenseUrl = false; 98 var foundLicenseUrl = false;
102 99
103 foreach (Row prereqInfoRow in prereqInfoTable.Rows) 100 foreach (var prereqInfoTuple in prereqInfoTuples)
104 { 101 {
105 if (null != prereqInfoRow[1]) 102 if (null != prereqInfoTuple.LicenseFile)
106 { 103 {
107 if (foundLicenseFile || foundLicenseUrl) 104 if (foundLicenseFile || foundLicenseUrl)
108 { 105 {
109 this.Messaging.Write(BalErrors.MultiplePrereqLicenses(prereqInfoRow.SourceLineNumbers)); 106 this.Messaging.Write(BalErrors.MultiplePrereqLicenses(prereqInfoTuple.SourceLineNumbers));
110 return; 107 return;
111 } 108 }
112 109
113 foundLicenseFile = true; 110 foundLicenseFile = true;
114 } 111 }
115 112
116 if (null != prereqInfoRow[2]) 113 if (null != prereqInfoTuple.LicenseUrl)
117 { 114 {
118 if (foundLicenseFile || foundLicenseUrl) 115 if (foundLicenseFile || foundLicenseUrl)
119 { 116 {
120 this.Messaging.Write(BalErrors.MultiplePrereqLicenses(prereqInfoRow.SourceLineNumbers)); 117 this.Messaging.Write(BalErrors.MultiplePrereqLicenses(prereqInfoTuple.SourceLineNumbers));
121 return; 118 return;
122 } 119 }
123 120
diff --git a/src/wixext/BalCompiler.cs b/src/wixext/BalCompiler.cs
index c9b232ba..c291d41f 100644
--- a/src/wixext/BalCompiler.cs
+++ b/src/wixext/BalCompiler.cs
@@ -15,16 +15,14 @@ namespace WixToolset.Bal
15 /// </summary> 15 /// </summary>
16 public sealed class BalCompiler : BaseCompilerExtension 16 public sealed class BalCompiler : BaseCompilerExtension
17 { 17 {
18 private SourceLineNumber addedConditionLineNumber; 18 private readonly Dictionary<string, WixMbaPrereqInformationTuple> prereqInfoTuplesByPackageId;
19 private Dictionary<string, WixMbaPrereqInformationTuple> prereqInfoRows;
20 19
21 /// <summary> 20 /// <summary>
22 /// Instantiate a new BalCompiler. 21 /// Instantiate a new BalCompiler.
23 /// </summary> 22 /// </summary>
24 public BalCompiler() 23 public BalCompiler()
25 { 24 {
26 this.addedConditionLineNumber = null; 25 this.prereqInfoTuplesByPackageId = new Dictionary<string, WixMbaPrereqInformationTuple>();
27 this.prereqInfoRows = new Dictionary<string, WixMbaPrereqInformationTuple>();
28 } 26 }
29 27
30 public override XNamespace Namespace => "http://wixtoolset.org/schemas/v4/wxs/bal"; 28 public override XNamespace Namespace => "http://wixtoolset.org/schemas/v4/wxs/bal";
@@ -82,7 +80,7 @@ namespace WixToolset.Bal
82 /// <param name="context">Extra information about the context in which this element is being parsed.</param> 80 /// <param name="context">Extra information about the context in which this element is being parsed.</param>
83 public override void ParseAttribute(Intermediate intermediate, IntermediateSection section, XElement parentElement, XAttribute attribute, IDictionary<string, string> context) 81 public override void ParseAttribute(Intermediate intermediate, IntermediateSection section, XElement parentElement, XAttribute attribute, IDictionary<string, string> context)
84 { 82 {
85 SourceLineNumber sourceLineNumbers = this.ParseHelper.GetSourceLineNumbers(parentElement); 83 var sourceLineNumbers = this.ParseHelper.GetSourceLineNumbers(parentElement);
86 WixMbaPrereqInformationTuple prereqInfo; 84 WixMbaPrereqInformationTuple prereqInfo;
87 85
88 switch (parentElement.Name.LocalName) 86 switch (parentElement.Name.LocalName)
@@ -102,18 +100,20 @@ namespace WixToolset.Bal
102 { 100 {
103 case "PrereqLicenseFile": 101 case "PrereqLicenseFile":
104 102
105 if (!this.prereqInfoRows.TryGetValue(packageId, out prereqInfo)) 103 if (!this.prereqInfoTuplesByPackageId.TryGetValue(packageId, out prereqInfo))
106 { 104 {
107 // at the time the extension attribute is parsed, the compiler might not yet have 105 // at the time the extension attribute is parsed, the compiler might not yet have
108 // parsed the PrereqPackage attribute, so we need to get it directly from the parent element. 106 // parsed the PrereqPackage attribute, so we need to get it directly from the parent element.
109 XAttribute prereqPackage = parentElement.Attribute(this.Namespace + "PrereqPackage"); 107 var prereqPackage = parentElement.Attribute(this.Namespace + "PrereqPackage");
110 108
111 if (null != prereqPackage && YesNoType.Yes == this.ParseHelper.GetAttributeYesNoValue(sourceLineNumbers, prereqPackage)) 109 if (null != prereqPackage && YesNoType.Yes == this.ParseHelper.GetAttributeYesNoValue(sourceLineNumbers, prereqPackage))
112 { 110 {
113 prereqInfo = (WixMbaPrereqInformationTuple)this.ParseHelper.CreateTuple(section, sourceLineNumbers, "WixMbaPrereqInformation"); 111 prereqInfo = section.AddTuple(new WixMbaPrereqInformationTuple(sourceLineNumbers)
114 prereqInfo.PackageId = packageId; 112 {
113 PackageId = packageId,
114 });
115 115
116 this.prereqInfoRows.Add(packageId, prereqInfo); 116 this.prereqInfoTuplesByPackageId.Add(packageId, prereqInfo);
117 } 117 }
118 else 118 else
119 { 119 {
@@ -133,18 +133,20 @@ namespace WixToolset.Bal
133 break; 133 break;
134 case "PrereqLicenseUrl": 134 case "PrereqLicenseUrl":
135 135
136 if (!this.prereqInfoRows.TryGetValue(packageId, out prereqInfo)) 136 if (!this.prereqInfoTuplesByPackageId.TryGetValue(packageId, out prereqInfo))
137 { 137 {
138 // at the time the extension attribute is parsed, the compiler might not yet have 138 // at the time the extension attribute is parsed, the compiler might not yet have
139 // parsed the PrereqPackage attribute, so we need to get it directly from the parent element. 139 // parsed the PrereqPackage attribute, so we need to get it directly from the parent element.
140 XAttribute prereqPackage = parentElement.Attribute(this.Namespace + "PrereqPackage"); 140 var prereqPackage = parentElement.Attribute(this.Namespace + "PrereqPackage");
141 141
142 if (null != prereqPackage && YesNoType.Yes == this.ParseHelper.GetAttributeYesNoValue(sourceLineNumbers, prereqPackage)) 142 if (null != prereqPackage && YesNoType.Yes == this.ParseHelper.GetAttributeYesNoValue(sourceLineNumbers, prereqPackage))
143 { 143 {
144 prereqInfo = (WixMbaPrereqInformationTuple)this.ParseHelper.CreateTuple(section, sourceLineNumbers, "WixMbaPrereqInformation"); 144 prereqInfo = section.AddTuple(new WixMbaPrereqInformationTuple(sourceLineNumbers)
145 prereqInfo.PackageId = packageId; 145 {
146 PackageId = packageId,
147 });
146 148
147 this.prereqInfoRows.Add(packageId, prereqInfo); 149 this.prereqInfoTuplesByPackageId.Add(packageId, prereqInfo);
148 } 150 }
149 else 151 else
150 { 152 {
@@ -165,12 +167,14 @@ namespace WixToolset.Bal
165 case "PrereqPackage": 167 case "PrereqPackage":
166 if (YesNoType.Yes == this.ParseHelper.GetAttributeYesNoValue(sourceLineNumbers, attribute)) 168 if (YesNoType.Yes == this.ParseHelper.GetAttributeYesNoValue(sourceLineNumbers, attribute))
167 { 169 {
168 if (!this.prereqInfoRows.TryGetValue(packageId, out prereqInfo)) 170 if (!this.prereqInfoTuplesByPackageId.TryGetValue(packageId, out prereqInfo))
169 { 171 {
170 prereqInfo = (WixMbaPrereqInformationTuple)this.ParseHelper.CreateTuple(section, sourceLineNumbers, "WixMbaPrereqInformation"); 172 prereqInfo = section.AddTuple(new WixMbaPrereqInformationTuple(sourceLineNumbers)
171 prereqInfo.PackageId = packageId; 173 {
174 PackageId = packageId,
175 });
172 176
173 this.prereqInfoRows.Add(packageId, prereqInfo); 177 this.prereqInfoTuplesByPackageId.Add(packageId, prereqInfo);
174 } 178 }
175 } 179 }
176 break; 180 break;
@@ -193,8 +197,10 @@ namespace WixToolset.Bal
193 case "BAFunctions": 197 case "BAFunctions":
194 if (YesNoType.Yes == this.ParseHelper.GetAttributeYesNoValue(sourceLineNumbers, attribute)) 198 if (YesNoType.Yes == this.ParseHelper.GetAttributeYesNoValue(sourceLineNumbers, attribute))
195 { 199 {
196 var tuple = (WixBalBAFunctionsTuple)this.ParseHelper.CreateTuple(section, sourceLineNumbers, "WixBalBAFunctions"); 200 section.AddTuple(new WixBalBAFunctionsTuple(sourceLineNumbers)
197 tuple.PayloadId = payloadId; 201 {
202 PayloadId = payloadId,
203 });
198 } 204 }
199 break; 205 break;
200 default: 206 default:
@@ -206,7 +212,7 @@ namespace WixToolset.Bal
206 case "Variable": 212 case "Variable":
207 // at the time the extension attribute is parsed, the compiler might not yet have 213 // at the time the extension attribute is parsed, the compiler might not yet have
208 // parsed the Name attribute, so we need to get it directly from the parent element. 214 // parsed the Name attribute, so we need to get it directly from the parent element.
209 XAttribute variableName = parentElement.Attribute("Name"); 215 var variableName = parentElement.Attribute("Name");
210 if (null == variableName) 216 if (null == variableName)
211 { 217 {
212 this.Messaging.Write(ErrorMessages.ExpectedParentWithAttribute(sourceLineNumbers, "Variable", "Overridable", "Name")); 218 this.Messaging.Write(ErrorMessages.ExpectedParentWithAttribute(sourceLineNumbers, "Variable", "Overridable", "Name"));
@@ -218,8 +224,10 @@ namespace WixToolset.Bal
218 case "Overridable": 224 case "Overridable":
219 if (YesNoType.Yes == this.ParseHelper.GetAttributeYesNoValue(sourceLineNumbers, attribute)) 225 if (YesNoType.Yes == this.ParseHelper.GetAttributeYesNoValue(sourceLineNumbers, attribute))
220 { 226 {
221 var tuple = (WixStdbaOverridableVariableTuple)this.ParseHelper.CreateTuple(section, sourceLineNumbers, "WixStdbaOverridableVariable"); 227 section.AddTuple(new WixStdbaOverridableVariableTuple(sourceLineNumbers)
222 tuple.Name = variableName.Value; 228 {
229 Name = variableName.Value,
230 });
223 } 231 }
224 break; 232 break;
225 default: 233 default:
@@ -237,11 +245,11 @@ namespace WixToolset.Bal
237 /// <param name="node">The element to parse.</param> 245 /// <param name="node">The element to parse.</param>
238 private void ParseConditionElement(Intermediate intermediate, IntermediateSection section, XElement node) 246 private void ParseConditionElement(Intermediate intermediate, IntermediateSection section, XElement node)
239 { 247 {
240 SourceLineNumber sourceLineNumbers = this.ParseHelper.GetSourceLineNumbers(node); 248 var sourceLineNumbers = this.ParseHelper.GetSourceLineNumbers(node);
241 string condition = this.ParseHelper.GetConditionInnerText(node); // condition is the inner text of the element. 249 var condition = this.ParseHelper.GetConditionInnerText(node); // condition is the inner text of the element.
242 string message = null; 250 string message = null;
243 251
244 foreach (XAttribute attrib in node.Attributes()) 252 foreach (var attrib in node.Attributes())
245 { 253 {
246 if (String.IsNullOrEmpty(attrib.Name.NamespaceName) || this.Namespace == attrib.Name.Namespace) 254 if (String.IsNullOrEmpty(attrib.Name.NamespaceName) || this.Namespace == attrib.Name.Namespace)
247 { 255 {
@@ -276,14 +284,11 @@ namespace WixToolset.Bal
276 284
277 if (!this.Messaging.EncounteredError) 285 if (!this.Messaging.EncounteredError)
278 { 286 {
279 var tuple = (WixBalConditionTuple)this.ParseHelper.CreateTuple(section, sourceLineNumbers, "WixBalCondition"); 287 section.AddTuple(new WixBalConditionTuple(sourceLineNumbers)
280 tuple.Condition = condition;
281 tuple.Message = message;
282
283 if (null == this.addedConditionLineNumber)
284 { 288 {
285 this.addedConditionLineNumber = sourceLineNumbers; 289 Condition = condition,
286 } 290 Message = message,
291 });
287 } 292 }
288 } 293 }
289 294
@@ -293,11 +298,11 @@ namespace WixToolset.Bal
293 /// <param name="node">The element to parse.</param> 298 /// <param name="node">The element to parse.</param>
294 private void ParseWixStandardBootstrapperApplicationElement(Intermediate intermediate, IntermediateSection section, XElement node) 299 private void ParseWixStandardBootstrapperApplicationElement(Intermediate intermediate, IntermediateSection section, XElement node)
295 { 300 {
296 SourceLineNumber sourceLineNumbers = this.ParseHelper.GetSourceLineNumbers(node); 301 var sourceLineNumbers = this.ParseHelper.GetSourceLineNumbers(node);
297 string launchTarget = null; 302 string launchTarget = null;
298 string launchTargetElevatedId = null; 303 string launchTargetElevatedId = null;
299 string launchArguments = null; 304 string launchArguments = null;
300 YesNoType launchHidden = YesNoType.NotSet; 305 var launchHidden = YesNoType.NotSet;
301 string launchWorkingDir = null; 306 string launchWorkingDir = null;
302 string licenseFile = null; 307 string licenseFile = null;
303 string licenseUrl = null; 308 string licenseUrl = null;
@@ -305,13 +310,13 @@ namespace WixToolset.Bal
305 string logoSideFile = null; 310 string logoSideFile = null;
306 string themeFile = null; 311 string themeFile = null;
307 string localizationFile = null; 312 string localizationFile = null;
308 YesNoType suppressOptionsUI = YesNoType.NotSet; 313 var suppressOptionsUI = YesNoType.NotSet;
309 YesNoType suppressDowngradeFailure = YesNoType.NotSet; 314 var suppressDowngradeFailure = YesNoType.NotSet;
310 YesNoType suppressRepair = YesNoType.NotSet; 315 var suppressRepair = YesNoType.NotSet;
311 YesNoType showVersion = YesNoType.NotSet; 316 var showVersion = YesNoType.NotSet;
312 YesNoType supportCacheOnly = YesNoType.NotSet; 317 var supportCacheOnly = YesNoType.NotSet;
313 318
314 foreach (XAttribute attrib in node.Attributes()) 319 foreach (var attrib in node.Attributes())
315 { 320 {
316 if (String.IsNullOrEmpty(attrib.Name.NamespaceName) || this.Namespace == attrib.Name.Namespace) 321 if (String.IsNullOrEmpty(attrib.Name.NamespaceName) || this.Namespace == attrib.Name.Namespace)
317 { 322 {
@@ -387,90 +392,101 @@ namespace WixToolset.Bal
387 { 392 {
388 if (!String.IsNullOrEmpty(launchTarget)) 393 if (!String.IsNullOrEmpty(launchTarget))
389 { 394 {
390 var row = (WixBundleVariableTuple)this.ParseHelper.CreateTuple(section, sourceLineNumbers, "WixBundleVariable"); 395 section.AddTuple(new WixBundleVariableTuple(sourceLineNumbers, new Identifier(AccessModifier.Public, "LaunchTarget"))
391 row.Id = new Identifier(AccessModifier.Public, "LaunchTarget"); 396 {
392 row.Value = launchTarget; 397 Value = launchTarget,
393 row.Type = "string"; 398 Type = "string",
399 });
394 } 400 }
395 401
396 if (!String.IsNullOrEmpty(launchTargetElevatedId)) 402 if (!String.IsNullOrEmpty(launchTargetElevatedId))
397 { 403 {
398 var row = (WixBundleVariableTuple)this.ParseHelper.CreateTuple(section, sourceLineNumbers, "WixBundleVariable"); 404 section.AddTuple(new WixBundleVariableTuple(sourceLineNumbers, new Identifier(AccessModifier.Public, "LaunchTargetElevatedId"))
399 row.Id = new Identifier(AccessModifier.Public, "LaunchTargetElevatedId"); 405 {
400 row.Value = launchTargetElevatedId; 406 Value = launchTargetElevatedId,
401 row.Type = "string"; 407 Type = "string",
408 });
402 } 409 }
403 410
404 if (!String.IsNullOrEmpty(launchArguments)) 411 if (!String.IsNullOrEmpty(launchArguments))
405 { 412 {
406 var row = (WixBundleVariableTuple)this.ParseHelper.CreateTuple(section, sourceLineNumbers, "WixBundleVariable"); 413 section.AddTuple(new WixBundleVariableTuple(sourceLineNumbers, new Identifier(AccessModifier.Public, "LaunchArguments"))
407 row.Id = new Identifier(AccessModifier.Public, "LaunchArguments"); 414 {
408 row.Value = launchArguments; 415 Value = launchArguments,
409 row.Type = "string"; 416 Type = "string",
417 });
410 } 418 }
411 419
412 if (YesNoType.Yes == launchHidden) 420 if (YesNoType.Yes == launchHidden)
413 { 421 {
414 var row = (WixBundleVariableTuple)this.ParseHelper.CreateTuple(section, sourceLineNumbers, "WixBundleVariable"); 422 section.AddTuple(new WixBundleVariableTuple(sourceLineNumbers, new Identifier(AccessModifier.Public, "LaunchHidden"))
415 row.Id = new Identifier(AccessModifier.Public, "LaunchHidden"); 423 {
416 row.Value = "yes"; 424 Value = "yes",
417 row.Type = "string"; 425 Type = "string",
426 });
418 } 427 }
419 428
420 429
421 if (!String.IsNullOrEmpty(launchWorkingDir)) 430 if (!String.IsNullOrEmpty(launchWorkingDir))
422 { 431 {
423 var row = (WixBundleVariableTuple)this.ParseHelper.CreateTuple(section, sourceLineNumbers, "Variable"); 432 section.AddTuple(new WixBundleVariableTuple(sourceLineNumbers, new Identifier(AccessModifier.Public, "LaunchWorkingFolder"))
424 row.Id = new Identifier(AccessModifier.Public, "LaunchWorkingFolder"); 433 {
425 row.Value = launchWorkingDir; 434 Value = launchWorkingDir,
426 row.Type = "string"; 435 Type = "string",
436 });
427 } 437 }
428 438
429 if (!String.IsNullOrEmpty(licenseFile)) 439 if (!String.IsNullOrEmpty(licenseFile))
430 { 440 {
431 var wixVariableRow = (WixVariableTuple)this.ParseHelper.CreateTuple(section, sourceLineNumbers, "WixVariable"); 441 section.AddTuple(new WixVariableTuple(sourceLineNumbers, new Identifier(AccessModifier.Public, "WixStdbaLicenseRtf"))
432 wixVariableRow.Id = new Identifier(AccessModifier.Public, "WixStdbaLicenseRtf"); 442 {
433 wixVariableRow.Value = licenseFile; 443 Value = licenseFile,
444 });
434 } 445 }
435 446
436 if (null != licenseUrl) 447 if (null != licenseUrl)
437 { 448 {
438 var wixVariableRow = (WixVariableTuple)this.ParseHelper.CreateTuple(section, sourceLineNumbers, "WixVariable"); 449 section.AddTuple(new WixVariableTuple(sourceLineNumbers, new Identifier(AccessModifier.Public, "WixStdbaLicenseUrl"))
439 wixVariableRow.Id = new Identifier(AccessModifier.Public, "WixStdbaLicenseUrl"); 450 {
440 wixVariableRow.Value = licenseUrl; 451 Value = licenseUrl,
452 });
441 } 453 }
442 454
443 if (!String.IsNullOrEmpty(logoFile)) 455 if (!String.IsNullOrEmpty(logoFile))
444 { 456 {
445 var wixVariableRow = (WixVariableTuple)this.ParseHelper.CreateTuple(section, sourceLineNumbers, "WixVariable"); 457 section.AddTuple(new WixVariableTuple(sourceLineNumbers, new Identifier(AccessModifier.Public, "WixStdbaLogo"))
446 wixVariableRow.Id = new Identifier(AccessModifier.Public, "WixStdbaLogo"); 458 {
447 wixVariableRow.Value = logoFile; 459 Value = logoFile,
460 });
448 } 461 }
449 462
450 if (!String.IsNullOrEmpty(logoSideFile)) 463 if (!String.IsNullOrEmpty(logoSideFile))
451 { 464 {
452 var wixVariableRow = (WixVariableTuple)this.ParseHelper.CreateTuple(section, sourceLineNumbers, "WixVariable"); 465 section.AddTuple(new WixVariableTuple(sourceLineNumbers, new Identifier(AccessModifier.Public, "WixStdbaLogoSide"))
453 wixVariableRow.Id = new Identifier(AccessModifier.Public, "WixStdbaLogoSide"); 466 {
454 wixVariableRow.Value = logoSideFile; 467 Value = logoSideFile,
468 });
455 } 469 }
456 470
457 if (!String.IsNullOrEmpty(themeFile)) 471 if (!String.IsNullOrEmpty(themeFile))
458 { 472 {
459 var wixVariableRow = (WixVariableTuple)this.ParseHelper.CreateTuple(section, sourceLineNumbers, "WixVariable"); 473 section.AddTuple(new WixVariableTuple(sourceLineNumbers, new Identifier(AccessModifier.Public, "WixStdbaThemeXml"))
460 wixVariableRow.Id = new Identifier(AccessModifier.Public, "WixStdbaThemeXml"); 474 {
461 wixVariableRow.Value = themeFile; 475 Value = themeFile,
476 });
462 } 477 }
463 478
464 if (!String.IsNullOrEmpty(localizationFile)) 479 if (!String.IsNullOrEmpty(localizationFile))
465 { 480 {
466 var wixVariableRow = (WixVariableTuple)this.ParseHelper.CreateTuple(section, sourceLineNumbers, "WixVariable"); 481 section.AddTuple(new WixVariableTuple(sourceLineNumbers, new Identifier(AccessModifier.Public, "WixStdbaThemeWxl"))
467 wixVariableRow.Id = new Identifier(AccessModifier.Public, "WixStdbaThemeWxl"); 482 {
468 wixVariableRow.Value = localizationFile; 483 Value = localizationFile,
484 });
469 } 485 }
470 486
471 if (YesNoType.Yes == suppressOptionsUI || YesNoType.Yes == suppressDowngradeFailure || YesNoType.Yes == suppressRepair || YesNoType.Yes == showVersion || YesNoType.Yes == supportCacheOnly) 487 if (YesNoType.Yes == suppressOptionsUI || YesNoType.Yes == suppressDowngradeFailure || YesNoType.Yes == suppressRepair || YesNoType.Yes == showVersion || YesNoType.Yes == supportCacheOnly)
472 { 488 {
473 var tuple = (WixStdbaOptionsTuple)this.ParseHelper.CreateTuple(section, sourceLineNumbers, "WixStdbaOptions"); 489 var tuple = section.AddTuple(new WixStdbaOptionsTuple(sourceLineNumbers));
474 if (YesNoType.Yes == suppressOptionsUI) 490 if (YesNoType.Yes == suppressOptionsUI)
475 { 491 {
476 tuple.SuppressOptionsUI = 1; 492 tuple.SuppressOptionsUI = 1;
@@ -505,12 +521,12 @@ namespace WixToolset.Bal
505 /// <param name="node">The element to parse.</param> 521 /// <param name="node">The element to parse.</param>
506 private void ParseWixManagedBootstrapperApplicationHostElement(Intermediate intermediate, IntermediateSection section, XElement node) 522 private void ParseWixManagedBootstrapperApplicationHostElement(Intermediate intermediate, IntermediateSection section, XElement node)
507 { 523 {
508 SourceLineNumber sourceLineNumbers = this.ParseHelper.GetSourceLineNumbers(node); 524 var sourceLineNumbers = this.ParseHelper.GetSourceLineNumbers(node);
509 string logoFile = null; 525 string logoFile = null;
510 string themeFile = null; 526 string themeFile = null;
511 string localizationFile = null; 527 string localizationFile = null;
512 528
513 foreach (XAttribute attrib in node.Attributes()) 529 foreach (var attrib in node.Attributes())
514 { 530 {
515 if (String.IsNullOrEmpty(attrib.Name.NamespaceName) || this.Namespace == attrib.Name.Namespace) 531 if (String.IsNullOrEmpty(attrib.Name.NamespaceName) || this.Namespace == attrib.Name.Namespace)
516 { 532 {
@@ -542,23 +558,26 @@ namespace WixToolset.Bal
542 { 558 {
543 if (!String.IsNullOrEmpty(logoFile)) 559 if (!String.IsNullOrEmpty(logoFile))
544 { 560 {
545 var wixVariableRow = (WixVariableTuple)this.ParseHelper.CreateTuple(section, sourceLineNumbers, "WixVariable"); 561 section.AddTuple(new WixVariableTuple(sourceLineNumbers, new Identifier(AccessModifier.Public, "PreqbaLogo"))
546 wixVariableRow.Id = new Identifier(AccessModifier.Public, "PreqbaLogo"); 562 {
547 wixVariableRow.Value = logoFile; 563 Value = logoFile,
564 });
548 } 565 }
549 566
550 if (!String.IsNullOrEmpty(themeFile)) 567 if (!String.IsNullOrEmpty(themeFile))
551 { 568 {
552 var wixVariableRow = (WixVariableTuple)this.ParseHelper.CreateTuple(section, sourceLineNumbers, "WixVariable"); 569 section.AddTuple(new WixVariableTuple(sourceLineNumbers, new Identifier(AccessModifier.Public, "PreqbaThemeXml"))
553 wixVariableRow.Id = new Identifier(AccessModifier.Public, "PreqbaThemeXml"); 570 {
554 wixVariableRow.Value = themeFile; 571 Value = themeFile,
572 });
555 } 573 }
556 574
557 if (!String.IsNullOrEmpty(localizationFile)) 575 if (!String.IsNullOrEmpty(localizationFile))
558 { 576 {
559 var wixVariableRow = (WixVariableTuple)this.ParseHelper.CreateTuple(section, sourceLineNumbers, "WixVariable"); 577 section.AddTuple(new WixVariableTuple(sourceLineNumbers, new Identifier(AccessModifier.Public, "PreqbaThemeWxl"))
560 wixVariableRow.Id = new Identifier(AccessModifier.Public, "PreqbaThemeWxl"); 578 {
561 wixVariableRow.Value = localizationFile; 579 Value = localizationFile,
580 });
562 } 581 }
563 } 582 }
564 } 583 }