X-Git-Url: http://wien.tomnetworks.com/gitweb/?a=blobdiff_plain;ds=sidebyside;f=mcs%2Fmcs%2Fdriver.cs;h=ad1853a4a4ea530bf1bb1d25ff27c468477487ca;hb=acad24f57f6c36ae1cb2a6b17c52d00c0386e665;hp=475e97eb81b184f9cd8d13a2bd199f521a5c1a33;hpb=880bea0e62f7b4d97eab34fde65c5121e706ea72;p=mono.git diff --git a/mcs/mcs/driver.cs b/mcs/mcs/driver.cs index 475e97eb81b..ad1853a4a4e 100644 --- a/mcs/mcs/driver.cs +++ b/mcs/mcs/driver.cs @@ -20,6 +20,7 @@ using System.IO; using System.Text; using System.Globalization; using System.Diagnostics; +using System.Threading; namespace Mono.CSharp { @@ -41,20 +42,22 @@ namespace Mono.CSharp } } - void tokenize_file (CompilationSourceFile file) + void tokenize_file (SourceFile sourceFile, ModuleContainer module, ParserSession session) { Stream input; try { - input = File.OpenRead (file.Name); + input = File.OpenRead (sourceFile.Name); } catch { - Report.Error (2001, "Source file `" + file.Name + "' could not be found"); + Report.Error (2001, "Source file `" + sourceFile.Name + "' could not be found"); return; } using (input){ SeekableStreamReader reader = new SeekableStreamReader (input, ctx.Settings.Encoding); - Tokenizer lexer = new Tokenizer (reader, file, ctx); + var file = new CompilationSourceFile (module, sourceFile); + + Tokenizer lexer = new Tokenizer (reader, file, session, ctx.Report); int token, tokens = 0, errors = 0; while ((token = lexer.token ()) != Token.EOF){ @@ -70,50 +73,100 @@ namespace Mono.CSharp void Parse (ModuleContainer module) { - Location.Initialize (module.Compiler.SourceFiles); - bool tokenize_only = module.Compiler.Settings.TokenizeOnly; var sources = module.Compiler.SourceFiles; + + Location.Initialize (sources); + + var session = new ParserSession { + UseJayGlobalArrays = true, + LocatedTokens = new LocatedToken[15000] + }; + for (int i = 0; i < sources.Count; ++i) { if (tokenize_only) { - tokenize_file (sources[i]); + tokenize_file (sources[i], module, session); } else { - Parse (sources[i], module); + Parse (sources[i], module, session, Report); } } } - public void Parse (CompilationSourceFile file, ModuleContainer module) +#if false + void ParseParallel (ModuleContainer module) + { + var sources = module.Compiler.SourceFiles; + + Location.Initialize (sources); + + var pcount = Environment.ProcessorCount; + var threads = new Thread[System.Math.Max (2, pcount - 1)]; + + for (int i = 0; i < threads.Length; ++i) { + var t = new Thread (l => { + var session = new ParserSession () { + //UseJayGlobalArrays = true, + }; + + var report = new Report (ctx, Report.Printer); // TODO: Implement flush at once printer + + for (int ii = (int) l; ii < sources.Count; ii += threads.Length) { + Parse (sources[ii], module, session, report); + } + + // TODO: Merge warning regions + }); + + t.Start (i); + threads[i] = t; + } + + for (int t = 0; t < threads.Length; ++t) { + threads[t].Join (); + } + } +#endif + + public void Parse (SourceFile file, ModuleContainer module, ParserSession session, Report report) { Stream input; try { input = File.OpenRead (file.Name); } catch { - Report.Error (2001, "Source file `{0}' could not be found", file.Name); + report.Error (2001, "Source file `{0}' could not be found", file.Name); return; } // Check 'MZ' header if (input.ReadByte () == 77 && input.ReadByte () == 90) { - Report.Error (2015, "Source file `{0}' is a binary file and not a text file", file.Name); + + report.Error (2015, "Source file `{0}' is a binary file and not a text file", file.Name); input.Close (); return; } input.Position = 0; - SeekableStreamReader reader = new SeekableStreamReader (input, ctx.Settings.Encoding); + SeekableStreamReader reader = new SeekableStreamReader (input, ctx.Settings.Encoding, session.StreamReaderBuffer); + + Parse (reader, file, module, session, report); + + if (ctx.Settings.GenerateDebugInfo && report.Errors == 0 && !file.HasChecksum) { + input.Position = 0; + var checksum = session.GetChecksumAlgorithm (); + file.SetChecksum (checksum.ComputeHash (input)); + } - Parse (reader, file, module); reader.Dispose (); input.Close (); - } - - public void Parse (SeekableStreamReader reader, CompilationSourceFile file, ModuleContainer module) + } + + public static void Parse (SeekableStreamReader reader, SourceFile sourceFile, ModuleContainer module, ParserSession session, Report report) { - file.NamespaceContainer = new NamespaceContainer (null, module, null, file); + var file = new CompilationSourceFile (module, sourceFile); + module.AddTypeContainer (file); - CSharpParser parser = new CSharpParser (reader, file); + CSharpParser parser = new CSharpParser (reader, file, report, session); parser.parse (); } @@ -121,16 +174,15 @@ namespace Mono.CSharp { Location.InEmacs = Environment.GetEnvironmentVariable ("EMACS") == "t"; - var r = new Report (new ConsoleReportPrinter ()); - CommandLineParser cmd = new CommandLineParser (r); + CommandLineParser cmd = new CommandLineParser (Console.Out); var settings = cmd.ParseArguments (args); - if (settings == null || r.Errors > 0) + if (settings == null) return 1; if (cmd.HasBeenStopped) return 0; - Driver d = new Driver (new CompilerContext (settings, r)); + Driver d = new Driver (new CompilerContext (settings, new ConsoleReportPrinter ())); if (d.Compile () && d.Report.Errors == 0) { if (d.Report.Warnings > 0) { @@ -207,6 +259,11 @@ namespace Mono.CSharp return false; } + if (settings.Platform == Platform.AnyCPU32Preferred && (settings.Target == Target.Library || settings.Target == Target.Module)) { + Report.Error (4023, "Platform option `anycpu32bitpreferred' is valid only for executables"); + return false; + } + TimeReporter tr = new TimeReporter (settings.Timestamps); ctx.TimeReporter = tr; tr.StartTotal (); @@ -247,6 +304,12 @@ namespace Mono.CSharp output_file = output_file_name; } else { output_file_name = Path.GetFileName (output_file); + + if (string.IsNullOrEmpty (Path.GetFileNameWithoutExtension (output_file_name)) || + output_file_name.IndexOfAny (Path.GetInvalidFileNameChars ()) >= 0) { + Report.Error (2021, "Output file name is not valid"); + return false; + } } #if STATIC @@ -263,7 +326,7 @@ namespace Mono.CSharp // loaded assembly into compiled builder to be resolved // correctly tr.Start (TimeReporter.TimerType.CreateTypeTotal); - module.CreateType (); + module.CreateContainer (); importer.AddCompiledAssembly (assembly); tr.Stop (TimeReporter.TimerType.CreateTypeTotal); @@ -292,18 +355,12 @@ namespace Mono.CSharp if (!assembly.Create (AppDomain.CurrentDomain, AssemblyBuilderAccess.Save)) return false; - module.CreateType (); + module.CreateContainer (); loader.LoadModules (assembly, module.GlobalRootNamespace); #endif module.InitializePredefinedTypes (); - tr.Start (TimeReporter.TimerType.UsingResolve); - foreach (var source_file in ctx.SourceFiles) { - source_file.NamespaceContainer.Resolve (); - } - tr.Stop (TimeReporter.TimerType.UsingResolve); - tr.Start (TimeReporter.TimerType.ModuleDefinitionTotal); module.Define (); tr.Stop (TimeReporter.TimerType.ModuleDefinitionTotal); @@ -331,11 +388,12 @@ namespace Mono.CSharp } tr.Start (TimeReporter.TimerType.CloseTypes); - module.CloseType (); + module.CloseContainer (); tr.Stop (TimeReporter.TimerType.CloseTypes); tr.Start (TimeReporter.TimerType.Resouces); - assembly.EmbedResources (); + if (!settings.WriteMetadataOnly) + assembly.EmbedResources (); tr.Stop (TimeReporter.TimerType.Resouces); if (Report.Errors > 0) @@ -360,13 +418,12 @@ namespace Mono.CSharp public static bool InvokeCompiler (string [] args, TextWriter error) { try { - var r = new Report (new StreamReportPrinter (error)); - CommandLineParser cmd = new CommandLineParser (r, error); + CommandLineParser cmd = new CommandLineParser (error); var setting = cmd.ParseArguments (args); - if (setting == null || r.Errors > 0) + if (setting == null) return false; - var d = new Driver (new CompilerContext (setting, r)); + var d = new Driver (new CompilerContext (setting, new StreamReportPrinter (error))); return d.Compile (); } finally { Reset (); @@ -391,17 +448,11 @@ namespace Mono.CSharp public static void Reset (bool full_flag) { - CSharpParser.yacc_verbose_flag = 0; Location.Reset (); if (!full_flag) return; - AnonymousTypeClass.Reset (); - AnonymousMethodBody.Reset (); - AnonymousMethodStorey.Reset (); - SymbolWriter.Reset (); - Switch.Reset (); Linq.QueryBlock.TransparentParameter.Reset (); TypeInfo.Reset (); }