Skip to content

Commit 368c1c9

Browse files
author
Christian Lütticke
committed
processing#2 processing-java - Vorbereitung EntPreprocessor, weitere Umstrukturierung für Compile-Prozess
1 parent 8d88ff4 commit 368c1c9

8 files changed

Lines changed: 1042 additions & 1365 deletions

File tree

java/.classpath

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -22,5 +22,14 @@
2222
<classpathentry kind="con" path="org.eclipse.jdt.launching.JRE_CONTAINER"/>
2323
<classpathentry combineaccessrules="false" kind="src" path="/processing-app"/>
2424
<classpathentry combineaccessrules="false" kind="src" path="/processing-core"/>
25+
<classpathentry combineaccessrules="false" kind="src" path="/polyglot-master"/>
26+
<classpathentry kind="lib" path="/ent/lib/ent.jar"/>
27+
<classpathentry kind="lib" path="/ent/lib/ent-rt.jar"/>
28+
<classpathentry kind="lib" path="/ent/lib/guava-18.0.jar"/>
29+
<classpathentry kind="lib" path="/ent/lib/java_cup.jar"/>
30+
<classpathentry kind="lib" path="/ent/lib/jflex.jar"/>
31+
<classpathentry kind="lib" path="/ent/lib/polyglot.jar"/>
32+
<classpathentry kind="lib" path="/ent/lib/ppg.jar"/>
33+
<classpathentry kind="lib" path="/ent/lib/pth.jar"/>
2534
<classpathentry kind="output" path="bin"/>
2635
</classpath>

