コード例 #1
0
ファイル: Tester.cs プロジェクト: parhelia512/compiler
    private static void CompileAndExecute(FileInfo file)
    {
        // We launch the compiler for given test, then execute the code,
        // and then process the compilation/execution results,
        // and finally create the TestResult instance.

        // Take the test file and its name
        string testFileName   = file.FullName;
        string binaryFileName = testFileName;

        binaryFileName = binaryFileName.Replace(@"/", @"_");
        binaryFileName = binaryFileName.Replace(@"\", @"_");
        binaryFileName = binaryFileName.Replace(@":", @"_");
        binaryFileName = binaryFileName.Replace(@"znn", @"exe");
        string shortFileName  = Path.GetFileNameWithoutExtension(testFileName);
        string outputFileName = outputDirectory + Path.DirectorySeparatorChar +
                                binaryFileName;
        // shortFileName + ".exe";

        string resPassed    = "PASSED";
        string resError     = "ERROR";
        string resNotRun    = "NOT RUN";
        string resNotPassed = "NOT PASSED";
        string resSuccess   = "SUCCESS";
        string resAbort     = "ABORT";
        string resFail      = "FAIL";
        string resBad       = "BAD TEST";
        string resBadCode   = "BAD CODE";

        // Every test file name should be built by the following template:
        //
        //    T-CC-SS-PP-XX-NN-k.znn
        //    CCSSPP-kNNN.znn
        //
        // where
        //       CC - Chapter number from the Zonnon Language Report;
        //       SS - Section number;
        //       PP - Subsection number;
        //       XX - Additional number;
        //       k  - test kind: 't' for "normal" tests,
        //                       'x' for error tests,
        //                       'c' for compilation only tests;
        //       .znn - file extension

        // if ( Path.GetExtension(testFileName) != ".znn" ) return; -- we have already selected znn-files
        // if ( shortFileName.Length < 18 ) continue;

        Statistics.overallTests++;
        System.Console.WriteLine(">>>>> {0}", shortFileName);
        System.Console.WriteLine("FULL: {0}", testFileName);

        // char testKind = shortFileName[17];
        char testKind = shortFileName[shortFileName.Length - 1];

        string compilationResult = resError;
        string executionResult   = resNotRun;
        string commonResult      = resNotPassed;

        // Prepare the "variable" part of the compiler options
        options.OutputAssembly = outputFileName;
        options.SourceFiles    = new StringCollection();
        options.SourceFiles.Add(testFileName);

        // Launch the compilation process
        CompilerResults results = null;
        Exception       compilationException = null;
        Exception       executionException   = null;

        try
        {
            results = compiler.CompileAssemblyFromFile(options, testFileName);

            if (results.NativeCompilerReturnValue == 0)
            {
                compilationResult = resSuccess;
                Statistics.compilationSucceed++;
            }
            else
            {
                compilationResult = resError;
                Statistics.compilationFailed++;
            }

            // Print compiler messages
            // (if necessary we can redirect stdout to a disk file to see diagnostics)

            // foreach ( CompilerError e in results.Errors )
            // {
            //     Console.Write(e.ErrorNumber);
            //     Console.Write(": ");
            //  // Console.Write(e.FileName);
            //     Console.Write('(');
            //     Console.Write(e.Line);
            //     Console.Write(',');
            //     Console.Write(e.Column);
            //     Console.Write("): ");
            //     Console.WriteLine(e.ErrorText);
            // }

            int errCount = results.Errors.Count;
            if (errCount > 1)
            {
                for (int j = 0; j < errCount; j++)
                {
                    CompilerError e = results.Errors[j];
                    if (int.Parse(e.ErrorNumber) == (int)ErrorKind.EndOfMessages)
                    {
                        if (j == 0)
                        {
                            continue;         // No Zonnon messages BUT some CCI messages; continue
                        }
                        break;                // End of Zonnon error messages; don't issue CCI messages
                    }

                    Console.Write(e.ErrorNumber);
                    Console.Write(": ");
                    // Console.Write(e.FileName);
                    Console.Write('(');
                    Console.Write(e.Line);
                    Console.Write(',');
                    Console.Write(e.Column);
                    Console.Write("): ");
                    Console.WriteLine(e.ErrorText);
                }
            }
        }
        catch (Exception e)
        {
            compilationResult    = resAbort;
            compilationException = e;
            Statistics.compilationAbort++;
        }

        if (testKind == 'c' || testKind == 'C')
        {
            Statistics.compilationNotPlanned++;
        }
        if (compilationResult == resSuccess && (testKind == 't' || testKind == 'T'))
        {
            // Launch the compiled code
            try
            {
                Assembly assemblyToRun          = Assembly.LoadFrom(outputFileName);
                System.Reflection.Module module = assemblyToRun.GetModules(false)[0];
                System.Type type = module.GetType("Zonnon.Main");

                if (type == null)
                {
                    executionResult = resBadCode;
                }
                else
                {
                    MethodInfo mainMethod = type.GetMethod("Main");

                    if (mainMethod == null)
                    {
                        executionResult = resBadCode;
                        Statistics.executionNotPlanned++;
                    }
                    else
                    {
                        object res = mainMethod.Invoke(null, null);
                        if (res is int && (int)res == 1)
                        {
                            executionResult = resSuccess;
                            Statistics.executionSucceed++;
                        }
                        else
                        {
                            executionResult = resFail;
                            Statistics.executionFailed++;
                        }
                    }
                }
            }
            catch (Exception e)
            {
                // System.Console.WriteLine(e.StackTrace);
                // System.Console.WriteLine("================================");
                // System.Console.WriteLine(e.Source);
                // System.Console.WriteLine("================================");
                // System.Console.WriteLine(e.InnerException.StackTrace);

                System.Console.WriteLine(e.Message);

                executionResult    = resAbort;
                executionException = e;
                Statistics.executionAbort++;
            }
        }

        switch (testKind)
        {
        case 't':
        case 'T':

            if (compilationResult == resSuccess && executionResult == resSuccess)
            {
                commonResult = resPassed;
                Statistics.successfulTests++;
            }
            else
            {
                commonResult = resNotPassed;
                Statistics.failedTests++;
            }
            break;

        case 'x':
        case 'X':

            if (compilationResult != resSuccess && compilationResult != resAbort)
            {
                commonResult = resPassed;
                Statistics.successfulTests++;
            }
            else
            {
                commonResult = resNotPassed;
                Statistics.failedTests++;
            }
            break;

        case 'c':
        case 'C':

            if (compilationResult == resSuccess)
            {
                commonResult = resPassed;
                Statistics.successfulTests++;
            }
            else
            {
                commonResult = resNotPassed;
                Statistics.failedTests++;
            }
            break;

        default:

            commonResult = resBad;
            break;
        }

        // System.Console.WriteLine(">>>>> {0} FINISHED",shortFileName);
        System.Console.WriteLine("      Compilation Result: {0}", compilationResult);
        System.Console.WriteLine("      Execution   Result: {0}", executionResult);
        System.Console.WriteLine("      Common      Result: {0}", commonResult);

        // Create the report for the passed test
        TestResult testResult = new TestResult();  // will add the new node to the common list

        testResult.testName = Path.GetDirectoryName(testFileName) + Path.DirectorySeparatorChar +
                              Path.GetFileNameWithoutExtension(testFileName);
        testResult.compilerDateTime  = compilerDateTime;
        testResult.compilerVersion   = compilerVersion;
        testResult.runDateTime       = runDateTime;
        testResult.compilationResult = compilationResult;
        testResult.executionResult   = executionResult;
        testResult.commonResult      = commonResult;

        testResult.compilerResults = results;

        testResult.compilationException = compilationException;
        testResult.executionException   = executionException;
    }
コード例 #2
0
ファイル: Main.cs プロジェクト: zonnonproject/compiler
    public static int Main(string[] args)
    {
        // Process compiler options
        ZonnonCompilerParameters options = parseCommandLineParameters(args);

        // Display help and do nothing
        if (options.DisplayHelp)
        {
            #region Help
            System.Console.WriteLine("zc.exe [parameters...] source file [source files ...]");
            System.Console.WriteLine("Example: zc.exe /entry:run test.znn");
            System.Console.WriteLine("");
            System.Console.WriteLine("   /file:source-file-name   ");
            System.Console.WriteLine("                  alternative way to pass source-file names under Linux");
            System.Console.WriteLine("                  when it starts with /. E.g. for /root/q.znn use");
            System.Console.WriteLine("                  /file:/root/q.znn");
            System.Console.WriteLine("");
            System.Console.WriteLine("   /out:assembly-name-without-extension");
            System.Console.WriteLine("                  the name of output assembly.");
            System.Console.WriteLine("                  If parameter is not specified ");
            System.Console.WriteLine("                  then the name of the (first) source file is ");
            System.Console.WriteLine("                  taken (without extension).");
            System.Console.WriteLine("");
            System.Console.WriteLine("   /entry:startup-module-name ");
            System.Console.WriteLine("                  program module (in Zonnon terminology) the ");
            System.Console.WriteLine("                  execution should start from.");
            System.Console.WriteLine("");
            System.Console.WriteLine("   /ref:assembly-file  ");
            System.Console.WriteLine("                  the assembly which is used in the program ");
            System.Console.WriteLine("                  (via import declarations). ");
            System.Console.WriteLine("");
            System.Console.WriteLine("   /version:0.0.0.0  ");
            System.Console.WriteLine("                  sets versions of the assembly and the file ");
            System.Console.WriteLine("");
            System.Console.WriteLine("   /safe          affects the way of handling exceptions in the ");
            System.Console.WriteLine("                  executable programs generated by the compiler.");
            System.Console.WriteLine("                  If /safe parameter is specified then no stack ");
            System.Console.WriteLine("                  is printed out but just the message about the ");
            System.Console.WriteLine("                  exception.");
            System.Console.WriteLine("");
            System.Console.WriteLine("   /xml           compiler generates xml file with semantic ");
            System.Console.WriteLine("                  infromation of the entire compilation.");
            System.Console.WriteLine("");
            System.Console.WriteLine("   /quiet         compiler doesn't output its title");
            System.Console.WriteLine("");
            System.Console.WriteLine("   /mathopt       compilation with mathematical optimizations");
            System.Console.WriteLine("");
            System.Console.WriteLine("   /compute       use OpenCL");
            #endregion
            return(0);
        }

        // If it is not suppressed by the 'quiet' option, print the compiler title and info.
        if (!options.Quiet)
        {
            System.Reflection.Assembly assembly = typeof(ETH.Zonnon.ZonnonCompiler).Assembly;

            object[] attributes = assembly.GetCustomAttributes(false);

            string version   = assembly.GetName(false).Version.ToString();
            string title     = null;
            string copyright = null;

            DateTime dt   = File.GetLastWriteTime(assembly.GetModules()[0].FullyQualifiedName);
            string   date = dt.ToLongDateString();
            string   time = dt.ToLongTimeString();

            // We take compiler title & copyright from the corresponding
            // assembly attributes (see Compiler's AssemblyInfo.cs file).
            for (int i = 0, n = attributes.Length; i < n; i++)
            {
                AssemblyTitleAttribute titleAttr = attributes[i] as AssemblyTitleAttribute;
                if (titleAttr != null)
                {
                    title = titleAttr.Title; continue;
                }

                AssemblyCopyrightAttribute copyrightAttr = attributes[i] as AssemblyCopyrightAttribute;
                if (copyrightAttr != null)
                {
                    copyright = copyrightAttr.Copyright;
                }
            }

            if (copyright == null)
            {
                copyright = "(c) ETH Zurich";
            }
            if (title == null)
            {
                title = "ETH Zonnon compiler (rotor/mono edition)";
                System.Console.WriteLine("{0},\n\rVersion {1} of {2}, {3}", title, version, date, time);
            }
            else
            {
                System.Console.WriteLine("{0}, Version {1} of {2}, {3}", title, version, date, time);
            }

            // System.Reflection.Assembly rtl = typeof(Zonnon.RTL.Input).Assembly;
            // string rtl_version = rtl.GetName(false).Version.ToString();
            // System.Console.WriteLine("Zonnon RTL, Version {0}",rtl_version);

            System.Console.WriteLine("{0}", copyright);
        }

        // Print messages if there were errors in compiler options,
        // and complete the execution.
        if (options.Messages.Count > 0)
        {
            for (int i = 0, n = options.Messages.Count; i < n; i++)
            {
                System.Console.WriteLine(options.Messages[i]);
            }
            return(1);
        }

        // Create the Zonnon compiler
        ETH.Zonnon.ZonnonCompiler compiler = new ETH.Zonnon.ZonnonCompiler();
///     compiler.options = options;
        //System.Diagnostics.Debugger.Launch();
        // Launch the compilation process
        CompilerResults results;

#if TRACE
        System.Console.WriteLine("START compilation");
#endif
        switch (options.SourceFiles.Count)
        {
        case 0:       // NO sources; message has been issued before
            return(1);

        case 1:       // only ONE source file
            results = compiler.CompileAssemblyFromFile(options, options.SourceFiles[0]);
            break;

        default:      // SEVERAL source files
        {
            string[] sources = new string[options.SourceFiles.Count];
            options.SourceFiles.CopyTo(sources, 0);
            results = compiler.CompileAssemblyFromFileBatch(options, sources);
            break;
        }
        }
#if TRACE
        System.Console.WriteLine("END compilation");
#endif

        // Print compiler messages
//		XmlDocument doc = null;
//		XmlNode report = null;
//		XmlNode result = null;
//		if(options.ExportReport != null)
//		{
//			doc = new XmlDocument();
//			report = doc.CreateNode(XmlNodeType.Element, "report", "");
//			result = doc.CreateNode(XmlNodeType.Element, "result", "");
//			report.AppendChild(result);
//		}
#if TRACE
        System.Console.WriteLine("PASS Creating TextWriter");
#endif
        TextWriter doc = null;
        if (options.ExportReport != null)
        {
            doc = new StreamWriter(options.ExportReport);
#if TRACE
            System.Console.WriteLine("PASS TextWriter created");
#endif
        }

        int errCount     = results.Errors.Count;
        int trueErrCount = results.Errors.Count;
        for (int i = 0, n = results.Errors.Count; i < n; i++)
        {
            if (int.Parse(results.Errors[i].ErrorNumber) == 0)
            {
                trueErrCount--;
            }
        }


        if (trueErrCount == 0)    // Only "end of messages" message
        {
#if TRACE
            System.Console.WriteLine("PASS report success");
#endif
            // ERROR.Success();
            Console.WriteLine("Compilation completed successfully");
            if (doc != null)
            {
                doc.WriteLine("success");
            }
        }
        else
        {
#if TRACE
            System.Console.WriteLine("PASS report failures");
#endif
            // foreach ( CompilerError e in results.Errors )
            int j = 0;

            if (doc != null)
            {
                doc.WriteLine("failure");
            }
//			XmlNode messages = null;
//			if(report != null)
//			{
//				result.InnerText = "failure";
//				messages = doc.CreateNode(XmlNodeType.Element, "messages", "");
//				report.AppendChild(messages);
//			}

            for (int i = 0, n = errCount; i < n; i++)
            {
#if TRACE
                System.Console.WriteLine("PASS report one problem");
#endif

                CompilerError e = results.Errors[i];

                // The idea of the code below is to prevent the output of CCI messages
                // in case there are some compiler messages. (This means the compiler
                // itself has already issued messages, and there is no need to issue
                // cryptic CCI messages which typically seem to be unrelated to the source
                // (from the user's point of view).

                int x = int.Parse(e.ErrorNumber);
                if (x == 0)
                {
                    continue;
                }
#if TRACE
                System.Console.WriteLine("PASS report with code {0}", x);
#endif

                if (x >= 2000)
                {
                    j++;                               // count only non-warning messages
                }
                if (x == (int)ErrorKind.EndOfMessages) // special final compiler message
                {
                    if (j == 0)
                    {
                        continue;         // No Zonnon messages BUT some CCI messages; continue
                    }
                    break;                // End of Zonnon error messages; don't issue CCI messages
                }
                Console.Write(e.ErrorNumber);
                Console.Write(": ");
                Console.Write(e.FileName);
                Console.Write('(');
                Console.Write(e.Line);
                Console.Write(',');
                Console.Write(e.Column);
                Console.Write("): ");
                Console.WriteLine(e.ErrorText);

#if TRACE
                System.Console.WriteLine("PASS write problem to XML");
#endif

                // Prepare an XML version of the error report if needed
                if (doc != null)
                {
                    doc.Write(e.ErrorNumber);
                    doc.Write(", ");
                    doc.Write(e.FileName);
                    doc.Write(", ");
                    doc.Write(e.Line);
                    doc.Write(", ");
                    doc.WriteLine(e.ErrorText);
                }
//				if(messages != null)
//				{
//					XmlNode message = doc.CreateNode(XmlNodeType.Element, "message", "");
//					message.Attributes.Append(doc.CreateAttribute("ErrorNumber"));
//					message.Attributes["ErrorNumber"].Value = e.ErrorNumber;
//					message.Attributes.Append(doc.CreateAttribute("FileName"));
//					message.Attributes["FileName"].Value = e.FileName;
//					message.Attributes.Append(doc.CreateAttribute("Line"));
//					message.Attributes["Line"].Value = e.Line.ToString();
//					message.Attributes.Append(doc.CreateAttribute("Column"));
//					message.Attributes["Column"].Value = e.Column.ToString();
//					message.Attributes.Append(doc.CreateAttribute("ErrorText"));
//					message.Attributes["ErrorText"].Value = e.ErrorText;
//					messages.AppendChild(message);
//				}
#if TRACE
                System.Console.WriteLine("PASS end of problem");
#endif
            }
#if TRACE
            System.Console.WriteLine("PASS end of all problems");
#endif
        }
        if (doc != null)
        {
            doc.Close();
        }
//		if(doc != null)
//		{ //Save report
//			System.Xml.XmlTextWriter writer = new System.Xml.XmlTextWriter(options.ExportReport, System.Text.Encoding.UTF8);
//			writer.Formatting = System.Xml.Formatting.Indented;
//			writer.WriteStartDocument(true);
//			report.WriteTo(writer);
//			writer.Flush();
//			writer.Close();
//		}
        // Return the result of the compiler's invokation
#if TRACE
        System.Console.WriteLine("EXIT compiler");
#endif
        return(results.NativeCompilerReturnValue);
    }