Example #1
0
        private void HandleCompilerErrors(CompilerException ex, ScriptCompilerLogger logger)
        {
            logger.Error(ex);
            StringBuilder sb = new StringBuilder();

            sb.AppendLine(ex.Message);
            sb.AppendLine();
            sb.AppendLine($"Text: \"{ex.Text}\"");
            sb.AppendLine("Line: " + ex.Line);
            sb.AppendLine("Column: " + ex.Column);
            var _ = MetroMessageBox.Show("Compilation Failed", sb.ToString(), MetroMessageBox.MessageBoxButtons.Ok);

            if (txtScript.TextArea.Focus())
            {
                txtScript.TextArea.Caret.Offset = txtScript.Document.GetOffset(ex.Line, ex.Column);
                txtScript.ScrollToLine(ex.Line);
            }
        }
Example #2
0
        private ScriptData CompileScripts(string code, IProgress <int> progress, ScriptCompilerLogger logger, ParsingExceptionCollector collector)
        {
            using (IReader reader = _streamManager.OpenRead())
            {
                // Set up the lexer.
                logger.Information("Running the lexer...");
                ICharStream  stream = CharStreams.fromstring(code);
                HS_Gen1Lexer lexer  = new HS_Gen1Lexer(stream);
                lexer.AddErrorListener(collector);
                ITokenStream tokens = new CommonTokenStream(lexer);

                // Set up the parser.
                logger.Information("Running the parser...");
                HS_Gen1Parser parser = new HS_Gen1Parser(tokens);
                parser.AddErrorListener(collector);

                // Parse the scripts.
                parser.BuildParseTree = true;
                IParseTree tree = parser.hsc();

                // Throw an exception if ANTLR reports parsing or lexing errors.
                if (collector.ContainsExceptions)
                {
                    logger.Information("The collector contained errors. Cancelling the process...");
                    throw new OperationCanceledException($"Parsing Failed! {collector.ExceptionCount} Exceptions occured during the parsing process.");
                }

                // Load the context.
                var context = _scriptFile.LoadContext(reader, _cashefile);

                // Run the compiler.
                logger.Information("Running the compiler...");
                bool           outputDebugData = App.AssemblyStorage.AssemblySettings.OutputCompilerDebugData;
                ScriptCompiler compiler        = new ScriptCompiler(_cashefile, _buildInfo, _opcodes, context, progress, logger, outputDebugData);
                ParseTreeWalker.Default.Walk(compiler, tree);
                return(compiler.Result());
            }
        }
Example #3
0
        private void HandleParsingErrors(OperationCanceledException ex, ParsingExceptionCollector collector, ScriptCompilerLogger logger)
        {
            StringBuilder sb = new StringBuilder();

            ParsingExceptionInformation[] errors = collector.GetExceptions().ToArray();
            int counter = errors.Length <= 10 ? errors.Length : 10;

            for (int i = 0; i < counter; i++)
            {
                string errorMessage = $"{i + 1}: {errors[i].Message}, Line: {errors[i].Line}, Column: {errors[i].Column}";
                sb.AppendLine(errorMessage);
                logger.Error("Parsing Error " + errorMessage);
            }

            var _ = MetroMessageBox.Show("Parsing Failed", sb.ToString(), MetroMessageBox.MessageBoxButtons.Ok);

            if (txtScript.TextArea.Focus())
            {
                // Go to the first error.
                var firstError = errors[0];
                if (firstError.Exception != null && firstError.Exception.OffendingToken != null)
                {
                    txtScript.Select(firstError.Exception.OffendingToken.StartIndex, firstError.Exception.OffendingToken.StopIndex + 1 - firstError.Exception.OffendingToken.StartIndex);
                }
                else
                {
                    txtScript.TextArea.Caret.Offset = txtScript.Document.GetOffset(firstError.Line, firstError.Column);
                }
                txtScript.ScrollToLine(firstError.Line);
            }
        }
Example #4
0
        private async void CompileClick(object sender, RoutedEventArgs e)
        {
            // Logger Setup
            string folder = "Compiler";

            if (!Directory.Exists(folder))
            {
                Directory.CreateDirectory(folder);
            }
            string logPath = Path.Combine(folder, "ScriptCompiler.log");

            using (var logStream = File.Create(logPath))
            {
                // Create the logger and the exception collector. They are used for debugging.
                var traceListener      = new TextWriterTraceListener(logStream);
                var logger             = new ScriptCompilerLogger(traceListener);
                var exceptionCollector = new ParsingExceptionCollector();
                logger.Information($"Attempting to compile: {_scriptFile.Name}, Time: {DateTime.Now}");
                try
                {
                    // Get the script file.
                    string hsc = txtScript.Text;

                    // Measure the time it took to compile the scripts.
                    var stopWatch = Stopwatch.StartNew();

                    // Compile the scripts.
                    ScriptData compileData = await Task.Run(() => CompileScripts(hsc, _progress, logger, exceptionCollector));

                    stopWatch.Stop();
                    var    timeSpan           = stopWatch.Elapsed;
                    string compilationMessage = $"The scripts were successfully compiled in {Math.Round(timeSpan.TotalSeconds, 3)} seconds.";
                    logger.Information(compilationMessage);

                    // Show the message box.
                    var saveResult = MetroMessageBox.Show("Scripts Compiled", compilationMessage
                                                          + "\nWARNING: This compiler is not 100% accurate and could corrupt the map in rare cases. Making a backup before proceeding is advisable."
                                                          + "\n\nDo you want to save the changes to the file?", MetroMessageBox.MessageBoxButtons.YesNo);
                    if (saveResult == MetroMessageBox.MessageBoxResult.Yes)
                    {
                        //TODO: Move this to its own function.
                        await Task.Run(() =>
                        {
                            using (IStream stream = _streamManager.OpenReadWrite())
                            {
                                _scriptFile.SaveScripts(compileData, stream, _progress);
                                _cashefile.SaveChanges(stream);
                            }
                        });

                        RefreshMeta();
                        StatusUpdater.Update("Scripts saved");
                    }
                }
                // Handle Parsing Errors.
                catch (OperationCanceledException opEx)
                {
                    if (exceptionCollector.ContainsExceptions)
                    {
                        HandleParsingErrors(opEx, exceptionCollector, logger);
                    }
                    else
                    {
                        MetroMessageBox.Show("Operation Canceled", opEx.Message);
                    }
                }
                // Handle Compiler Errors.
                catch (CompilerException compEx)
                {
                    HandleCompilerErrors(compEx, logger);
                }
                finally
                {
                    logger.Flush();
                    ResetProgressBar();
                }
            }
        }