aboutsummaryrefslogtreecommitdiff
path: root/src/light
diff options
context:
space:
mode:
Diffstat (limited to 'src/light')
-rw-r--r--src/light/LightCommandLine.cs196
-rw-r--r--src/light/light.cs49
2 files changed, 80 insertions, 165 deletions
diff --git a/src/light/LightCommandLine.cs b/src/light/LightCommandLine.cs
index 9a90b9ce..2aa9ea59 100644
--- a/src/light/LightCommandLine.cs
+++ b/src/light/LightCommandLine.cs
@@ -6,8 +6,8 @@ namespace WixToolset.Tools
6 using System.Collections.Generic; 6 using System.Collections.Generic;
7 using System.Globalization; 7 using System.Globalization;
8 using System.IO; 8 using System.IO;
9 using WixToolset.Core.CommandLine;
10 using WixToolset.Data; 9 using WixToolset.Data;
10 using WixToolset.Extensibility;
11 using WixToolset.Extensibility.Services; 11 using WixToolset.Extensibility.Services;
12 12
13 public class LightCommandLine 13 public class LightCommandLine
@@ -22,7 +22,6 @@ namespace WixToolset.Tools
22 this.SuppressIces = new List<string>(); 22 this.SuppressIces = new List<string>();
23 this.Ices = new List<string>(); 23 this.Ices = new List<string>();
24 this.BindPaths = new List<BindPath>(); 24 this.BindPaths = new List<BindPath>();
25 this.Extensions = new List<string>();
26 this.Files = new List<string>(); 25 this.Files = new List<string>();
27 this.LocalizationFiles = new List<string>(); 26 this.LocalizationFiles = new List<string>();
28 this.Variables = new Dictionary<string, string>(); 27 this.Variables = new Dictionary<string, string>();
@@ -80,8 +79,6 @@ namespace WixToolset.Tools
80 79
81 public List<BindPath> BindPaths { get; private set; } 80 public List<BindPath> BindPaths { get; private set; }
82 81
83 public List<string> Extensions { get; private set; }
84
85 public List<string> Files { get; private set; } 82 public List<string> Files { get; private set; }
86 83
87 public List<string> LocalizationFiles { get; private set; } 84 public List<string> LocalizationFiles { get; private set; }
@@ -96,35 +93,40 @@ namespace WixToolset.Tools
96 /// Parse the commandline arguments. 93 /// Parse the commandline arguments.
97 /// </summary> 94 /// </summary>
98 /// <param name="args">Commandline arguments.</param> 95 /// <param name="args">Commandline arguments.</param>
99 public string[] Parse(string[] args) 96 public string[] Parse(ICommandLineContext context)
100 { 97 {
101 List<string> unprocessed = new List<string>(); 98 var unprocessed = new List<string>();
99
100 var extensions = context.ExtensionManager.Create<IExtensionCommandLine>();
101
102 foreach (var extension in extensions)
103 {
104 extension.PreParse(context);
105 }
106
107 var parser = context.Arguments.Parse();
102 108
103 for (int i = 0; i < args.Length; ++i) 109 while (!this.ShowHelp &&
110 String.IsNullOrEmpty(parser.ErrorArgument) &&
111 parser.TryGetNextSwitchOrArgument(out var arg))
104 { 112 {
105 string arg = args[i]; 113 if (String.IsNullOrWhiteSpace(arg)) // skip blank arguments.
106 if (String.IsNullOrEmpty(arg)) // skip blank arguments
107 { 114 {
108 continue; 115 continue;
109 } 116 }
110 117
111 if (1 == arg.Length) // treat '-' and '@' as filenames when by themselves. 118 if (parser.IsSwitch(arg))
112 { 119 {
113 unprocessed.Add(arg); 120 var parameter = arg.Substring(1);
114 }
115 else if ('-' == arg[0] || '/' == arg[0])
116 {
117 string parameter = arg.Substring(1);
118 if (parameter.Equals("b", StringComparison.Ordinal)) 121 if (parameter.Equals("b", StringComparison.Ordinal))
119 { 122 {
120 if (!CommandLineHelper.IsValidArg(args, ++i)) 123 var result = parser.GetNextArgumentOrError(arg);
124 if (!String.IsNullOrEmpty(result))
121 { 125 {
122 break; 126 var bindPath = BindPath.Parse(result);
123 }
124 127
125 var bindPath = BindPath.Parse(args[i]); 128 this.BindPaths.Add(bindPath);
126 129 }
127 this.BindPaths.Add(bindPath);
128 } 130 }
129 else if (parameter.StartsWith("cultures:", StringComparison.Ordinal)) 131 else if (parameter.StartsWith("cultures:", StringComparison.Ordinal))
130 { 132 {
@@ -184,25 +186,9 @@ namespace WixToolset.Tools
184 this.Variables.Add(value[0], value[1]); 186 this.Variables.Add(value[0], value[1]);
185 } 187 }
186 } 188 }
187 else if (parameter.Equals("ext", StringComparison.Ordinal))
188 {
189 if (!CommandLineHelper.IsValidArg(args, ++i))
190 {
191 this.Messaging.Write(ErrorMessages.TypeSpecificationForExtensionRequired("-ext"));
192 break;
193 }
194
195 this.Extensions.Add(args[i]);
196 }
197 else if (parameter.Equals("loc", StringComparison.Ordinal)) 189 else if (parameter.Equals("loc", StringComparison.Ordinal))
198 { 190 {
199 string locFile = CommandLineHelper.GetFile(parameter, this.Messaging, args, ++i); 191 parser.GetNextArgumentAsFilePathOrError(arg, "localization files", this.LocalizationFiles);
200 if (String.IsNullOrEmpty(locFile))
201 {
202 break;
203 }
204
205 this.LocalizationFiles.Add(locFile);
206 } 192 }
207 else if (parameter.Equals("nologo", StringComparison.Ordinal)) 193 else if (parameter.Equals("nologo", StringComparison.Ordinal))
208 { 194 {
@@ -214,11 +200,7 @@ namespace WixToolset.Tools
214 } 200 }
215 else if ("o" == parameter || "out" == parameter) 201 else if ("o" == parameter || "out" == parameter)
216 { 202 {
217 this.OutputFile = CommandLineHelper.GetFile(parameter, this.Messaging, args, ++i); 203 this.OutputFile = parser.GetNextArgumentAsFilePathOrError(arg);
218 if (String.IsNullOrEmpty(this.OutputFile))
219 {
220 break;
221 }
222 } 204 }
223 else if (parameter.Equals("pedantic", StringComparison.Ordinal)) 205 else if (parameter.Equals("pedantic", StringComparison.Ordinal))
224 { 206 {
@@ -230,12 +212,7 @@ namespace WixToolset.Tools
230 } 212 }
231 else if (parameter.Equals("usf", StringComparison.Ordinal)) 213 else if (parameter.Equals("usf", StringComparison.Ordinal))
232 { 214 {
233 this.UnreferencedSymbolsFile = CommandLineHelper.GetFile(parameter, this.Messaging, args, ++i); 215 this.UnreferencedSymbolsFile = parser.GetNextArgumentAsDirectoryOrError(arg);
234
235 if (String.IsNullOrEmpty(this.UnreferencedSymbolsFile))
236 {
237 break;
238 }
239 } 216 }
240 else if (parameter.Equals("xo", StringComparison.Ordinal)) 217 else if (parameter.Equals("xo", StringComparison.Ordinal))
241 { 218 {
@@ -243,41 +220,27 @@ namespace WixToolset.Tools
243 } 220 }
244 else if (parameter.Equals("cc", StringComparison.Ordinal)) 221 else if (parameter.Equals("cc", StringComparison.Ordinal))
245 { 222 {
246 this.CabCachePath = CommandLineHelper.GetDirectory(parameter, this.Messaging, args, ++i); 223 this.CabCachePath = parser.GetNextArgumentAsDirectoryOrError(arg);
247
248 if (String.IsNullOrEmpty(this.CabCachePath))
249 {
250 break;
251 }
252 } 224 }
253 else if (parameter.Equals("ct", StringComparison.Ordinal)) 225 else if (parameter.Equals("ct", StringComparison.Ordinal))
254 { 226 {
255 if (!CommandLineHelper.IsValidArg(args, ++i)) 227 var result = parser.GetNextArgumentOrError(arg);
228 if (!String.IsNullOrEmpty(result))
256 { 229 {
257 this.Messaging.Write(ErrorMessages.IllegalCabbingThreadCount(String.Empty)); 230 if (!Int32.TryParse(result, out var ct) || 0 >= ct)
258 break; 231 {
259 } 232 this.Messaging.Write(ErrorMessages.IllegalCabbingThreadCount(result));
233 parser.ErrorArgument = arg;
234 break;
235 }
260 236
261 int ct = 0; 237 this.CabbingThreadCount = ct;
262 if (!Int32.TryParse(args[i], out ct) || 0 >= ct) 238 this.Messaging.Write(VerboseMessages.SetCabbingThreadCount(this.CabbingThreadCount.ToString()));
263 {
264 this.Messaging.Write(ErrorMessages.IllegalCabbingThreadCount(args[i]));
265 break;
266 } 239 }
267
268 this.CabbingThreadCount = ct;
269 this.Messaging.Write(VerboseMessages.SetCabbingThreadCount(this.CabbingThreadCount.ToString()));
270 } 240 }
271 else if (parameter.Equals("cub", StringComparison.Ordinal)) 241 else if (parameter.Equals("cub", StringComparison.Ordinal))
272 { 242 {
273 string cubeFile = CommandLineHelper.GetFile(parameter, this.Messaging, args, ++i); 243 parser.GetNextArgumentAsFilePathOrError(arg, "static validation files", this.CubeFiles);
274
275 if (String.IsNullOrEmpty(cubeFile))
276 {
277 break;
278 }
279
280 this.CubeFiles.Add(cubeFile);
281 } 244 }
282 else if (parameter.StartsWith("ice:", StringComparison.Ordinal)) 245 else if (parameter.StartsWith("ice:", StringComparison.Ordinal))
283 { 246 {
@@ -285,57 +248,27 @@ namespace WixToolset.Tools
285 } 248 }
286 else if (parameter.Equals("intermediatefolder", StringComparison.OrdinalIgnoreCase)) 249 else if (parameter.Equals("intermediatefolder", StringComparison.OrdinalIgnoreCase))
287 { 250 {
288 this.IntermediateFolder = CommandLineHelper.GetDirectory(parameter, this.Messaging, args, ++i); 251 this.IntermediateFolder = parser.GetNextArgumentAsDirectoryOrError(arg);
289
290 if (String.IsNullOrEmpty(this.IntermediateFolder))
291 {
292 break;
293 }
294 } 252 }
295 else if (parameter.Equals("contentsfile", StringComparison.Ordinal)) 253 else if (parameter.Equals("contentsfile", StringComparison.Ordinal))
296 { 254 {
297 this.ContentsFile = CommandLineHelper.GetFile(parameter, this.Messaging, args, ++i); 255 this.ContentsFile = parser.GetNextArgumentAsFilePathOrError(arg);
298
299 if (String.IsNullOrEmpty(this.ContentsFile))
300 {
301 break;
302 }
303 } 256 }
304 else if (parameter.Equals("outputsfile", StringComparison.Ordinal)) 257 else if (parameter.Equals("outputsfile", StringComparison.Ordinal))
305 { 258 {
306 this.OutputsFile = CommandLineHelper.GetFile(parameter, this.Messaging, args, ++i); 259 this.OutputsFile = parser.GetNextArgumentAsFilePathOrError(arg);
307
308 if (String.IsNullOrEmpty(this.OutputsFile))
309 {
310 break;
311 }
312 } 260 }
313 else if (parameter.Equals("builtoutputsfile", StringComparison.Ordinal)) 261 else if (parameter.Equals("builtoutputsfile", StringComparison.Ordinal))
314 { 262 {
315 this.BuiltOutputsFile = CommandLineHelper.GetFile(parameter, this.Messaging, args, ++i); 263 this.BuiltOutputsFile = parser.GetNextArgumentAsFilePathOrError(arg);
316
317 if (String.IsNullOrEmpty(this.BuiltOutputsFile))
318 {
319 break;
320 }
321 } 264 }
322 else if (parameter.Equals("wixprojectfile", StringComparison.Ordinal)) 265 else if (parameter.Equals("wixprojectfile", StringComparison.Ordinal))
323 { 266 {
324 this.WixprojectFile = CommandLineHelper.GetFile(parameter, this.Messaging, args, ++i); 267 this.WixprojectFile = parser.GetNextArgumentAsFilePathOrError(arg);
325
326 if (String.IsNullOrEmpty(this.WixprojectFile))
327 {
328 break;
329 }
330 } 268 }
331 else if (parameter.Equals("pdbout", StringComparison.Ordinal)) 269 else if (parameter.Equals("pdbout", StringComparison.Ordinal))
332 { 270 {
333 this.PdbFile = CommandLineHelper.GetFile(parameter, this.Messaging, args, ++i); 271 this.PdbFile = parser.GetNextArgumentAsFilePathOrError(arg);
334
335 if (String.IsNullOrEmpty(this.PdbFile))
336 {
337 break;
338 }
339 } 272 }
340 else if (parameter.StartsWith("sice:", StringComparison.Ordinal)) 273 else if (parameter.StartsWith("sice:", StringComparison.Ordinal))
341 { 274 {
@@ -410,45 +343,35 @@ namespace WixToolset.Tools
410 this.ShowHelp = true; 343 this.ShowHelp = true;
411 break; 344 break;
412 } 345 }
413 else 346 else if (!this.TryParseCommandLineArgumentWithExtension(arg, parser, extensions))
414 { 347 {
415 unprocessed.Add(arg); 348 unprocessed.Add(arg);
416 } 349 }
417 } 350 }
418 else if ('@' == arg[0]) 351 else if (!this.TryParseCommandLineArgumentWithExtension(arg, parser, extensions))
419 {
420 string[] parsedArgs = CommandLineResponseFile.Parse(arg.Substring(1));
421 string[] unparsedArgs = this.Parse(parsedArgs);
422 unprocessed.AddRange(unparsedArgs);
423 }
424 else
425 { 352 {
426 unprocessed.Add(arg); 353 unprocessed.Add(arg);
427 } 354 }
428 } 355 }
429 356
430 return unprocessed.ToArray(); 357 return this.ParsePostExtensions(parser, unprocessed.ToArray());
431 } 358 }
432 359
433 public string[] ParsePostExtensions(string[] remaining) 360 private string[] ParsePostExtensions(IParseCommandLine parser, string[] remaining)
434 { 361 {
435 List<string> unprocessed = new List<string>(); 362 var unprocessed = new List<string>();
436 363
437 for (int i = 0; i < remaining.Length; ++i) 364 for (int i = 0; i < remaining.Length; ++i)
438 { 365 {
439 string arg = remaining[i]; 366 var arg = remaining[i];
440 if (String.IsNullOrEmpty(arg)) // skip blank arguments
441 {
442 continue;
443 }
444 367
445 if (1 < arg.Length && ('-' == arg[0] || '/' == arg[0])) 368 if (parser.IsSwitch(arg))
446 { 369 {
447 unprocessed.Add(arg); 370 unprocessed.Add(arg);
448 } 371 }
449 else 372 else
450 { 373 {
451 this.Files.AddRange(CommandLineHelper.GetFiles(arg, "Source")); 374 parser.GetArgumentAsFilePathOrError(arg, "source files", this.Files);
452 } 375 }
453 } 376 }
454 377
@@ -469,7 +392,7 @@ namespace WixToolset.Tools
469 // Add the directories of the input files as unnamed bind paths. 392 // Add the directories of the input files as unnamed bind paths.
470 foreach (string file in this.Files) 393 foreach (string file in this.Files)
471 { 394 {
472 BindPath bindPath = new BindPath(Path.GetDirectoryName(Path.GetFullPath(file))); 395 var bindPath = new BindPath(Path.GetDirectoryName(Path.GetFullPath(file)));
473 this.BindPaths.Add(bindPath); 396 this.BindPaths.Add(bindPath);
474 } 397 }
475 } 398 }
@@ -481,5 +404,18 @@ namespace WixToolset.Tools
481 404
482 return unprocessed.ToArray(); 405 return unprocessed.ToArray();
483 } 406 }
407
408 private bool TryParseCommandLineArgumentWithExtension(string arg, IParseCommandLine parser, IEnumerable<IExtensionCommandLine> extensions)
409 {
410 foreach (var extension in extensions)
411 {
412 if (extension.TryParseArgument(parser, arg))
413 {
414 return true;
415 }
416 }
417
418 return false;
419 }
484 } 420 }
485} 421}
diff --git a/src/light/light.cs b/src/light/light.cs
index c0967caa..0f467bbb 100644
--- a/src/light/light.cs
+++ b/src/light/light.cs
@@ -22,7 +22,6 @@ namespace WixToolset.Tools
22 public sealed class Light 22 public sealed class Light
23 { 23 {
24 LightCommandLine commandLine; 24 LightCommandLine commandLine;
25 private IEnumerable<IExtensionData> extensionData;
26 //private IEnumerable<IBinderExtension> binderExtensions; 25 //private IEnumerable<IBinderExtension> binderExtensions;
27 //private IEnumerable<IBinderFileManager> fileManagers; 26 //private IEnumerable<IBinderFileManager> fileManagers;
28 27
@@ -101,45 +100,20 @@ namespace WixToolset.Tools
101 /// <param name="args">Command line arguments to be parsed.</param> 100 /// <param name="args">Command line arguments to be parsed.</param>
102 private IEnumerable<string> ParseCommandLineAndLoadExtensions(IServiceProvider serviceProvider, IMessaging messaging, string[] args) 101 private IEnumerable<string> ParseCommandLineAndLoadExtensions(IServiceProvider serviceProvider, IMessaging messaging, string[] args)
103 { 102 {
104 this.commandLine = new LightCommandLine(messaging); 103 var arguments = serviceProvider.GetService<ICommandLineArguments>();
104 arguments.Populate(args);
105 105
106 string[] unprocessed = this.commandLine.Parse(args); 106 var extensionManager = CreateExtensionManagerWithStandardBackends(serviceProvider, arguments.Extensions);
107 if (messaging.EncounteredError)
108 {
109 return unprocessed;
110 }
111 107
112 // Load extensions.
113 var extensionManager = CreateExtensionManagerWithStandardBackends(serviceProvider);
114 foreach (string extension in this.commandLine.Extensions)
115 {
116 extensionManager.Load(extension);
117 }
118
119 // Extension data command line processing.
120 var context = serviceProvider.GetService<ICommandLineContext>(); 108 var context = serviceProvider.GetService<ICommandLineContext>();
121 context.Arguments = null;
122 context.ExtensionManager = extensionManager; 109 context.ExtensionManager = extensionManager;
123 context.Messaging = messaging; 110 context.Messaging = messaging;
124 context.ParsedArguments = args; 111 context.Arguments = arguments;
125
126 var commandLineExtensions = extensionManager.Create<IExtensionCommandLine>();
127 foreach (var extension in commandLineExtensions)
128 {
129 extension.PreParse(context);
130 }
131 112
132 // Process unproccessed arguments. 113 this.commandLine = new LightCommandLine(messaging);
133 List<string> actuallyUnprocessed = new List<string>(); 114 var unprocessed = this.commandLine.Parse(context);
134 foreach (var arg in unprocessed)
135 {
136 if (!this.TryParseCommandLineArgumentWithExtension(arg, commandLineExtensions))
137 {
138 actuallyUnprocessed.Add(arg);
139 }
140 }
141 115
142 return this.commandLine.ParsePostExtensions(actuallyUnprocessed.ToArray()); 116 return unprocessed;
143 } 117 }
144 118
145 private void Bind(IServiceProvider serviceProvider, IMessaging messaging) 119 private void Bind(IServiceProvider serviceProvider, IMessaging messaging)
@@ -194,7 +168,7 @@ namespace WixToolset.Tools
194 binder.IntermediateRepresentation = resolveResult.IntermediateRepresentation; 168 binder.IntermediateRepresentation = resolveResult.IntermediateRepresentation;
195 binder.OutputPath = this.commandLine.OutputFile; 169 binder.OutputPath = this.commandLine.OutputFile;
196 binder.OutputPdbPath = Path.ChangeExtension(this.commandLine.OutputFile, ".wixpdb"); 170 binder.OutputPdbPath = Path.ChangeExtension(this.commandLine.OutputFile, ".wixpdb");
197 binder.SuppressIces = this.commandLine.SuppressIces; 171 binder.SuppressIces = this.commandLine.SuppressIces;
198 binder.SuppressValidation = this.commandLine.SuppressValidation; 172 binder.SuppressValidation = this.commandLine.SuppressValidation;
199 173
200 bindResult = binder.Execute(); 174 bindResult = binder.Execute();
@@ -526,7 +500,7 @@ namespace WixToolset.Tools
526 return Intermediate.Load(path); 500 return Intermediate.Load(path);
527 } 501 }
528 502
529 private static IExtensionManager CreateExtensionManagerWithStandardBackends(IServiceProvider serviceProvider) 503 private static IExtensionManager CreateExtensionManagerWithStandardBackends(IServiceProvider serviceProvider, IEnumerable<string> extensions)
530 { 504 {
531 var extensionManager = serviceProvider.GetService<IExtensionManager>(); 505 var extensionManager = serviceProvider.GetService<IExtensionManager>();
532 506
@@ -535,6 +509,11 @@ namespace WixToolset.Tools
535 extensionManager.Add(type.Assembly); 509 extensionManager.Add(type.Assembly);
536 } 510 }
537 511
512 foreach (var extension in extensions)
513 {
514 extensionManager.Load(extension);
515 }
516
538 return extensionManager; 517 return extensionManager;
539 } 518 }
540 519