Java tutorial
/* * [The "BSD license"] * Copyright (c) 2012-2013 Marcel Schaible * All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * 3. The name of the author may not be used to endorse or promote products * derived from this software without specific prior written permission. * * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package org.smallpearl.compiler; import org.antlr.v4.runtime.ANTLRFileStream; import org.antlr.v4.runtime.CommonTokenStream; import org.antlr.v4.runtime.ParserRuleContext; import org.stringtemplate.v4.*; import java.io.FileNotFoundException; import java.util.ArrayList; import java.util.List; import java.io.PrintWriter; import java.io.IOException; import java.io.StringWriter; public class Compiler { static String version = "v0.2"; static String grammarName; static String startRuleName; static List<String> inputFiles = new ArrayList<String>(); static boolean printAST = false; static boolean gui = false; static String psFile = null; static String outputFilename = null; static boolean showTokens = false; static boolean trace = true; static boolean diagnostics = false; static String encoding = null; static boolean inspectAST = false; static boolean SLL = false; static boolean nosemantic = true; static int verbose = 1; static String groupFile = "SmallPearlCpp.stg"; static boolean lineSeparatorHasToBeModified = true; static boolean dumpDFA = false; static boolean dumpSymbolTable = true; static boolean debug = false; static boolean debugSTG = false; static boolean stacktrace = false; static boolean exportSystemPart = false; static int noOfErrors = 0; static int noOfWarnings = 0; static int warninglevel = 255; static int lineWidth = 80; public static void main(String[] args) throws Exception { int i; if (args.length < 1) { printHelp(); return; } if (!checkAndProcessArguments(args)) { return; } for (i = 0; i < inputFiles.size(); i++) { SmallPearlLexer lexer = null; try { lexer = new SmallPearlLexer(new ANTLRFileStream(inputFiles.get(i))); } catch (IOException ex) { System.out.println("Error:" + ex.getMessage()); System.exit(-2); } CommonTokenStream tokens = new CommonTokenStream(lexer); SmallPearlParser parser = new SmallPearlParser(tokens); parser.setBuildParseTree(true); //////////////////////////////////////////////////////////////////////////////////////////////////////////////// // Start Analysis //////////////////////////////////////////////////////////////////////////////////////////////////////////////// System.out.println("Start compiling of:" + inputFiles.get(i).toString()); System.out.println("Performing syntax check"); ParserRuleContext tree = parser.program(); System.out.flush(); if (printAST) { System.out.println("Parse tree:"); System.out.println(tree.toStringTree(parser)); } if (inspectAST) { System.out.println("Inspect Parse tree:"); // visualize parse tree in dialog box tree.inspect(parser); System.out.println("Press any key"); try { int ch = System.in.read(); } catch (IOException ex) { } } if (dumpDFA) { parser.dumpDFA(); } if (parser.getNumberOfSyntaxErrors() <= 0) { BuildSymbolTableVisitor buildSymbolTableVisitor = new BuildSymbolTableVisitor(verbose); buildSymbolTableVisitor.visit(tree); if (!nosemantic) { SemanticCheckVisitor semanticCheckVisitor = new SemanticCheckVisitor(verbose); semanticCheckVisitor.visit(tree); } if (exportSystemPart) { SystemPartExport(lexer.getSourceName(), tree); } // try { CppGenerate(lexer.getSourceName(), tree); /* } catch(Exception ex) { System.err.println(ex.getMessage()); System.err.println("Compilation aborted."); if ( stacktrace ) { System.err.println( getStackTrace(ex)); } System.exit(-1); } */ if (dumpSymbolTable) { SymbolTable symtab = SymbolTable.getSymbolTable(); System.out.println(symtab); symtab.getGlobalsDeclarations(); } } noOfErrors = parser.getNumberOfSyntaxErrors(); System.out.flush(); System.out.println("Number of errors in " + inputFiles.get(i) + " encountered: " + noOfErrors); if (noOfErrors == 0) { System.exit(0); } else { System.exit(1); } } } //////////////////////////////////////////////////////////////////////////////////////////////////////////////// public static void printHelp() { System.err.println("java org.smallpearl.compiler \n" + " Options: \n" + " --help Print this help message \n" + " --version Print version information \n" + " --verbose Print more information \n" + " --quiet Be quiet \n" + " --trace \n" + " --nosemantic Disable semantic checker \n" + " --printAST Print Abtract Syntax Tree \n" + " --inspectAST Show graphical representation \n" + " of the Abtract Syntax Tree \n" + " --dumpDFA Print DFA \n" + " --dumpSymbolTable Print the symboltable \n" + " --debug Generate debug information \n" + " --debugSTG Start the stg debug gui \n" + " --stacktrace Print stacktrace in case of an \n" + " exception \n" + " --warninglevel <level> Set the warning level \n" + " Level 0: no warning \n" + " Level 255: all warnings (default) \n" + " --export-systempart Export the System part into a xml \n" + " file \n" + " --output <filename> Filename of the generated code \n" + " infile ... \n"); } //////////////////////////////////////////////////////////////////////////////////////////////////////////////// public static boolean checkAndProcessArguments(String[] args) { int i = 0; while (i < args.length) { String arg = args[i]; i++; if (arg.charAt(0) != '-') { // input file name inputFiles.add(arg); continue; } if (arg.equals("--help")) { printHelp(); System.exit(0); } else if (arg.equals("--printAST")) { printAST = true; } else if (arg.equals("--inspectAST")) { inspectAST = true; } else if (arg.equals("--gui")) { gui = true; } else if (arg.equals("--tokens")) { showTokens = true; } else if (arg.equals("--trace")) { trace = true; } else if (arg.equals("--SLL")) { SLL = true; } else if (arg.equals("--nosemantic")) { nosemantic = true; } else if (arg.equals("--diagnostics")) { diagnostics = true; } else if (arg.equals("--dumpDFA")) { dumpDFA = true; } else if (arg.equals("--dumpSymbolTable")) { dumpSymbolTable = true; } else if (arg.equals("--debug")) { debug = true; } else if (arg.equals("--debugSTG")) { debugSTG = true; } else if (arg.equals("--stacktrace")) { stacktrace = true; } else if (arg.equals("--export-systempart")) { exportSystemPart = true; } else if (arg.equals("--output")) { if (i >= args.length) { System.err.println("missing filename on --output"); return false; } outputFilename = args[i]; i++; continue; } else if (arg.equals("-encoding")) { if (i >= args.length) { System.err.println("missing encoding on -encoding"); return false; } encoding = args[i]; i++; } else if (arg.equals("--ps")) { if (i >= args.length) { System.err.println("missing filename on --ps"); return false; } psFile = args[i]; i++; } else if (arg.equals("--version")) { System.out.println("OpenPEARL90 compiler version " + version); i++; } else if (arg.equals("--warninglevel")) { if (i >= args.length) { System.err.println("missing warning level on --warninglevel"); return false; } warninglevel = Integer.parseInt(args[i]); i++; } } return true; } private static Void CppGenerate(String sourceFileName, ParserRuleContext tree) { CppCodeGeneratorVisitor cppCodeGenerator = new CppCodeGeneratorVisitor(sourceFileName, groupFile, verbose, debug); ST code = cppCodeGenerator.visit(tree); if (debugSTG) { System.out.println("Press a key to continue"); code.inspect(); try { int ch = System.in.read(); } catch (IOException ex) { } } if (outputFilename != null) { try { if (outputFilename.lastIndexOf(".") == -1) { outputFilename += ".cc"; } if (verbose > 0) { System.out.println("Generating output file " + outputFilename); } PrintWriter writer = new PrintWriter(outputFilename, "UTF-8"); writer.println(code.render(lineWidth)); writer.close(); } catch (IOException e) { System.err.println("Problem writing to the file " + outputFilename); } } else { if (verbose > 0) { System.out.println("Generated output:"); } System.out.println(code.render(lineWidth)); } return null; } private static Void SystemPartExport(String sourceFileName, ParserRuleContext tree) { String outputFileName = sourceFileName; SystemPartExporter systemPartExporter = new SystemPartExporter(sourceFileName, verbose, debug); ST systemPart = systemPartExporter.visit(tree); if (debugSTG) { System.out.println("Press a key to continue"); systemPart.inspect(); try { int ch = System.in.read(); } catch (IOException ex) { } } outputFileName = outputFileName.substring(0, outputFileName.lastIndexOf('.')); outputFileName = outputFileName.concat(".xml"); try { if (verbose > 0) { System.out.println("Generating export file " + outputFileName); } PrintWriter writer = new PrintWriter(outputFileName, "UTF-8"); writer.println(systemPart.render(lineWidth)); writer.close(); } catch (IOException e) { System.err.println("Problem writing to the export file " + outputFileName); } return null; } static String getStackTrace(Throwable t) { StringWriter sw = new StringWriter(); PrintWriter pw = new PrintWriter(sw, true); t.printStackTrace(pw); pw.flush(); sw.flush(); return sw.toString(); } }