gitweb on Svarog

projekti pod git sistemom za održavanje verzija -- projects under the git version control system
4723e4d7188758aa7fec99484ac4b818de92abc2
[mjc2wsl.git] / src / mjc2wsl.java
1 /*
2 Copyright (C) 2014 Doni Pracner
4 This file is part of mjc2wsl.
6 mjc2wsl is free software: you can redistribute it and/or modify
7 it under the terms of the GNU General Public License as published by
8 the Free Software Foundation, either version 3 of the License, or
9 (at your option) any later version.
11 mjc2wsl is distributed in the hope that it will be useful,
12 but WITHOUT ANY WARRANTY; without even the implied warranty of
13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 GNU General Public License for more details.
16 You should have received a copy of the GNU General Public License
17 along with mjc2wsl. If not, see <http://www.gnu.org/licenses/>.
18 */
19 import java.io.*;
20 import java.util.*;
22 /**
23 * This program converts file from compiled MicroJava bytecode to WSL language
24 * which is a part of the FermaT Transformation system. MicroJava is a subset
25 * used in Compiler Construction courses by Hanspeter Moessenboeck, not
26 * "Java ME".
27 *
28 * @author Doni Pracner, http://perun.dmi.rs/pracner http://quemaster.com
29 */
30 public class mjc2wsl{
31 //default version name, used if the file is not found
32 private static String versionN = "0.1.x";
34 private String versionFile = "version.properties";
36 private TransMessages messages = new TransMessages();
38 private boolean genPauseAfterEachAddress=false,
39 genPrintForEachAddress = false,
40 genPrintEStackOnChange = false;
42 private boolean genPopPush=false;
44 private boolean genInlinePrint=false;
46 /** Constant used for marking a regular comment from the original file */
47 public static final char C_REG = ' ';
48 /**
49 * Constant used for marking when original code is inserted in the file,
50 * next to the translations
51 */
52 public static final char C_OC = '#';
53 /** Constant used for marking special messages from the translator */
54 public static final char C_SPEC = '&';
55 /** Constant used for marking error messages from the translator */
56 public static final char C_ERR = '!';
58 /** instruction code in MicroJava bytecode. */
59 public static final int
60 load = 1,
61 load_0 = 2,
62 load_1 = 3,
63 load_2 = 4,
64 load_3 = 5,
65 store = 6,
66 store_0 = 7,
67 store_1 = 8,
68 store_2 = 9,
69 store_3 = 10,
70 getstatic = 11,
71 putstatic = 12,
72 getfield = 13,
73 putfield = 14,
74 const_0 = 15,
75 const_1 = 16,
76 const_2 = 17,
77 const_3 = 18,
78 const_4 = 19,
79 const_5 = 20,
80 const_m1 = 21,
81 const_ = 22,
82 add = 23,
83 sub = 24,
84 mul = 25,
85 div = 26,
86 rem = 27,
87 neg = 28,
88 shl = 29,
89 shr = 30,
90 inc = 31,
91 new_ = 32,
92 newarray = 33,
93 aload = 34,
94 astore = 35,
95 baload = 36,
96 bastore = 37,
97 arraylength = 38,
98 pop = 39,
99 dup = 40,
100 dup2 = 41,
101 jmp = 42,
102 jeq = 43,
103 jne = 44,
104 jlt = 45,
105 jle = 46,
106 jgt = 47,
107 jge = 48,
108 call = 49,
109 return_ = 50,
110 enter = 51,
111 exit = 52,
112 read = 53,
113 print = 54,
114 bread = 55,
115 bprint = 56,
116 trap = 57;
118 private boolean originalInComments = false;
120 private HashMap<Integer,String> opMap = null;
122 private String opCodeFile = "mj-bytecodes.properties";
124 private HashMap<Integer, String> getOpMap() {
125 if (opMap == null) {
126 opMap = new HashMap<Integer, String>(60, 0.98f);
127 try {
128 BufferedReader in = new BufferedReader(new InputStreamReader(
129 getClass().getResourceAsStream(opCodeFile)));
130 String str = in.readLine();
131 while (str != null) {
132 String[] ss = str.split("=");
133 opMap.put(Integer.parseInt(ss[0]), ss[1]);
134 str = in.readLine();
136 in.close();
137 } catch (Exception ex) {
138 ex.printStackTrace();
141 return opMap;
144 private Properties versionData;
146 private String getVersion() {
147 if (versionData == null) {
148 versionData = new Properties();
149 try {
150 versionData.load(getClass().getResourceAsStream(versionFile));
151 } catch (IOException e) {
152 e.printStackTrace();
155 String ver = versionData.getProperty("version");
156 if (ver != null)
157 return ver;
158 else
159 return versionN;
162 public String getOpString(int op) {
163 return getOpMap().get(op);
166 public String describeOpCode(int op) {
167 return op + " (" + getOpString(op) + ")";
170 private InputStream mainIn;
171 private PrintWriter out = null;
172 private int counter = -1;
174 private void pr(int i){
175 out.print(i);
178 private void pr(char i){
179 out.print(i);
182 private void pr(String i){
183 out.print(i);
186 private void prl(String i){
187 out.println(i);
190 private int get() {
191 int res = -1;
192 try {
193 res = mainIn.read();
194 if (res >= 0)
195 res = res << 24 >>> 24;
196 } catch (IOException ex) {
197 ex.printStackTrace();
199 counter++;
200 return res;
203 private int get2() {
204 return (get() * 256 + get()) << 16 >> 16;
207 private int get4() {
208 return (get2() << 16) + (get2() << 16 >>> 16);
211 public String createStandardStart(){
212 return createStandardStart(10);
215 public String createStandardStart(int numWords){
216 StringBuilder ret = new StringBuilder(
217 "C:\" This file automatically converted from microjava bytecode\";\n"
218 +"C:\" with mjc2wsl v "+getVersion()+"\";\n");
220 ret.append("\nBEGIN");
221 ret.append("\nVAR <\n\t");
222 ret.append("mjvm_locals := ARRAY(1,0),");
223 ret.append("\n\tmjvm_statics := ARRAY("+numWords+",0),");
224 ret.append("\n\tmjvm_arrays := < >,");
225 ret.append("\n\tmjvm_flag_jump := 0,");
226 ret.append("\n\tmjvm_objects := < >,");
227 ret.append("\n\tmjvm_estack := < >, mjvm_mstack := < > > :");
229 return ret.toString();
232 public String createAsciiString(){
233 StringBuilder ret = new StringBuilder("C:\"char array for ascii code conversions\";");
234 ret.append("\nascii := \"????????????????????????????????\"++\n");
235 ret.append("\" !\"++Quote++\"#$%&'()*+,-./0123456789:;<=>?@ABCDEFGHIJKLMNOPQRSTUVWXYZ[\\]^_`abcdefghijklmnopqrstuvwxyz{|}~\";\n");
237 return ret.toString();
240 public String createStandardEnd(){
241 StringBuilder ret = new StringBuilder("SKIP\nENDVAR\n");
242 ret.append("\nWHERE\n");
244 ret.append("\nFUNCT CHR(num) ==:\n");
245 ret.append("\t@List_To_String(< num >)\n");
246 ret.append("END\n");
248 if (!genInlinePrint) {
249 ret.append("\nPROC Print_MJ(val, format VAR)==\n");
250 ret.append(createComment("print spacing", C_SPEC));
251 ret.append("\n\tIF format>1 THEN\n\t\tFOR i:=2 TO ");
252 ret.append("format STEP 1 DO PRINFLUSH(\" \") OD\n");
253 ret.append("\tFI;\n\tPRINFLUSH(val)\nEND\n");
255 ret.append("\nPROC Print_MJ_CHAR(val, format VAR)==\n");
256 ret.append(createComment("print spacing", C_SPEC));
257 ret.append("\n\tIF format>1 THEN\n\t\tFOR i:=2 TO ");
258 ret.append("format STEP 1 DO PRINFLUSH(\" \") OD\n");
259 ret.append("\tFI;\n\tPRINFLUSH(CHR(val))\n");
260 ret.append("END\n");
263 ret.append("\nEND");
264 return ret.toString();
267 private String createStartVar(String... vars){
268 StringBuilder ret = new StringBuilder("VAR < ");
269 ret.append(vars[0] + " := 0");
270 for (int i=1; i<vars.length; i++)
271 ret.append(", "+ vars[i] +" := 0");
272 ret.append(" > : ");
274 return ret.toString();
277 private String createEndVar(){
278 return "ENDVAR;";
281 private String createLocal(int i) {
282 // arrays start at 1 in WSL, so we need an offset
283 return "mjvm_locals[" + (i + 1) + "]";
286 private String createStatic(int i) {
287 return "mjvm_statics[" + (i + 1) + "]";
290 private String createArray(int i) {
291 return "mjvm_arrays[" + i + "]";
294 private String createArray(String i) {
295 return "mjvm_arrays[" + i + "]";
298 private String createObject(String i) {
299 return "mjvm_objects[" + i + "]";
302 /**
303 * Creates a WSL comment with care to quote chars.
304 */
305 public static String createComment(String str){
306 return createComment(str, C_REG);
309 /**
310 * Creates a WSL comment with care to quote chars, of the
311 * given type. Types are given as char constants. They can be
312 * default comments, comments that contain the original code
313 * in them, or additional comments regarding the translation
314 * process.
315 */
316 public static String createComment(String str, char type) {
317 return "C:\"" + type + str.replace("\"", "''") + "\";";
320 // generalised stack operations
322 private String createToStack(String stack, String var){
323 if (genPopPush)
324 return "PUSH("+stack+"," + var + ");";
325 else
326 return stack + " := <" + var + " > ++ " + stack +";";
329 private String createFromStack(String stack, String var){
330 if (genPopPush)
331 return "POP("+ var + ", "+stack+");";
332 else
333 return var + ":= HEAD("+stack+"); "+stack+" := TAIL("+stack+");";
335 //Expression stack
337 private String createToEStack(int i) {
338 return createToEStack(i+"");
341 private String createToEStack(String i) {
342 String res = createToStack("mjvm_estack", i);
343 if (genPrintEStackOnChange)
344 res += "PRINT(\"eStack\",mjvm_estack);";
345 return res;
348 private String createFromEStack(String st) {
349 String res = createFromStack("mjvm_estack",st);
350 if (genPrintEStackOnChange)
351 res += "PRINT(\"eStack\",mjvm_estack);";
352 return res;
355 private String createPopEStack() {
356 String res = "mjvm_estack := TAIL(mjvm_estack);";
357 if (genPrintEStackOnChange)
358 res += "PRINT(\"eStack\",mjvm_estack);";
359 return res;
362 private String createTopTwoEStack() {
363 return createFromEStack("tempa") + "\n" + createFromEStack("tempb");
366 private String createTopEStack() {
367 return createFromEStack("tempa");
370 //Method stack
372 private String createToMStack(int i) {
373 return createToMStack(i+"");
376 private String createToMStack(String i) {
377 return createToStack("mjvm_mstack", i);
380 private String createFromMStack(String st) {
381 return createFromStack("mjvm_mstack", st);
384 private String getRelationFor(int opcode) throws Exception {
385 switch (opcode) {
386 case jeq: return "=";
387 case jne: return "<>";
388 case jlt: return "<";
389 case jle: return "<=";
390 case jgt: return ">";
391 case jge: return ">=";
393 throw new Exception("Wrong opcode for a relation");
396 private boolean isJumpCode(int opcode) {
397 return (opcode >= jmp) && (opcode <= jge);
400 public void convertStream(InputStream ins) throws Exception{
401 mainIn = ins;
402 //process start
403 byte m = (byte) get();
404 byte j = (byte) get();
405 if (m!='M' || j !='J')
406 throw new Exception("Wrong start of bytecode file");
407 int codesize = get4();
408 int numberOfWords = get4();
409 int mainAdr = get4();
411 prl(createStandardStart(numberOfWords));
412 prl("SKIP;\n ACTIONS a" + (14 + mainAdr) + " :");
413 int op = get();
414 while (op >= 0) {
415 prl(" a" + counter + " ==");
416 if (originalInComments)
417 prl(createComment(describeOpCode(op), C_OC));
418 if (genPrintForEachAddress) {
419 prl("PRINT(\"a" + counter + "\");");
420 if (genPauseAfterEachAddress)
421 prl("debug_disposable_string := @Read_Line(Standard_Input_Port);");
423 switch (op) {
424 case load: {
425 prl(createToEStack(createLocal(get())));
426 break;
428 case load_0:
429 case load_1:
430 case load_2:
431 case load_3: {
432 prl(createStartVar("tempa"));
433 prl("tempa :="+createLocal(op - load_0)+";");
434 prl(createToEStack("tempa"));
435 prl(createEndVar());
436 break;
438 case store: {
439 prl(createFromEStack(createLocal(get())));
440 break;
442 case store_0:
443 case store_1:
444 case store_2:
445 case store_3: {
446 prl(createStartVar("tempa"));
447 prl(createFromEStack("tempa"));
448 prl(createLocal(op - store_0)+" := tempa;");
449 prl(createEndVar());
450 break;
453 case getstatic: {
454 prl(createToEStack(createStatic(get2())));
455 break;
457 case putstatic: {
458 prl(createFromEStack(createStatic(get2())));
459 break;
462 case getfield: {
463 int f = get2();
464 prl(createStartVar("tempa"));
465 prl(createTopEStack());
466 prl(createToEStack(createObject("tempa") + "[" + (f + 1) + "]"));
467 prl(createEndVar());
468 break;
470 case putfield: {
471 int f = get2();
472 prl(createStartVar("tempa", "tempb"));
473 prl(createTopTwoEStack());
474 prl(createObject("tempb") + "[" + (f + 1) + "]:=tempa;");
475 prl(createEndVar());
476 break;
479 case const_: {
480 prl(createToEStack(get4()));
481 break;
484 case const_m1: {
485 prl(createToEStack(-1));
486 break;
489 case const_0:
490 case const_1:
491 case const_2:
492 case const_3:
493 case const_4:
494 case const_5: {
495 prl(createToEStack(op - const_0));
496 break;
499 case add: {
500 prl(createStartVar("tempa", "tempb", "tempres"));
501 prl(createTopTwoEStack());
502 prl("tempres := tempb + tempa;");
503 prl(createToEStack("tempres"));
504 prl(createEndVar());
505 break;
507 case sub: {
508 prl(createStartVar("tempa", "tempb", "tempres"));
509 prl(createTopTwoEStack());
510 prl("tempres := tempb - tempa;");
511 prl(createToEStack("tempres"));
512 prl(createEndVar());
513 break;
515 case mul: {
516 prl(createStartVar("tempa", "tempb", "tempres"));
517 prl(createTopTwoEStack());
518 prl("tempres := tempb * tempa;");
519 prl(createToEStack("tempres"));
520 prl(createEndVar());
521 break;
523 case div: {
524 prl(createStartVar("tempa", "tempb", "tempres"));
525 prl(createTopTwoEStack());
526 prl("IF tempa = 0 THEN ERROR(\"division by zero\") FI;");
527 prl("tempres := tempb DIV tempa;");
528 prl(createToEStack("tempres"));
529 prl(createEndVar());
530 break;
532 case rem: {
533 prl(createStartVar("tempa", "tempb", "tempres"));
534 prl(createTopTwoEStack());
535 prl("IF tempa = 0 THEN ERROR(\"division by zero\") FI;");
536 prl("tempres := tempb MOD tempa;");
537 prl(createToEStack("tempres"));
538 prl(createEndVar());
539 break;
542 case neg: {
543 prl(createStartVar("tempa"));
544 prl(createTopEStack());
545 prl(createToEStack("-tempa"));
546 prl(createEndVar());
547 break;
550 case shl: {
551 prl(createStartVar("tempa", "tempb"));
552 prl(createTopTwoEStack());
553 prl("VAR <tempres :=tempb, i:=1 >:");
554 prl("\tFOR i:=1 TO tempa STEP 1 DO tempres := tempres * 2 OD;");
555 prl(createToEStack("tempres"));
556 prl("ENDVAR;");
557 prl(createEndVar());
558 break;
560 case shr: {
561 prl(createStartVar("tempa", "tempb"));
562 prl(createTopTwoEStack());
563 prl("VAR <tempres :=tempb, i:=1 >:");
564 prl("\tFOR i:=1 TO tempa STEP 1 DO tempres := tempres DIV 2 OD;");
565 prl(createToEStack("tempres"));
566 prl("ENDVAR;");
567 prl(createEndVar());
568 break;
571 case inc: {
572 int b1 = get(), b2 = get();
573 prl(createLocal(b1) + " := " + createLocal(b1) + " + " + b2 + ";");
574 break;
577 case new_: {
578 int size = get2();
579 // TODO maybe objects and arrays should be in the same list?
580 prl("mjvm_objects := mjvm_objects ++ < ARRAY(" + size
581 + ",0) >;");
582 prl(createToEStack("LENGTH(mjvm_objects)"));
583 break;
585 case newarray: {
586 get();// 0 - bytes, 1 - words; ignore for now
587 // TODO take into consideration 0/1
588 prl(createStartVar("tempa"));
589 prl(createTopEStack());
590 prl("mjvm_arrays := mjvm_arrays ++ < ARRAY(tempa,0) >;");
591 prl(createToEStack("LENGTH(mjvm_arrays)"));
592 prl(createEndVar());
593 break;
596 case aload:
597 case baload: {
598 prl(createStartVar("tempa", "tempb"));
599 prl(createTopTwoEStack());
600 prl(createToEStack(createArray("tempb") + "[tempa+1]"));
601 prl(createEndVar());
602 break;
604 case astore:
605 case bastore: {
606 prl(createStartVar("tempa", "tempb", "tempres"));
607 prl(createFromEStack("tempres"));
608 prl(createTopTwoEStack());
609 prl("mjvm_arrays[tempb][tempa+1]:=tempres;");
610 prl(createEndVar());
611 break;
613 case arraylength: {
614 prl(createStartVar("tempa", "tempb"));
615 prl(createTopEStack());
616 prl("tempb := LENGTH("+ createArray("tempa") + ");");
617 prl(createToEStack("tempb"));
618 prl(createEndVar());
619 break;
622 case dup: {
623 prl(createStartVar("tempa", "tempb"));
624 prl(createTopEStack());
625 prl(createToEStack("tempa"));
626 prl(createToEStack("tempa"));
627 prl(createEndVar());
628 break;
630 case dup2: {
631 prl(createStartVar("tempa", "tempb"));
632 prl(createTopTwoEStack());
633 prl(createToEStack("tempb"));
634 prl(createToEStack("tempa"));
635 prl(createToEStack("tempb"));
636 prl(createToEStack("tempa"));
637 prl(createEndVar());
638 break;
641 case pop: {
642 prl(createPopEStack());
643 break;
646 case jmp: {
647 prl("CALL a" + (counter + get2()) + ";");
648 break;
651 case jeq:
652 case jne:
653 case jlt:
654 case jle:
655 case jgt:
656 case jge: {
657 prl(createStartVar("tempa", "tempb"));
658 prl(createTopTwoEStack());
659 prl("IF tempb " + getRelationFor(op)
660 + " tempa THEN mjvm_flag_jump := 1"
661 + " ELSE mjvm_flag_jump := 0"
662 + " FI;");
663 prl(createEndVar());
664 prl("IF mjvm_flag_jump = 1 THEN CALL a"
665 + (counter + get2())
666 + " ELSE CALL a" + (counter + 1)
667 + " FI;");
669 break;
672 case call: {
673 prl("CALL a" + (counter + get2()) + ";");
674 break;
677 case return_: {
678 // we let the actions return
679 // there is nothing to clean up
680 prl("SKIP\n END\n b" + counter + " ==");
681 break;
683 case enter: {
684 int parameters = get();
686 int locals = get();
687 prl(createToMStack("mjvm_locals"));
688 prl("mjvm_locals := ARRAY(" + locals + ",0);");
689 for (int i = parameters - 1; i >= 0; i--)
690 prl(createFromEStack(createLocal(i)));
691 break;
693 case exit: {
694 prl(createFromMStack("mjvm_locals"));
695 break;
698 // read, print
699 case bread: {
700 // TODO make it a char for read
701 messages.message("char is read like a number", TransMessages.M_WAR);
702 prl(createComment("char is read like a number", C_SPEC));
704 case read: {
705 prl(createStartVar("tempa"));
706 prl("tempa := @String_To_Num(@Read_Line(Standard_Input_Port));");
707 prl(createToEStack("tempa"));
708 prl(createEndVar());
709 break;
712 // the prints
713 case bprint: {
714 prl(createStartVar("tempa", "tempb"));
715 prl(createTopTwoEStack());
716 if (genInlinePrint){
717 prl(createComment("print spacing and transformation",C_SPEC));
718 prl("PRINFLUSH(SUBSTR(\" \", 0, MIN(10, MAX(0,tempa-1))), @List_To_String(< tempb >));");
719 } else
720 prl("Print_MJ_CHAR(tempb,tempa);");
721 prl(createEndVar());
722 break;
724 case print: {
725 // TODO printing numbers needs different lengths of spacing
726 prl(createStartVar("tempa", "tempb"));
728 prl(createTopTwoEStack());
729 if (genInlinePrint){
730 prl(createComment("print spacing",C_SPEC));
731 prl("PRINFLUSH(SUBSTR(\" \", 0, MIN(10, MAX(0, tempa-1))), tempb);");
733 else
734 prl("Print_MJ(tempb,tempa);");
735 prl(createEndVar());
736 break;
739 case trap: {
740 prl("ERROR(\"Runtime error: trap(" + get() + ")\");");
741 break;
744 default:
745 prl(createComment("unknown op error: " + op, C_ERR));
746 messages.message("unknown op error: " + op, TransMessages.M_ERR);
747 break;
750 boolean wasJump = isJumpCode(op);
751 op = get();
752 if (op >= 0)
753 if (wasJump)
754 prl("SKIP\n END");
755 else
756 prl("CALL a" + counter + "\n END");
758 prl("SKIP\n END\nENDACTIONS;\n");
759 pr(createStandardEnd());
762 public void convertFile(File f) {
763 try {
764 convertStream(new FileInputStream(f));
765 } catch (Exception ex) {
766 ex.printStackTrace();
770 public void printHelp() {
771 printVersion();
772 printUsage();
773 printHelpOutput();
774 printHelpHelp();
777 public void printLongHelp() {
778 printVersion();
779 printUsage();
780 System.out.println();
781 printHelpOutput();
782 System.out.println();
783 printHelpDirectives();
784 System.out.println();
785 printHelpGenerating();
786 System.out.println();
787 printHelpHelp();
790 public void printHelpOutput() {
791 System.out.println("Output options:");
792 System.out.println(" --screen print output to screen");
793 System.out.println(" -o --oc[+-] include original code in comments");
794 System.out.println(" -v verbose, print warning messages");
795 System.out.println(" -q quiet; don't print even the error messages");
796 System.out.println(" -d print detailed debug messages");
799 public void printHelpGenerating() {
800 System.out.println("Options for generating extra code for tracking code execution");
801 System.out.println(" --genEStackPrint generate print for all EStack changes");
802 System.out.println(" --genAddrPrint generate prints after every address of the original code ");
803 System.out.println(" --genAddrPause generate a pause after every address of the original code ");
804 System.out.println(" --genAddr short for --genAddrPrint and --genAddrPause");
805 System.out.println(" --genAll short for applying all code generation");
808 public void printHelpDirectives(){
809 System.out.println("Alternatives for code generation:");
810 System.out.println(" --genPopPush generate POP/PUSH instead of TAIL/HEAD");
811 System.out.println(" --genHeadTail generate TAIL/HEAD instead of POP/PUSH ");
812 System.out.println();
813 System.out.println(" --genInlinePrint generate prints directly instead of procedure calls");
814 System.out.println(" --genProcedurePrint generate prints as custom procedure calls");
817 public void printHelpHelp() {
818 System.out.println("Help and info options");
819 System.out.println(" -h basic help");
820 System.out.println(" --help print more detailed help");
821 System.out.println(" --version or -version print version and exit");
824 public void printUsage(){
825 System.out.println("usage:\n\t mjc2wsl {options} filename [outfile]");
828 public void printVersion() {
829 System.out.println("MicroJava bytecode to WSL converter. v " + getVersion()
830 + ", by Doni Pracner");
833 public String makeDefaultOutName(String inname){
834 String rez = inname;
835 if (inname.endsWith(".obj"))
836 rez = rez.substring(0, rez.length() - 4);
837 return rez + ".wsl";
840 public void run(String[] args) {
841 if (args.length == 0) {
842 printHelp();
843 } else {
844 int i = 0;
845 while (i < args.length && args[i].charAt(0) == '-') {
846 if (args[i].compareTo("-h") == 0) {
847 printHelp();
848 return;
849 } else if (args[i].compareTo("--help") == 0) {
850 printLongHelp();
851 return;
852 } else if (args[i].compareTo("--version") == 0
853 || args[i].compareTo("-version") == 0) {
854 printVersion();
855 return;
856 } else if (args[i].compareTo("-o") == 0
857 || args[i].startsWith("--oc")) {
858 if (args[i].length() == 2)
859 originalInComments = true;
860 else if (args[i].length() == 5)
861 originalInComments = args[i].charAt(4) == '+';
862 else
863 originalInComments = true;
864 } else if (args[i].compareTo("--screen") == 0) {
865 out = new PrintWriter(System.out);
866 } else if (args[i].compareTo("-d") == 0) {
867 messages.setPrintLevel(TransMessages.M_DEB);// print debug info
868 } else if (args[i].compareTo("-v") == 0) {
869 messages.setPrintLevel(TransMessages.M_WAR);// print warnings
870 } else if (args[i].compareTo("-q") == 0) {
871 messages.setPrintLevel(TransMessages.M_QUIET);// no printing
872 } else if (args[i].compareToIgnoreCase("--genEStackPrint") == 0) {
873 genPrintEStackOnChange = true;
874 } else if (args[i].compareToIgnoreCase("--genAddrPause") == 0) {
875 genPauseAfterEachAddress = true;
876 } else if (args[i].compareToIgnoreCase("--genAddrPrint") == 0) {
877 genPrintForEachAddress = true;
878 } else if (args[i].compareToIgnoreCase("--genAddr") == 0) {
879 genPrintForEachAddress = true;
880 genPauseAfterEachAddress = true;
881 } else if (args[i].compareToIgnoreCase("--genAll") == 0) {
882 genPrintEStackOnChange = true;
883 genPrintForEachAddress = true;
884 genPauseAfterEachAddress = true;
885 } else if (args[i].compareToIgnoreCase("--genPopPush") == 0) {
886 genPopPush = true;
887 } else if (args[i].compareToIgnoreCase("--genInlinePrint") == 0) {
888 genInlinePrint = true;
889 } else if (args[i].compareToIgnoreCase("--genHeadTail") == 0) {
890 genPopPush = false;
891 } else if (args[i].compareToIgnoreCase("--genProcedurePrint") == 0) {
892 genInlinePrint = false;
894 i++;
897 if (i >= args.length) {
898 System.out.println("no filename supplied");
899 System.exit(2);
901 File f = new File(args[i]);
903 if (i + 1 < args.length) {
904 try {
905 out = new PrintWriter(args[i + 1]);
906 } catch (Exception e) {
907 System.err.println("error in opening out file:");
908 e.printStackTrace();
911 if (out == null) {
912 // if not set to screen, or a file, make a default filename
913 try {
914 out = new PrintWriter(makeDefaultOutName(args[i]));
915 } catch (Exception e) {
916 System.err.println("error in opening out file:");
917 e.printStackTrace();
920 if (f.exists()) {
921 Calendar now = Calendar.getInstance();
922 convertFile(f);
923 long mili = Calendar.getInstance().getTimeInMillis()
924 - now.getTimeInMillis();
925 System.out.println("conversion time:" + mili + " ms");
926 messages.printMessageCounters();
927 out.close();
928 } else
929 System.out.println("file does not exist");
933 public static void main(String[] args) {
934 new mjc2wsl().run(args);
Svarog.pmf.uns.ac.rs/gitweb maintanance Doni Pracner