java/src/processing/mode/java/Compiler.java

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -51,7 +51,7 @@ public class Compiler {
5151
/**
5252
* Compile with ECJ. See http://j.mp/8paifz for documentation.
5353
*
54-
* @param sketch Sketch object to be compiled, used for placing exceptions
54+
* @param data.sketch Sketch object to be compiled, used for placing exceptions
5555
* @param buildPath Where the temporary files live and will be built from.
5656
* @return true if successful.
5757
* @throws SketchException Only if there's a problem. Only then.

java/src/processing/mode/java/CompilerCUSTOM.java

Lines changed: 280 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -51,12 +51,12 @@ public class CompilerCUSTOM {
5151
/**
5252
* Compile with ECJ. See http://j.mp/8paifz for documentation.
5353
*
54-
* @param sketch Sketch object to be compiled, used for placing exceptions
54+
* @param data.sketch Sketch object to be compiled, used for placing exceptions
5555
* @param buildPath Where the temporary files live and will be built from.
5656
* @return true if successful.
5757
* @throws SketchException Only if there's a problem. Only then.
5858
*/
59-
static public boolean compile(JavaBuildCUSTOM build) throws SketchException {
59+
static public boolean compileCUSTOM(JavaBuildCUSTOM build) throws SketchException {
6060

6161
// This will be filled in if anyone gets angry
6262
SketchException exception = null;
@@ -66,7 +66,14 @@ static public boolean compile(JavaBuildCUSTOM build) throws SketchException {
6666

6767
String[] commandCUSTOM = generateCommandCUSTOM(build);
6868

69-
polyglot.main.Main.main(commandCUSTOM);
69+
polyglot.main.Main polyglotMain = new polyglot.main.Main();
70+
71+
try {
72+
polyglotMain.start(commandCUSTOM, new ent.EntExtensionInfo());
73+
} catch (polyglot.main.Main.TerminationException e) {
74+
System.err.println(e.getMessage());
75+
System.exit(1);
76+
}
7077

7178
try {
7279
// Load errors into a local StringBuilder
@@ -305,6 +312,268 @@ public void close() { }
305312
return success;
306313
}
307314

315+
316+
static public boolean compile(JavaBuildCUSTOM build) throws SketchException {
317+
318+
// This will be filled in if anyone gets angry
319+
SketchException exception = null;
320+
boolean success = false;
321+
322+
String baseCommand[] = new String[] {
323+
"-g",
324+
"-Xemacs",
325+
//"-noExit", // not necessary for ecj
326+
"-source", "1.7",
327+
"-target", "1.7",
328+
"-encoding", "utf8",
329+
"-classpath", build.getClassPath(),
330+
"-nowarn", // we're not currently interested in warnings (works in ecj)
331+
"-d", build.getBinFolder().getAbsolutePath() // output the classes in the buildPath
332+
};
333+
//PApplet.println(baseCommand);
334+
335+
String[] sourceFiles = Util.listFiles(build.getSrcFolder(), false, ".java");
336+
String[] command = PApplet.concat(baseCommand, sourceFiles);
337+
//PApplet.println(command);
338+
339+
try {
340+
// Load errors into a local StringBuilder
341+
final StringBuilder errorBuffer = new StringBuilder();
342+
343+
// Create single method dummy writer class to slurp errors from ecj
344+
Writer internalWriter = new Writer() {
345+
public void write(char[] buf, int off, int len) {
346+
errorBuffer.append(buf, off, len);
347+
}
348+
349+
public void flush() { }
350+
351+
public void close() { }
352+
};
353+
// Wrap as a PrintWriter since that's what compile() wants
354+
PrintWriter writer = new PrintWriter(internalWriter);
355+
356+
//result = com.sun.tools.javac.Main.compile(command, writer);
357+
358+
PrintWriter outWriter = new PrintWriter(System.out);
359+
360+
// Version that's not dynamically loaded
361+
//CompilationProgress progress = null;
362+
//success = BatchCompiler.compile(command, outWriter, writer, progress);
363+
364+
// Version that *is* dynamically loaded. First gets the mode class loader
365+
// so that it can grab the compiler JAR files from it.
366+
ClassLoader loader = build.mode.getClassLoader();
367+
try {
368+
Class<?> batchClass =
369+
Class.forName("org.eclipse.jdt.core.compiler.batch.BatchCompiler", false, loader);
370+
Class<?> progressClass =
371+
Class.forName("org.eclipse.jdt.core.compiler.CompilationProgress", false, loader);
372+
Class<?>[] compileArgs =
373+
new Class<?>[] { String[].class, PrintWriter.class, PrintWriter.class, progressClass };
374+
Method compileMethod = batchClass.getMethod("compile", compileArgs);
375+
success = (Boolean)
376+
compileMethod.invoke(null, new Object[] { command, outWriter, writer, null });
377+
} catch (Exception e) {
378+
e.printStackTrace();
379+
throw new SketchException("Unknown error inside the compiler.");
380+
}
381+
382+
// Close out the stream for good measure
383+
writer.flush();
384+
writer.close();
385+
386+
BufferedReader reader =
387+
new BufferedReader(new StringReader(errorBuffer.toString()));
388+
//System.err.println(errorBuffer.toString());
389+
390+
String line = null;
391+
while ((line = reader.readLine()) != null) {
392+
//System.out.println("got line " + line); // debug
393+
394+
// get first line, which contains file name, line number,
395+
// and at least the first line of the error message
396+
String errorFormat = "([\\w\\d_]+.java):(\\d+):\\s*(.*):\\s*(.*)\\s*";
397+
String[] pieces = PApplet.match(line, errorFormat);
398+
//PApplet.println(pieces);
399+
400+
// if it's something unexpected, die and print the mess to the console
401+
if (pieces == null) {
402+
exception = new SketchException("Cannot parse error text: " + line);
403+
exception.hideStackTrace();
404+
// Send out the rest of the error message to the console.
405+
System.err.println(line);
406+
while ((line = reader.readLine()) != null) {
407+
System.err.println(line);
408+
}
409+
break;
410+
}
411+
412+
// translate the java filename and line number into a un-preprocessed
413+
// location inside a source file or tab in the environment.
414+
String dotJavaFilename = pieces[1];
415+
// Line numbers are 1-indexed from javac
416+
int dotJavaLineIndex = PApplet.parseInt(pieces[2]) - 1;
417+
String errorMessage = pieces[4];
418+
419+
exception = build.placeException(errorMessage,
420+
dotJavaFilename,
421+
dotJavaLineIndex);
422+
423+
if (exception == null) {
424+
exception = new SketchException(errorMessage);
425+
}
426+
427+
String[] parts = null;
428+
429+
if (errorMessage.startsWith("The import ") &&
430+
errorMessage.endsWith("cannot be resolved")) {
431+
// The import poo cannot be resolved
432+
//import poo.shoe.blah.*;
433+
//String what = errorMessage.substring("The import ".length());
434+
String[] m = PApplet.match(errorMessage, "The import (.*) cannot be resolved");
435+
//what = what.substring(0, what.indexOf(' '));
436+
if (m != null) {
437+
// System.out.println("'" + m[1] + "'");
438+
if (m[1].equals("processing.xml")) {
439+
exception.setMessage("processing.xml no longer exists, this code needs to be updated for 2.0.");
440+
System.err.println("The processing.xml library has been replaced " +
441+
"with a new 'XML' class that's built-in.");
442+
handleCrustyCode();
443+
444+
} else {
445+
exception.setMessage("The package " +
446+
"\u201C" + m[1] + "\u201D" +
447+
" does not exist. " +
448+
"You might be missing a library.");
449+
System.err.println("Libraries must be " +
450+
"installed in a folder named 'libraries' " +
451+
"inside the sketchbook folder " +
452+
"(see the Preferences window).");
453+
}
454+
}
455+
456+
} else if (errorMessage.endsWith("cannot be resolved to a type")) {
457+
// xxx cannot be resolved to a type
458+
//xxx c;
459+
460+
String what = errorMessage.substring(0, errorMessage.indexOf(' '));
461+
462+
if (what.equals("BFont") ||
463+
what.equals("BGraphics") ||
464+
what.equals("BImage")) {
465+
exception.setMessage(what + " has been replaced with P" + what.substring(1));
466+
handleCrustyCode();
467+
468+
} else {
469+
exception.setMessage("Cannot find a class or type " +
470+
"named \u201C" + what + "\u201D");
471+
472+
String suggestion = importSuggestions.get(what);
473+
if (suggestion != null) {
474+
System.err.println("You may need to add \"import " + suggestion + ";\" to the top of your sketch.");
475+
System.err.println("To make sketches more portable, imports that are not part of the Processing API were removed in Processing 2.");
476+
System.err.println("See the changes page for more information: https://github.com/processing/processing/wiki/Changes");
477+
}
478+
}
479+
480+
} else if (errorMessage.endsWith("cannot be resolved")) {
481+
// xxx cannot be resolved
482+
//println(xxx);
483+
484+
String what = errorMessage.substring(0, errorMessage.indexOf(' '));
485+
486+
if (what.equals("LINE_LOOP") ||
487+
what.equals("LINE_STRIP")) {
488+
exception.setMessage("LINE_LOOP and LINE_STRIP are not available, " +
489+
"please update your code.");
490+
handleCrustyCode();
491+
492+
} else if (what.equals("framerate")) {
493+
exception.setMessage("framerate should be changed to frameRate.");
494+
handleCrustyCode();
495+
496+
} else if (what.equals("screen")) {
497+
exception.setMessage("Change screen.width and screen.height to " +
498+
"displayWidth and displayHeight.");
499+
handleCrustyCode();
500+
501+
} else if (what.equals("screenWidth") ||
502+
what.equals("screenHeight")) {
503+
exception.setMessage("Change screenWidth and screenHeight to " +
504+
"displayWidth and displayHeight.");
505+
handleCrustyCode();
506+
507+
} else {
508+
exception.setMessage("Cannot find anything " +
509+
"named \u201C" + what + "\u201D");
510+
}
511+
512+
} else if (errorMessage.startsWith("Duplicate")) {
513+
// "Duplicate nested type xxx"
514+
// "Duplicate local variable xxx"
515+
516+
} else if (null != (parts = PApplet.match(errorMessage,
517+
"literal (\\S*) of type (\\S*) is out of range"))) {
518+
if ("int".equals(parts[2])) {
519+
exception.setMessage("The type int can't handle numbers that big. Try "
520+
+ parts[1] + "L to upgrade to long.");
521+
} else {
522+
// I'd like to give an essay on BigInteger and BigDecimal, but
523+
// this margin is too narrow to contain it.
524+
exception.setMessage("Even the type " + parts[2] + " can't handle "
525+
+ parts[1] + ". Research big numbers in Java.");
526+
}
527+
} else {
528+
// The method xxx(String) is undefined for the type Temporary_XXXX_XXXX
529+
//xxx("blah");
530+
// The method xxx(String, int) is undefined for the type Temporary_XXXX_XXXX
531+
//xxx("blah", 34);
532+
// The method xxx(String, int) is undefined for the type PApplet
533+
//PApplet.sub("ding");
534+
String undefined =
535+
"The method (\\S+\\(.*\\)) is undefined for the type (.*)";
536+
parts = PApplet.match(errorMessage, undefined);
537+
if (parts != null) {
538+
if (parts[1].equals("framerate(int)")) {
539+
exception.setMessage("framerate() no longer exists, use frameRate() instead.");
540+
handleCrustyCode();
541+
542+
} else if (parts[1].equals("push()")) {
543+
exception.setMessage("push() no longer exists, use pushMatrix() instead.");
544+
handleCrustyCode();
545+
546+
} else if (parts[1].equals("pop()")) {
547+
exception.setMessage("pop() no longer exists, use popMatrix() instead.");
548+
handleCrustyCode();
549+
550+
} else {
551+
String mess = "The function " + parts[1] + " does not exist.";
552+
exception.setMessage(mess);
553+
}
554+
break;
555+
}
556+
}
557+
if (exception != null) {
558+
// The stack trace just shows that this happened inside the compiler,
559+
// which is a red herring. Don't ever show it for compiler stuff.
560+
exception.hideStackTrace();
561+
break;
562+
}
563+
}
564+
} catch (IOException e) {
565+
String bigSigh = "Error while compiling. (" + e.getMessage() + ")";
566+
exception = new SketchException(bigSigh);
567+
e.printStackTrace();
568+
success = false;
569+
}
570+
// In case there was something else.
571+
if (exception != null) throw exception;
572+
573+
return success;
574+
}
575+
576+
308577

309578
private static String[] generateCommand(JavaBuildCUSTOM build) {
310579
String baseCommand[] = new String[] {
@@ -330,7 +599,7 @@ private static String[] generateCommand(JavaBuildCUSTOM build) {
330599

331600
private static String[] generateCommandCUSTOM(JavaBuildCUSTOM build) {
332601

333-
String sketchPath = "/Users/christianluetticke/Documents/processing/java/src/test/source/Sketch.pde";
602+
File expectedFolder = new File("/Users/christianluetticke/Documents/processing/java/src/test/output/");
334603

335604
String baseCommand[] = new String[] {
336605
"-g",
@@ -340,11 +609,14 @@ private static String[] generateCommandCUSTOM(JavaBuildCUSTOM build) {
340609
};
341610
PApplet.println(baseCommand);
342611

343-
String[] sourceFiles = Util.listFiles(build.getSrcFolder(), false, ".java");
612+
//String[] sourceFiles = Util.listFiles(build.getSrcFolder(), false, ".java");
613+
//PApplet.println("build.getSrcFolder(): " + build.getSrcFolder());
614+
615+
String[] sourceFiles = Util.listFiles(expectedFolder, false, ".java");
616+
PApplet.println("build.getSrcFolder(): " + build.getSrcFolder());
617+
344618
String[] command = PApplet.concat(baseCommand, sourceFiles);
345-
//PApplet.println(command);
346-
PApplet.println(command);
347-
return command;
619+
return command;
348620
}
349621

350622
static protected void handleCrustyCode() {

0 commit comments

Comments
 (0)