Fixed lot of random bugs. Added code generate strings for expr's.
[repair.git] / Repair / RepairCompiler / MCC / Compiler.java
1 package MCC;
2
3 import java.io.*;
4 import java.util.*;
5 import MCC.IR.*;
6
7 /**
8  * The main compiler module, which does the following:
9  * <ul>
10  *  <li>
11  *   nothing.
12  *  </li> 
13  * <ul>
14  *
15  * @author <b>Daniel Roy</b> droy (at) mit (dot) edu
16  * @version %I, %G 
17  */
18
19 public class Compiler {
20     public static boolean REPAIR=true;
21     
22     public static void main(String[] args) {
23         State state = null;
24         boolean success = true;
25         CLI cli = new CLI();
26         cli.parse(args);
27         printArgInfo(cli); // prints debugging information and warning
28
29         state = new State();
30         State.currentState = state;
31         State.debug = cli.debug;
32         State.verbose = cli.verbose;
33         State.infile = cli.infile;
34         State.outfile = cli.outfile;
35
36         /*
37          * added: terminates with an error message if no input file
38          * specified at command line
39          */
40
41         System.out.println("\nMCC v0.0.1 - MIT LCS (Author: Daniel Roy, Brian Demsky)");
42
43         if (cli.infile == null) {
44             System.err.println("\nError: no input file specified");
45             System.exit(-1);
46         }
47         
48         if (cli.target == CLI.ASSEMBLY || cli.target == CLI.DEFAULT) {
49             if (state.debug) {
50                 System.out.println("Compiling " + cli.infile + ".");
51             }
52
53             success = scan(state) || error(state, "Scanning failed, not attempting to parse.");
54             success = parse(state) || error(state, "Parsing failed, not attempting semantic analysis.");
55             success = semantics(state) || error(state, "Semantic analysis failed, not attempting variable initialization.");
56
57             if (REPAIR) {
58                 (new ImplicitSchema(state)).update();
59                 Termination t=new Termination(state);
60             }
61             
62             (new DependencyBuilder(state)).calculate();
63             
64             try {
65                 Vector nodes = new Vector(state.constraintnodes.values());
66                 nodes.addAll(state.rulenodes.values());
67
68                 FileOutputStream dotfile;
69                 dotfile = new FileOutputStream(cli.infile + ".dependencies.edgelabels.dot");
70                 GraphNode.useEdgeLabels = true;
71                 GraphNode.DOTVisitor.visit(dotfile, nodes);
72                 dotfile.close();
73
74                 dotfile = new FileOutputStream(cli.infile + ".dependencies.dot");
75                 GraphNode.useEdgeLabels = false;
76                 GraphNode.DOTVisitor.visit(dotfile, nodes);                
77                 dotfile.close();
78             } catch (Exception e) {
79                 e.printStackTrace();
80                 System.exit(-1);
81             }
82             
83             try {
84                 FileOutputStream gcode = new FileOutputStream(cli.infile + ".cc");
85
86                 // do model optimizations
87                 //(new Optimizer(state)).optimize();
88
89                 NaiveGenerator ng = new NaiveGenerator(state);
90                 ng.generate(gcode);
91                 //WorklistGenerator wg = new WorklistGenerator(state);
92                 //wg.generate(gcode);
93                 gcode.close();
94             } catch (Exception e) {
95                 e.printStackTrace();
96                 System.exit(-1);
97             }
98             
99             if (state.debug) {
100                 System.out.println("Compilation of " + state.infile + " successful.");
101                 System.out.println("#SUCCESS#");
102             }
103         } else if (cli.target == CLI.INTER) {
104             if (state.debug) {
105                 System.out.println("Semantic analysis for " + cli.infile + ".");
106             }
107
108             success = scan(state) || error(state, "Scanning failed, not attempting to parse.");
109             success = parse(state) || error(state, "Parsing failed, not attempting semantic analysis.");
110             success = semantics(state) || error(state, "Semantic analysis failed.");
111
112             if (state.debug) {
113                 System.out.println("Semantic analysis of " + state.infile + " successful.");
114                 System.out.println("#SUCCESS#");
115             }
116         } else if (cli.target == CLI.PARSE) {
117             if (state.debug) {
118                 System.out.println("Parsing " + cli.infile + ".");
119             }
120
121             success = scan(state) || error(state, "Scanning failed, not attempting to parse.");
122             success = parse(state) || error(state, "Parsing failed.");
123
124             if (state.debug) {
125                 System.out.println("Parsing of " + state.infile + " successful.");
126                 System.out.println("#SUCCESS#");
127             }
128         } else if (cli.target == CLI.SCAN) {
129             if (state.debug) {
130                 System.out.println("Scanning " + cli.infile + ".");
131             }
132
133             success = scan(state) || error(state, "Scanning failed.");
134
135             if (state.debug) {
136                 System.out.println("Scanning of " + state.infile + " successful.");
137                 System.out.println("#SUCCESS#");
138             }
139         }
140     }
141
142     private static void printArgInfo(CLI cli) {
143         if (cli.debug) {
144             System.out.println("Printing debugging information...");
145             System.out.println("Input filename: " + cli.infile);
146             System.out.println("Output filename: " + cli.outfile);
147             System.out.print("Target: ");
148
149             switch(cli.target) {
150             case CLI.ASSEMBLY:
151                 System.out.println("ASSEMBLY");
152                 break;
153             case CLI.DEFAULT:
154                 System.out.println("DEFAULT");
155                 break;
156             case CLI.INTER:
157                 System.out.println("INTER");
158                 break;
159             case CLI.LOWIR:
160                 System.out.println("LOWIR");
161                 break;
162             case CLI.PARSE:
163                 System.out.println("PARSE");
164                 break;
165             case CLI.SCAN:
166                 System.out.println("SCAN");
167                 break;
168             default:
169                 System.out.println("not recognized");
170                 break;
171             }
172
173             for (int i = 0; i < cli.opts.length; i++) {
174                 if (cli.opts[i]) {
175                     System.out.println("Optimization");
176                 }
177             }
178         }
179
180         for (int i = 0; i < cli.extraopts.size(); i++) {
181             System.err.println("Warning: optimization \"" +
182                                cli.extraopts.elementAt(i) +
183                                "\" not recognized");
184         }
185
186         for (int i = 0; i < cli.extras.size(); i++) {
187             System.err.println("Warning: option \"" +
188                                cli.extras.elementAt(i) +
189                                "\" not recognized");
190         }
191     }
192
193     private static boolean error(State state, String error) {
194         System.err.println(error);
195         if (state.debug) {
196             System.out.println("#ERROR#");
197         }
198         System.exit(-1);
199         return false;
200     }
201
202     public static boolean semantics(State state) {
203         SimpleIRErrorReporter er = new SimpleIRErrorReporter();
204         SemanticChecker checker = new SemanticChecker();
205         boolean ok = true;
206
207         try {
208             ok = checker.check(state, er);
209         } catch (Exception e) {
210             er.report(null, e.toString());
211             e.printStackTrace();
212             er.error = true;
213         }
214
215         if (!ok) {
216             er.report(null, "Semantic check failed.");
217         }
218
219         System.out.print(er.toString());
220
221         return !er.error;
222     }
223
224     public static void debugMessage(int level, String s) {
225         if (State.currentState.verbose >= level) {
226             System.err.println(s);
227         }
228     }
229
230     public static boolean parse(State state) {
231         
232         /* parse structure file */
233         try {
234             debugMessage(1, "Parsing structure file");
235             LineCount.reset();
236             FileInputStream infile = new FileInputStream(state.infile + ".struct");
237             TDLParser parser = new TDLParser(new Lexer(infile));
238             CUP$TDLParser$actions.debug = state.verbose > 1 ;
239             state.ptStructures = (ParseNode) parser.parse().value;
240         } catch (FileNotFoundException fnfe) {
241             System.err.println("Unable to open file: " + state.infile + ".struct");
242             System.exit(-1);
243         } catch (Exception e) {
244             //      System.out.println(e);
245             //      e.printStackTrace();
246             return false;
247         }
248
249         /* parse model file */
250         try {
251             debugMessage(1, "Parsing model file");
252             LineCount.reset();
253             FileInputStream infile = new FileInputStream(state.infile + ".model");
254             MDLParser parser = new MDLParser(new Lexer(infile));
255             CUP$MDLParser$actions.debug = state.verbose > 1 ;
256             state.ptModel = (ParseNode) parser.parse().value;
257         } catch (FileNotFoundException fnfe) {
258             System.err.println("Unable to open file: " + state.infile + ".model");
259             System.exit(-1);
260         } catch (Exception e) {
261             //      System.out.println(e);
262             //      e.printStackTrace();
263             return false;
264         }
265
266         /* parse space file */
267         try {
268             debugMessage(1, "Parsing space file");
269             LineCount.reset();
270             FileInputStream infile = new FileInputStream(state.infile + ".space");
271             SDLParser parser = new SDLParser(new Lexer(infile));
272             CUP$SDLParser$actions.debug = state.verbose > 1 ;
273             state.ptSpace = (ParseNode) parser.parse().value;
274         } catch (FileNotFoundException fnfe) {
275             System.err.println("Unable to open file: " + state.infile + ".space");
276             System.exit(-1);
277         } catch (Exception e) {
278             //      System.out.println(e);
279             //      e.printStackTrace();
280             return false;
281         }
282
283         /* parse constraints file */
284         try {
285             debugMessage(1, "Parsing constraints file");
286             LineCount.reset();
287             FileInputStream infile = new FileInputStream(state.infile + ".constraints");
288             CDLParser parser = new CDLParser(new Lexer(infile));
289             CUP$CDLParser$actions.debug = state.verbose > 1 ;
290             state.ptConstraints = (ParseNode) parser.parse().value;
291         } catch (FileNotFoundException fnfe) {
292             System.err.println("Unable to open file: " + state.infile + ".constraints");
293             System.exit(-1);
294         } catch (Exception e) {
295             //      System.out.println(e);
296             //      e.printStackTrace();
297             return false;
298         }
299
300         boolean success = 
301             !CUP$TDLParser$actions.errors && 
302             !CUP$SDLParser$actions.errors && 
303             !CUP$CDLParser$actions.errors && 
304             !CUP$MDLParser$actions.errors;
305
306                 
307         // if verbosity is on, then output parse trees as .dot files
308         if (success && state.verbose > 0) {
309             try {
310                 FileOutputStream dotfile;
311
312                 dotfile = new FileOutputStream(state.infile + ".struct.dot");
313                 ParseNodeDOTVisitor.visit(dotfile, state.ptStructures);                
314                 dotfile.close();
315
316                 dotfile = new FileOutputStream(state.infile + ".model.dot");
317                 ParseNodeDOTVisitor.visit(dotfile, state.ptModel);                
318                 dotfile.close();
319
320                 dotfile = new FileOutputStream(state.infile + ".space.dot");
321                 ParseNodeDOTVisitor.visit(dotfile, state.ptSpace);                
322                 dotfile.close();
323
324                 dotfile = new FileOutputStream(state.infile + ".constraints.dot");
325                 ParseNodeDOTVisitor.visit(dotfile, state.ptConstraints);                
326                 dotfile.close();
327             } catch (Exception e) {
328                 e.printStackTrace();
329                 return false;
330             }
331         }
332             
333         return success;
334     }
335
336
337     public static boolean scan(State state) {
338         FileInputStream infile = null;
339         Lexer lexer;
340         boolean errors = false;
341         String files[] = { new String(state.infile + ".struct"),
342                            new String(state.infile + ".model"),
343                            new String(state.infile + ".constraints"),
344                            new String(state.infile + ".space") };
345
346
347
348         for (int i = 0; i < files.length; i++) {
349
350             String filename = files[i];
351
352             try {
353                 infile = new FileInputStream(filename);
354             } catch (FileNotFoundException fnfe) {
355                 System.err.println("Unable to open file: " + filename);
356                 System.exit(-1);
357             }
358             
359             lexer = new Lexer(infile);
360
361             
362             try {
363                 while (true) {
364                     java_cup.runtime.Symbol symbol;
365                     
366                     symbol = lexer.next_token();
367                     
368                     if (symbol.sym == Sym.EOF) {
369                         break;
370                     } else if (symbol.sym == Sym.BAD) {
371                         errors = true;
372                     }
373                     
374                     if (State.verbose > 2) {
375                         System.out.println("Got token: " + symbol.value);
376                     }
377                 }
378             } catch (Exception e) {
379                 return false;
380             }
381         }
382
383         return !errors;
384     }
385
386
387 }
388