| /******************************************************************************* |
| * Copyright (c) 2008, 2011 IBM Corporation and others. |
| * All rights reserved. This program and the accompanying materials |
| * are made available under the terms of the Eclipse Public License v1.0 |
| * which accompanies this distribution, and is available at |
| * http://www.eclipse.org/legal/epl-v10.html |
| * |
| * Contributors: |
| * IBM Corporation - initial API and implementation |
| * IBM Corporation - fix for 342936 |
| *******************************************************************************/ |
| package org.eclipse.jdt.compiler.tool.tests; |
| |
| import java.io.ByteArrayOutputStream; |
| import java.io.File; |
| import java.io.IOException; |
| import java.io.InputStream; |
| import java.io.OutputStream; |
| import java.io.PrintStream; |
| import java.io.PrintWriter; |
| import java.io.Reader; |
| import java.io.Writer; |
| import java.util.ArrayList; |
| import java.util.Arrays; |
| import java.util.Iterator; |
| import java.util.List; |
| import java.util.Properties; |
| import java.util.Set; |
| import java.util.logging.LogRecord; |
| |
| import javax.tools.FileObject; |
| import javax.tools.ForwardingJavaFileObject; |
| import javax.tools.JavaFileObject; |
| import javax.tools.StandardJavaFileManager; |
| import javax.tools.StandardLocation; |
| import javax.tools.ToolProvider; |
| import javax.tools.JavaCompiler.CompilationTask; |
| import javax.tools.JavaFileObject.Kind; |
| |
| import junit.framework.Test; |
| |
| import org.eclipse.jdt.internal.compiler.batch.Main; |
| import org.eclipse.jdt.internal.compiler.classfmt.ClassFileConstants; |
| import org.eclipse.jdt.internal.compiler.classfmt.ClassFileReader; |
| import org.eclipse.jdt.internal.compiler.classfmt.ClassFormatException; |
| |
| public class CompilerInvocationTests extends AbstractCompilerToolTest { |
| static { |
| // TESTS_NAMES = new String[] { "test019_sourcepath_without_destination" }; |
| // TESTS_NUMBERS = new int[] { 5 }; |
| // TESTS_RANGE = new int[] { 1, -1 }; |
| } |
| public CompilerInvocationTests(String name) { |
| super(name); |
| } |
| public static Test suite() { |
| return buildUniqueComplianceTestSuite(CompilerInvocationTests.class, ClassFileConstants.JDK1_6); |
| } |
| public static Class<CompilerInvocationTests> testClass() { |
| return CompilerInvocationTests.class; |
| } |
| |
| protected void checkClassFiles(String[] fileNames) { |
| for (int i = 0, l = fileNames.length; i < l; i++) { |
| ClassFileReader reader = null; |
| try { |
| reader = ClassFileReader.read(new File(OUTPUT_DIR, fileNames[i]), true); |
| } catch (ClassFormatException e) { |
| fail("Class format exception for file " + fileNames[i]); |
| } catch (IOException e) { |
| fail("IO exception for file " + fileNames[i]); |
| } |
| assertNotNull("Could not read " + fileNames[i], reader); |
| assertEquals("Wrong Java version for " + fileNames[i], ClassFileConstants.JDK1_6, reader.getVersion()); |
| } |
| } |
| void runTest( |
| boolean shouldCompileOK, |
| String[] sourceFiles, |
| StandardJavaFileManager standardJavaFileManager, |
| List<String> options, |
| String[] compileFileNames, |
| String expectedOutOutputString, |
| String expectedErrOutputString, |
| boolean shouldFlushOutputDirectory, |
| String[] classFileNames) { |
| super.runTest( |
| shouldCompileOK, |
| sourceFiles, |
| new CompilerInvocationTestsArguments(standardJavaFileManager, options, compileFileNames), |
| expectedOutOutputString, |
| expectedErrOutputString, |
| shouldFlushOutputDirectory, |
| null /* progress */); |
| // TODO maxime introduce stderr comparison based upon specific diagnostic listener |
| if (classFileNames != null) { |
| checkClassFiles(classFileNames); |
| } |
| } |
| class GetLocationDetector extends ForwardingStandardJavaFileManager<StandardJavaFileManager> { |
| private Location match; |
| private boolean matchFound; |
| GetLocationDetector(StandardJavaFileManager javaFileManager, Location location) { |
| super(javaFileManager); |
| this.match = location; |
| } |
| @Override |
| public Iterable<? extends File> getLocation(Location location) { |
| if (location == this.match) { |
| this.matchFound = true; |
| } |
| return super.getLocation(location); |
| } |
| boolean matchFound() { |
| return this.matchFound; |
| } |
| } |
| abstract class GetJavaFileDetector extends ForwardingStandardJavaFileManager<StandardJavaFileManager> { |
| boolean matchFound; |
| String discriminatingSuffix; |
| GetJavaFileDetector(StandardJavaFileManager javaFileManager) { |
| super(javaFileManager); |
| } |
| GetJavaFileDetector(StandardJavaFileManager javaFileManager, |
| String discriminatingSuffix) { |
| super(javaFileManager); |
| this.discriminatingSuffix = discriminatingSuffix; |
| } |
| abstract JavaFileObject detector(JavaFileObject original); |
| @Override |
| public Iterable<? extends JavaFileObject> getJavaFileObjects(File... files) { |
| return getJavaFileObjectsFromFiles(Arrays.asList(files)); |
| } |
| @Override |
| public Iterable<? extends JavaFileObject> getJavaFileObjects( |
| String... names) { |
| return getJavaFileObjectsFromStrings(Arrays.asList(names)); |
| } |
| @Override |
| public Iterable<? extends JavaFileObject> getJavaFileObjectsFromFiles( |
| Iterable<? extends File> files) { |
| ArrayList<JavaFileObject> result = new ArrayList<JavaFileObject>(); |
| for (JavaFileObject file: super.getJavaFileObjectsFromFiles(files)) { |
| result.add(detector(file)); |
| } |
| return result; |
| } |
| @Override |
| public Iterable<? extends JavaFileObject> getJavaFileObjectsFromStrings( |
| Iterable<String> names) { |
| ArrayList<JavaFileObject> result = new ArrayList<JavaFileObject>(); |
| for (JavaFileObject file: getJavaFileObjectsFromStrings(names)) { |
| result.add(detector(file)); |
| } |
| return result; |
| } |
| @Override |
| public Iterable<JavaFileObject> list(Location location, String packageName, |
| Set<Kind> kinds, boolean recurse) throws IOException { |
| ArrayList<JavaFileObject> result = new ArrayList<JavaFileObject>(); |
| for (JavaFileObject file: super.list(location, packageName, kinds, recurse)) { |
| result.add(detector(file)); |
| } |
| return result; |
| } |
| } |
| class GetJavaFileForInputDetector extends GetJavaFileDetector { |
| private Kind discriminatingKind; |
| GetJavaFileForInputDetector(StandardJavaFileManager javaFileManager) { |
| super(javaFileManager); |
| this.discriminatingKind = Kind.SOURCE; |
| } |
| GetJavaFileForInputDetector(StandardJavaFileManager javaFileManager, |
| String discriminatingSuffix, |
| Kind discriminatingKind) { |
| super(javaFileManager, discriminatingSuffix); |
| this.discriminatingKind = discriminatingKind; |
| } |
| class JavaFileInputDetector extends ForwardingJavaFileObject<JavaFileObject> { |
| JavaFileInputDetector(JavaFileObject fileObject) { |
| super(fileObject); |
| } |
| @Override |
| public CharSequence getCharContent(boolean ignoreEncodingErrors) |
| throws IOException { |
| matchFound = true; |
| return super.getCharContent(ignoreEncodingErrors); |
| } |
| @Override |
| public InputStream openInputStream() throws IOException { |
| matchFound = true; |
| return super.openInputStream(); |
| } |
| @Override |
| public Reader openReader(boolean ignoreEncodingErrors) |
| throws IOException { |
| matchFound = true; |
| return super.openReader(ignoreEncodingErrors); |
| } |
| } |
| JavaFileObject detector(JavaFileObject original) { |
| if (original != null && original.getKind() == this.discriminatingKind |
| && (this.discriminatingSuffix == null || original.getName().endsWith(this.discriminatingSuffix))) { |
| return new JavaFileInputDetector(original); |
| } |
| return original; |
| } |
| @Override |
| public FileObject getFileForInput(Location location, String packageName, |
| String relativeName) throws IOException { |
| FileObject result = |
| super.getFileForInput(location, packageName, relativeName); |
| if (result instanceof JavaFileObject) { |
| return detector((JavaFileObject) result); |
| } |
| return result; |
| } |
| @Override |
| public JavaFileObject getJavaFileForInput(Location location, |
| String className, Kind kind) throws IOException { |
| return detector(super.getJavaFileForInput(location, className, kind)); |
| } |
| } |
| class GetJavaFileForOutputDetector extends GetJavaFileDetector { |
| GetJavaFileForOutputDetector(StandardJavaFileManager javaFileManager) { |
| super(javaFileManager); |
| } |
| GetJavaFileForOutputDetector(StandardJavaFileManager javaFileManager, |
| String discriminatingSuffix) { |
| super(javaFileManager, discriminatingSuffix); |
| } |
| class JavaFileOutputDetector extends ForwardingJavaFileObject<JavaFileObject> { |
| JavaFileOutputDetector(JavaFileObject fileObject) { |
| super(fileObject); |
| } |
| @Override |
| public OutputStream openOutputStream() throws IOException { |
| matchFound = true; |
| return super.openOutputStream(); |
| } |
| @Override |
| public Writer openWriter() throws IOException { |
| matchFound = true; |
| return super.openWriter(); |
| } |
| } |
| JavaFileObject detector(JavaFileObject original) { |
| if (original != null && original.getKind() == Kind.CLASS |
| && (this.discriminatingSuffix == null || original.getName().endsWith(this.discriminatingSuffix))) { |
| return new JavaFileOutputDetector(original); |
| } |
| return original; |
| } |
| @Override |
| public FileObject getFileForOutput(Location location, String packageName, |
| String relativeName, FileObject sibling) throws IOException { |
| FileObject result = |
| super.getFileForOutput(location, packageName, relativeName, sibling); |
| if (result instanceof JavaFileObject) { |
| return detector((JavaFileObject) result); |
| } |
| return result; |
| } |
| @Override |
| public JavaFileObject getJavaFileForOutput(Location location, |
| String className, Kind kind, FileObject sibling) throws IOException { |
| return detector(super.getJavaFileForOutput(location, className, kind, sibling)); |
| } |
| } |
| class SetLocationDetector extends ForwardingStandardJavaFileManager<StandardJavaFileManager> { |
| private Location match; |
| private boolean matchFound; |
| SetLocationDetector(StandardJavaFileManager javaFileManager, Location location) { |
| super(javaFileManager); |
| this.match = location; |
| } |
| @Override |
| public void setLocation(Location location, Iterable<? extends File> path) |
| throws IOException { |
| if (location == this.match) { |
| this.matchFound = true; |
| } |
| super.setLocation(location, path); |
| } |
| boolean matchFound() { |
| return this.matchFound; |
| } |
| } |
| class SubstringDetector extends java.util.logging.Logger { |
| private String match; |
| private boolean matchFound; |
| SubstringDetector(String match) { |
| super("SubstringDetector", null); |
| this.match = match; |
| } |
| @Override |
| public void log(LogRecord record) { |
| if (!this.matchFound && record.getMessage().indexOf(this.match) != -1) { |
| this.matchFound = true; |
| } |
| } |
| boolean matchFound() { |
| return this.matchFound; |
| } |
| } |
| // most possibly basic test |
| public void test001_basic() { |
| runTest( |
| true /* shouldCompileOK */, |
| new String [] { /* sourceFiles */ |
| "X.java", |
| "public class X {}", |
| }, |
| null /* standardJavaFileManager */, |
| Arrays.asList("-d", OUTPUT_DIR) /* options */, |
| new String[] { /* compileFileNames */ |
| "X.java" |
| }, |
| "" /* expectedOutOutputString */, |
| "" /* expectedErrOutputString */, |
| true /* shouldFlushOutputDirectory */, |
| new String[] { /* classFileNames */ |
| "X.class" |
| }); |
| } |
| // exploring -d / FileManager interaction |
| // -d changes CLASS_OUTPUT location |
| public void test002_dash_d_option() { |
| if (JAVAC_COMPILER == null) { |
| System.out.println("No system java compiler available"); |
| return; |
| } |
| StandardJavaFileManager javacStandardJavaFileManager = JAVAC_COMPILER.getStandardFileManager(null, null, null); // will pick defaults up |
| runTest( |
| true /* shouldCompileOK */, |
| new String [] { /* sourceFiles */ |
| "X.java", |
| "public class X {}", |
| }, |
| javacStandardJavaFileManager /* standardJavaFileManager */, |
| Arrays.asList("-d", OUTPUT_DIR) /* options */, |
| new String[] { /* compileFileNames */ |
| "X.java" |
| }, |
| "" /* expectedOutOutputString */, |
| "" /* expectedErrOutputString */, |
| true /* shouldFlushOutputDirectory */, |
| new String[] { /* classFileNames */ |
| "X.class" |
| }); |
| assertEquals(OUTPUT_DIR, javacStandardJavaFileManager.getLocation(StandardLocation.CLASS_OUTPUT).toString()); |
| } |
| // exploring -d / FileManager interaction |
| // -d changes CLASS_OUTPUT location (OUTPUT_DIR subdirectory) |
| public void test003_dash_d_option() { |
| if (JAVAC_COMPILER == null) { |
| System.out.println("No system java compiler available"); |
| return; |
| } |
| StandardJavaFileManager javacStandardJavaFileManager = JAVAC_COMPILER.getStandardFileManager(null, null, null); // will pick defaults up |
| String outputDir = OUTPUT_DIR + File.separator + "bin"; |
| runTest( |
| true /* shouldCompileOK */, |
| new String [] { /* sourceFiles */ |
| "src/X.java", |
| "public class X {}", |
| }, |
| javacStandardJavaFileManager /* standardJavaFileManager */, |
| Arrays.asList("-d", outputDir) /* options */, |
| new String[] { /* compileFileNames */ |
| "src/X.java" |
| }, |
| "" /* expectedOutOutputString */, |
| "" /* expectedErrOutputString */, |
| true /* shouldFlushOutputDirectory */, |
| new String[] { /* classFileNames */ |
| "bin/X.class" |
| }); |
| assertEquals(outputDir, javacStandardJavaFileManager.getLocation(StandardLocation.CLASS_OUTPUT).toString()); |
| } |
| // exploring -d / FileManager interaction |
| // ecj uses the output location from the javac standard Java file manager if it |
| // is set |
| public void test004_no_dash_d_option() throws IOException { |
| if (JAVAC_COMPILER == null) { |
| System.out.println("No system java compiler available"); |
| return; |
| } |
| File binDirectory = new File(OUTPUT_DIR + File.separator + "bin"); |
| binDirectory.mkdir(); |
| StandardJavaFileManager javacStandardJavaFileManager = JAVAC_COMPILER.getStandardFileManager(null, null, null); // will pick defaults up |
| javacStandardJavaFileManager.setLocation( |
| StandardLocation.CLASS_OUTPUT, |
| Arrays.asList(binDirectory)); |
| runTest( |
| true /* shouldCompileOK */, |
| new String [] { /* sourceFiles */ |
| "src/X.java", |
| "public class X {}", |
| }, |
| javacStandardJavaFileManager /* standardJavaFileManager */, |
| null /* options */, |
| new String[] { /* compileFileNames */ |
| "src/X.java" |
| }, |
| "" /* expectedOutOutputString */, |
| "" /* expectedErrOutputString */, |
| true /* shouldFlushOutputDirectory */, |
| new String[] { /* classFileNames */ |
| "bin/X.class" |
| }); |
| } |
| // exploring -d / FileManager interaction |
| // ecj does not call setLocation on standard Java file managers; it uses |
| // handleOption instead; javac does the same |
| public void test005_dash_d_option_custom_file_manager() { |
| if (JAVAC_COMPILER == null) { |
| System.out.println("No system java compiler available"); |
| return; |
| } |
| StandardJavaFileManager javacJavaFileManager = JAVAC_COMPILER.getStandardFileManager(null, null, null); |
| SetLocationDetector customJavaFileManager = |
| new SetLocationDetector( |
| javacJavaFileManager, |
| StandardLocation.CLASS_OUTPUT); |
| runTest( |
| true /* shouldCompileOK */, |
| new String [] { /* sourceFiles */ |
| "X.java", |
| "public class X {}", |
| }, |
| customJavaFileManager /* standardJavaFileManager */, |
| Arrays.asList("-d", OUTPUT_DIR) /* options */, |
| new String[] { /* compileFileNames */ |
| "X.java" |
| }, |
| "" /* expectedOutOutputString */, |
| "" /* expectedErrOutputString */, |
| true /* shouldFlushOutputDirectory */, |
| new String[] { /* classFileNames */ |
| "X.class" |
| }); |
| assertEquals(OUTPUT_DIR, customJavaFileManager.getLocation(StandardLocation.CLASS_OUTPUT).toString()); |
| assertFalse(customJavaFileManager.matchFound()); |
| if (RUN_JAVAC && JAVAC_COMPILER != null) { |
| customJavaFileManager = new SetLocationDetector(javacJavaFileManager, |
| StandardLocation.CLASS_OUTPUT); |
| assertTrue(JAVAC_COMPILER.getTask(null, customJavaFileManager, null, |
| Arrays.asList("-d", OUTPUT_DIR), null, |
| customJavaFileManager.getJavaFileObjectsFromFiles( |
| Arrays.asList(new File(OUTPUT_DIR + File.separator + "X.java")))).call()); |
| assertFalse(customJavaFileManager.matchFound()); |
| } |
| } |
| // exploring -d / FileManager interaction |
| // ecj calls getLocation on a non-javac standard Java file manager |
| public void test006_no_dash_d_option_custom_file_manager() throws IOException { |
| if (JAVAC_COMPILER == null) { |
| System.out.println("No system java compiler available"); |
| return; |
| } |
| File binDirectory = new File(OUTPUT_DIR + File.separator + "bin"); |
| binDirectory.mkdirs(); |
| GetLocationDetector customJavaFileManager = |
| new GetLocationDetector( |
| JAVAC_COMPILER.getStandardFileManager(null, null, null), |
| StandardLocation.CLASS_OUTPUT); |
| customJavaFileManager.setLocation( |
| StandardLocation.CLASS_OUTPUT, |
| Arrays.asList(binDirectory)); |
| runTest( |
| true /* shouldCompileOK */, |
| new String [] { /* sourceFiles */ |
| "src/X.java", |
| "public class X {}", |
| }, |
| customJavaFileManager /* standardJavaFileManager */, |
| null /* options */, |
| new String[] { /* compileFileNames */ |
| "src/X.java" |
| }, |
| "" /* expectedOutOutputString */, |
| "" /* expectedErrOutputString */, |
| true /* shouldFlushOutputDirectory */, |
| new String[] { /* classFileNames */ |
| "bin/X.class" |
| }); |
| assertTrue(customJavaFileManager.matchFound()); // failure here means that getLocation was not called for the class output location |
| } |
| // https://bugs.eclipse.org/bugs/show_bug.cgi?id=226918 |
| // options consumption - compare with javac and ensure the consumption mechanism |
| // behaves the same on an option that is supported by both compilers |
| public void test007_options_consumption() throws IOException { |
| List<String> remainingAsList = Arrays.asList("output", "remainder"); |
| StandardJavaFileManager ecjStandardJavaFileManager = |
| COMPILER.getStandardFileManager(null /* diagnosticListener */, null /* locale */, null /* charset */); |
| Iterator<String> remaining = remainingAsList.iterator(); |
| assertTrue("does not support -d option", ecjStandardJavaFileManager.handleOption("-d", remaining)); |
| assertEquals("unexpected consumption rate", "remainder", remaining.next()); |
| if (RUN_JAVAC && JAVAC_COMPILER != null) { |
| StandardJavaFileManager javacStandardJavaFileManager = |
| ToolProvider.getSystemJavaCompiler().getStandardFileManager(null, null, null); // will pick defaults up |
| remaining = remainingAsList.iterator(); |
| assertTrue("does not support -d option", javacStandardJavaFileManager.handleOption("-d", remaining)); |
| assertEquals("unexpected consumption rate", "remainder", remaining.next()); |
| } |
| } |
| // https://bugs.eclipse.org/bugs/show_bug.cgi?id=226918 |
| // options consumption - check consumption rate on supported zero-args options |
| public void test008_options_consumption() throws IOException { |
| final String REMAINDER = "remainder"; |
| List<String> remainingAsList = Arrays.asList("output", REMAINDER); |
| StandardJavaFileManager ecjStandardJavaFileManager = |
| COMPILER.getStandardFileManager(null /* diagnosticListener */, null /* locale */, null /* charset */); |
| for (String option: CompilerToolTests.ZERO_ARG_OPTIONS) { |
| if (ecjStandardJavaFileManager.isSupportedOption(option) != -1) { // some options that the compiler support could well not be supported by the file manager |
| Iterator<String> remaining = remainingAsList.iterator(); |
| assertTrue("does not support " + option + " option", ecjStandardJavaFileManager.handleOption(option, remaining)); |
| assertEquals("unexpected consumption rate", REMAINDER, remaining.next()); |
| } |
| } |
| for (String option: CompilerToolTests.FAKE_ZERO_ARG_OPTIONS) { |
| if (ecjStandardJavaFileManager.isSupportedOption(option) != -1) { |
| Iterator<String> remaining = remainingAsList.iterator(); |
| assertTrue("does not support " + option + " option", ecjStandardJavaFileManager.handleOption(option, remaining)); |
| assertEquals("unexpected consumption rate", REMAINDER, remaining.next()); |
| } |
| } |
| } |
| // https://bugs.eclipse.org/bugs/show_bug.cgi?id=226918 |
| // options consumption - check consumption rate on supported one-arg options |
| public void test009_options_consumption() throws IOException { |
| final String REMAINDER = "remainder"; |
| List<String> remainingAsList = Arrays.asList("utf-8", REMAINDER); |
| StandardJavaFileManager ecjStandardJavaFileManager = |
| COMPILER.getStandardFileManager(null /* diagnosticListener */, null /* locale */, null /* charset */); |
| for (String option: CompilerToolTests.ONE_ARG_OPTIONS) { |
| if (ecjStandardJavaFileManager.isSupportedOption(option) != -1) { // some options that the compiler support could well not be supported by the file manager |
| Iterator<String> remaining = remainingAsList.iterator(); |
| assertTrue("does not support " + option + " option", ecjStandardJavaFileManager.handleOption(option, remaining)); |
| assertEquals("unexpected consumption rate", REMAINDER, remaining.next()); |
| } |
| } |
| } |
| // tests #10-11 show that ecj throws a RuntimeException when encountering a wrong |
| // encoding in its parameters, while the default compiler swallows it silently |
| // based upon the behavior of the command-line javac for the same level, we |
| // would expect an error to be raised in some fashion here, hence we make the |
| // tests fail when RUN_JAVAC is on |
| public void test010_inappropriate_encoding_diagnosis() throws IOException { |
| List<String> buggyEncoding = Arrays.asList("dummy"); |
| boolean passed = true; |
| try { |
| passed = COMPILER.getStandardFileManager(null /* diagnosticListener */, null /* locale */, null /* charset */). |
| handleOption("-encoding", buggyEncoding.iterator()); |
| } catch (RuntimeException e) { |
| passed = false; |
| } |
| assertFalse("does not catch inappropriate -encoding option", passed); |
| if (RUN_JAVAC && JAVAC_COMPILER != null) { |
| // this fails, which may be deemed appropriate or not; but at least |
| // test #11 shows that the behavior that can be observed from the |
| // outside is inappropriate |
| passed = true; |
| try { |
| passed = JAVAC_COMPILER.getStandardFileManager(null, null, null). |
| handleOption("-encoding", buggyEncoding.iterator()); |
| } catch (Throwable t) { |
| passed = false; |
| } |
| assertFalse("does not catch inappropriate -encoding option", passed); |
| } |
| } |
| public void test011_inappropriate_encoding_diagnosis() { |
| List<String> options = Arrays.asList("-d", OUTPUT_DIR, "-encoding", "dummy"); |
| boolean passed = true; |
| try { |
| runTest( |
| false /* shouldCompileOK */, |
| new String [] { /* sourceFiles */ |
| "X.java", |
| "public class X {}", |
| }, |
| null /* standardJavaFileManager */, |
| options /* options */, |
| new String[] { /* compileFileNames */ |
| "X.java" |
| }, |
| "" /* expectedOutOutputString */, |
| "" /* expectedErrOutputString */, |
| true /* shouldFlushOutputDirectory */, |
| null /* classFileNames */); |
| } catch (RuntimeException e) { |
| passed = false; |
| } |
| assertFalse("does not catch inappropriate -encoding option", passed); |
| if (RUN_JAVAC && JAVAC_COMPILER != null) { |
| // compared to what the command-line javac does, this is due to be a |
| // bug |
| passed = true; |
| try { |
| passed = JAVAC_COMPILER.getTask(null, null, null, options, null, |
| JAVAC_COMPILER.getStandardFileManager(null, null, null).getJavaFileObjectsFromFiles( |
| Arrays.asList(new File(OUTPUT_DIR + File.separator + "X.java")))).call(); |
| } catch (Throwable t) { |
| passed = false; |
| } |
| assertFalse("does not catch inappropriate -encoding option", passed); |
| } |
| } |
| // https://bugs.eclipse.org/bugs/show_bug.cgi?id=188796 |
| // files access must happen through the user-specified file manager |
| // simplest source read case |
| public void test012_files_access_read() throws IOException { |
| if (JAVAC_COMPILER == null) { |
| System.out.println("No system java compiler available"); |
| return; |
| } |
| GetJavaFileForInputDetector customJavaFileManager = |
| new GetJavaFileForInputDetector( |
| JAVAC_COMPILER.getStandardFileManager(null /* diagnosticListener */, null /* locale */, null /* charset */)); |
| runTest( |
| true /* shouldCompileOK */, |
| new String [] { /* sourceFiles */ |
| "X.java", |
| "public class X {}", |
| }, |
| customJavaFileManager /* standardJavaFileManager */, |
| Arrays.asList("-d", OUTPUT_DIR) /* options */, |
| new String[] { /* compileFileNames */ |
| "X.java" |
| }, |
| "" /* expectedOutOutputString */, |
| "" /* expectedErrOutputString */, |
| true /* shouldFlushOutputDirectory */, |
| new String[] { /* classFileNames */ |
| "X.class" |
| }); |
| assertTrue(customJavaFileManager.matchFound); |
| if (RUN_JAVAC && JAVAC_COMPILER != null) { |
| customJavaFileManager.matchFound = false; |
| assertTrue(JAVAC_COMPILER.getTask(null, customJavaFileManager, null, |
| Arrays.asList("-d", OUTPUT_DIR), null, |
| customJavaFileManager.getJavaFileObjectsFromFiles( |
| Arrays.asList(new File(OUTPUT_DIR + File.separator + "X.java")))).call()); |
| assertTrue(customJavaFileManager.matchFound); |
| } |
| } |
| // https://bugs.eclipse.org/bugs/show_bug.cgi?id=188796 |
| // files access must happen through the user-specified file manager |
| // source file accessed through the sourcepath |
| public void _test013_files_access_read() throws IOException { |
| if (JAVAC_COMPILER == null) { |
| System.out.println("No system java compiler available"); |
| return; |
| } |
| GetJavaFileForInputDetector customJavaFileManager = |
| new GetJavaFileForInputDetector( |
| COMPILER.getStandardFileManager(null /* diagnosticListener */, null /* locale */, null /* charset */), |
| "Y.java", Kind.SOURCE); |
| List<String> options = Arrays.asList( |
| "-d", OUTPUT_DIR, |
| "-sourcepath", OUTPUT_DIR + File.separator + "src2"); |
| runTest( |
| true /* shouldCompileOK */, |
| new String [] { /* sourceFiles */ |
| "src1/X.java", |
| "public class X {\n" + |
| " Y y;\n" + |
| "}", |
| "src2/Y.java", |
| "public class Y {}", |
| }, |
| customJavaFileManager /* standardJavaFileManager */, |
| options /* options */, |
| new String[] { /* compileFileNames */ |
| "src1/X.java" |
| }, |
| "" /* expectedOutOutputString */, |
| "" /* expectedErrOutputString */, |
| true /* shouldFlushOutputDirectory */, |
| new String[] { /* classFileNames */ |
| "X.class" |
| }); |
| assertTrue(customJavaFileManager.matchFound); |
| if (RUN_JAVAC && JAVAC_COMPILER != null) { |
| customJavaFileManager.matchFound = false; |
| assertTrue(JAVAC_COMPILER.getTask(null, customJavaFileManager, null, |
| options, null, |
| customJavaFileManager.getJavaFileObjectsFromFiles( |
| Arrays.asList(new File(OUTPUT_DIR + File.separator + "src1/X.java")))).call()); |
| assertTrue(customJavaFileManager.matchFound); |
| } |
| } |
| // https://bugs.eclipse.org/bugs/show_bug.cgi?id=188796 |
| // files access must happen through the user-specified file manager |
| // class file accessed for read through the classpath |
| public void _test014_files_access_read() throws IOException { |
| GetJavaFileForInputDetector customJavaFileManager = |
| new GetJavaFileForInputDetector( |
| COMPILER.getStandardFileManager(null /* diagnosticListener */, null /* locale */, null /* charset */), |
| "Y.class", Kind.CLASS); |
| List<String> options = Arrays.asList( |
| "-d", OUTPUT_DIR, |
| "-classpath", OUTPUT_DIR); |
| runTest( |
| true /* shouldCompileOK */, |
| new String [] { /* sourceFiles */ |
| "src2/Y.java", |
| "public class Y {}", |
| }, |
| customJavaFileManager /* standardJavaFileManager */, |
| options /* options */, |
| new String[] { /* compileFileNames */ |
| "src2/Y.java" |
| }, |
| "" /* expectedOutOutputString */, |
| "" /* expectedErrOutputString */, |
| true /* shouldFlushOutputDirectory */, |
| new String[] { /* classFileNames */ |
| "Y.class" |
| }); |
| runTest( |
| true /* shouldCompileOK */, |
| new String [] { /* sourceFiles */ |
| "src1/X.java", |
| "public class X {\n" + |
| " Y y;\n" + |
| "}", |
| }, |
| customJavaFileManager /* standardJavaFileManager */, |
| options /* options */, |
| new String[] { /* compileFileNames */ |
| "src1/X.java" |
| }, |
| "" /* expectedOutOutputString */, |
| "" /* expectedErrOutputString */, |
| false /* shouldFlushOutputDirectory */, |
| new String[] { /* classFileNames */ |
| "X.class" |
| }); |
| assertTrue(customJavaFileManager.matchFound); |
| if (RUN_JAVAC && JAVAC_COMPILER != null) { |
| // javac merely throws an exception, which is due to be a bug on their |
| // side |
| customJavaFileManager.matchFound = false; |
| assertTrue(JAVAC_COMPILER.getTask(null, customJavaFileManager, null, |
| options, null, |
| customJavaFileManager.getJavaFileObjectsFromFiles( |
| Arrays.asList(new File(OUTPUT_DIR + File.separator + "src1/X.java")))).call()); |
| assertTrue(customJavaFileManager.matchFound); |
| } |
| } |
| // https://bugs.eclipse.org/bugs/show_bug.cgi?id=188796 |
| // files access must happen through the user-specified file manager |
| // class file accessed for write |
| public void test015_files_access_write() throws IOException { |
| GetJavaFileForOutputDetector customJavaFileManager = |
| new GetJavaFileForOutputDetector( |
| COMPILER.getStandardFileManager(null /* diagnosticListener */, null /* locale */, null /* charset */), |
| "X.class"); |
| List<String> options = Arrays.asList("-d", OUTPUT_DIR); |
| runTest( |
| true /* shouldCompileOK */, |
| new String [] { /* sourceFiles */ |
| "src/X.java", |
| "public class X {\n" + |
| "}", |
| }, |
| customJavaFileManager /* standardJavaFileManager */, |
| options /* options */, |
| new String[] { /* compileFileNames */ |
| "src/X.java" |
| }, |
| "" /* expectedOutOutputString */, |
| "" /* expectedErrOutputString */, |
| true /* shouldFlushOutputDirectory */, |
| new String[] { /* classFileNames */ |
| "X.class" |
| }); |
| assertTrue(customJavaFileManager.matchFound); |
| if (RUN_JAVAC && JAVAC_COMPILER != null) { |
| customJavaFileManager.matchFound = false; |
| assertTrue(JAVAC_COMPILER.getTask(null, customJavaFileManager, null, |
| options, null, |
| customJavaFileManager.getJavaFileObjectsFromFiles( |
| Arrays.asList(new File(OUTPUT_DIR + File.separator + "src/X.java")))).call()); |
| assertTrue(customJavaFileManager.matchFound); |
| } |
| } |
| // https://bugs.eclipse.org/bugs/show_bug.cgi?id=188796 |
| // files access must happen through the user-specified file manager |
| // class file accessed for write |
| public void test016_files_access_write() throws IOException { |
| GetJavaFileForOutputDetector customJavaFileManager = |
| new GetJavaFileForOutputDetector( |
| COMPILER.getStandardFileManager(null /* diagnosticListener */, null /* locale */, null /* charset */), |
| "Y.class"); |
| List<String> options = Arrays.asList( |
| "-sourcepath", OUTPUT_DIR + File.separator + "src2"); |
| runTest( |
| true /* shouldCompileOK */, |
| new String [] { /* sourceFiles */ |
| "src/X.java", |
| "public class X {\n" + |
| " Y y;\n" + |
| "}", |
| "src2/Y.java", |
| "public class Y {\n" + |
| "}", |
| }, |
| customJavaFileManager /* standardJavaFileManager */, |
| options /* options */, |
| new String[] { /* compileFileNames */ |
| "src/X.java" |
| }, |
| "" /* expectedOutOutputString */, |
| "" /* expectedErrOutputString */, |
| true /* shouldFlushOutputDirectory */, |
| new String[] { /* classFileNames */ |
| "src/X.class" |
| }); |
| assertTrue(customJavaFileManager.matchFound); |
| if (RUN_JAVAC && JAVAC_COMPILER != null) { |
| customJavaFileManager.matchFound = false; |
| assertTrue(JAVAC_COMPILER.getTask(null, customJavaFileManager, null, |
| options, null, |
| customJavaFileManager.getJavaFileObjectsFromFiles( |
| Arrays.asList(new File(OUTPUT_DIR + File.separator + "src/X.java")))).call()); |
| assertTrue(customJavaFileManager.matchFound); |
| } |
| } |
| // https://bugs.eclipse.org/bugs/show_bug.cgi?id=227583 |
| public void test017_sourcepath_without_destination() throws IOException { |
| runTest( |
| true /* shouldCompileOK */, |
| new String [] { /* sourceFiles */ |
| "src1/X.java", |
| "public class X {\n" + |
| " Y y;\n" + |
| "}", |
| "src2/Y.java", |
| "public class Y {}", |
| }, |
| null /* standardJavaFileManager */, |
| Arrays.asList( |
| "-d", OUTPUT_DIR + "/bin1", /* options */ |
| "-sourcepath", OUTPUT_DIR + "/src2"), |
| new String[] { /* compileFileNames */ |
| "src1/X.java" |
| }, |
| "" /* expectedOutOutputString */, |
| "" /* expectedErrOutputString */, |
| true /* shouldFlushOutputDirectory */, |
| new String[] { /* classFileNames */ |
| "bin1/X.class", |
| "bin1/Y.class" |
| }); |
| } |
| // https://bugs.eclipse.org/bugs/show_bug.cgi?id=227583 |
| // see BatchCompilerTest#68 and following, that show how the option works |
| // with jsr199-less ecj |
| public void _test018_sourcepath_with_destination() throws IOException { |
| runTest( |
| true /* shouldCompileOK */, |
| new String [] { /* sourceFiles */ |
| "src1/X.java", |
| "public class X {\n" + |
| " Y y;\n" + |
| "}", |
| "src2/Y.java", |
| "public class Y {}", |
| }, |
| null /* standardJavaFileManager */, |
| Arrays.asList( |
| "-d", OUTPUT_DIR + "/bin1", /* options */ |
| "-sourcepath", "\"" + OUTPUT_DIR + "/src2\"[-d \"" + OUTPUT_DIR + "/bin2\"]"), |
| new String[] { /* compileFileNames */ |
| "src1/X.java" |
| }, |
| "" /* expectedOutOutputString */, |
| "" /* expectedErrOutputString */, |
| true /* shouldFlushOutputDirectory */, |
| new String[] { /* classFileNames */ |
| "bin1/X.class", |
| "bin2/Y.class" |
| }); |
| } |
| // https://bugs.eclipse.org/bugs/show_bug.cgi?id=227583 |
| public void test019_sourcepath_without_destination() throws IOException { |
| String sourceDirectoryName = OUTPUT_DIR + "/src2"; |
| File sourceFolder = new File(sourceDirectoryName); |
| if (!sourceFolder.exists()) { |
| if (!sourceFolder.mkdirs()) { |
| // source folder could not be built |
| return; |
| } |
| } |
| StandardJavaFileManager ecjStandardJavaFileManager = |
| COMPILER.getStandardFileManager(null /* diagnosticListener */, null /* locale */, null /* charset */); |
| assertTrue(ecjStandardJavaFileManager.handleOption( |
| "-sourcepath", |
| Arrays.asList(OUTPUT_DIR + "/src2").iterator())); |
| runTest( |
| true /* shouldCompileOK */, |
| new String [] { /* sourceFiles */ |
| "src1/X.java", |
| "public class X {\n" + |
| " Y y;\n" + |
| "}", |
| "src2/Y.java", |
| "public class Y {}", |
| }, |
| ecjStandardJavaFileManager /* standardJavaFileManager */, |
| Arrays.asList("-d", OUTPUT_DIR + "/bin1") /* options */, |
| new String[] { /* compileFileNames */ |
| "src1/X.java" |
| }, |
| "" /* expectedOutOutputString */, |
| "" /* expectedErrOutputString */, |
| true /* shouldFlushOutputDirectory */, |
| new String[] { /* classFileNames */ |
| "bin1/X.class", |
| "bin1/Y.class" |
| }); |
| } |
| // https://bugs.eclipse.org/bugs/show_bug.cgi?id=227583 |
| public void _test020_sourcepath_with_destination() throws IOException { |
| StandardJavaFileManager ecjStandardJavaFileManager = |
| COMPILER.getStandardFileManager(null /* diagnosticListener */, null /* locale */, null /* charset */); |
| assertTrue(ecjStandardJavaFileManager.handleOption( |
| "-sourcepath", |
| Arrays.asList("\"" + OUTPUT_DIR + "/src2\"[-d \"" + OUTPUT_DIR + "/bin2\"]").iterator())); |
| runTest( |
| true /* shouldCompileOK */, |
| new String [] { /* sourceFiles */ |
| "src1/X.java", |
| "public class X {\n" + |
| " Y y;\n" + |
| "}", |
| "src2/Y.java", |
| "public class Y {}", |
| }, |
| ecjStandardJavaFileManager /* standardJavaFileManager */, |
| Arrays.asList("-d", OUTPUT_DIR + "/bin1") /* options */, |
| new String[] { /* compileFileNames */ |
| "src1/X.java" |
| }, |
| "" /* expectedOutOutputString */, |
| "" /* expectedErrOutputString */, |
| true /* shouldFlushOutputDirectory */, |
| new String[] { /* classFileNames */ |
| "bin1/X.class", |
| "bin2/Y.class" |
| }); |
| } |
| // most basic output test |
| public void test021_output_streams() throws IOException { |
| ByteArrayOutputStream |
| outBuffer = new ByteArrayOutputStream(), |
| errBuffer = new ByteArrayOutputStream(); |
| CompilationTask task = COMPILER.getTask( |
| new PrintWriter(outBuffer), |
| COMPILER.getStandardFileManager(null /* diagnosticListener */, null /* locale */, null /* charset */), |
| new CompilerInvocationDiagnosticListener(new PrintWriter(errBuffer)), |
| Arrays.asList("-v"), null, null); |
| assertTrue(task.call()); |
| Properties properties = new Properties(); |
| InputStream resourceAsStream = null; |
| try { |
| resourceAsStream = Main.class.getResourceAsStream("messages.properties"); |
| properties.load(resourceAsStream); |
| } finally { |
| if (resourceAsStream != null) { |
| resourceAsStream.close(); |
| } |
| } |
| assertTrue(outBuffer.toString().startsWith(properties.getProperty("compiler.name"))); |
| assertTrue(errBuffer.toString().isEmpty()); |
| } |
| // https://bugs.eclipse.org/bugs/show_bug.cgi?id=236814 |
| public void test022_output_streams() throws IOException { |
| ByteArrayOutputStream |
| outBuffer = new ByteArrayOutputStream(), |
| errBuffer = new ByteArrayOutputStream(); |
| PrintStream |
| systemOut = System.out, |
| systemErr = System.err; |
| System.setOut(new PrintStream(outBuffer)); |
| System.setErr(new PrintStream(errBuffer)); |
| CompilationTask task = COMPILER.getTask( |
| null, |
| COMPILER.getStandardFileManager(null /* diagnosticListener */, null /* locale */, null /* charset */), |
| new CompilerInvocationDiagnosticListener(new PrintWriter(errBuffer)), |
| Arrays.asList("-v"), null, null); |
| try { |
| assertTrue(task.call()); |
| assertTrue(outBuffer.toString().isEmpty()); |
| assertTrue(errBuffer.toString().startsWith("Eclipse Compiler for Java")); |
| } finally { |
| System.setOut(systemOut); |
| System.setErr(systemErr); |
| } |
| } |
| // https://bugs.eclipse.org/bugs/show_bug.cgi?id=236817 |
| // according to JavaCompiler#getTask, out should receive supplementary compiler |
| // output only; errors should be funneled through the diagnostic listener |
| public void _test023_output_streams() throws IOException { |
| runTest( |
| false /* shouldCompileOK */, |
| new String [] { /* sourceFiles */ |
| "X.java", |
| "public class Y {}", |
| }, |
| null /* standardJavaFileManager */, |
| Arrays.asList("-d", OUTPUT_DIR) /* options */, |
| new String[] { /* compileFileNames */ |
| "X.java" |
| }, |
| "" /* expectedOutOutputString */, |
| "----------\n" + /* expectedErrOutputString */ |
| "1. ERROR in X.java (at line 1)\n" + |
| " public class Y {}\n" + |
| " ^\n" + |
| "The public type Y must be defined in its own file\n" + |
| "----------\n" + |
| "1 problem (1 error)", |
| true /* shouldFlushOutputDirectory */, |
| null /* classFileNames */); |
| } |
| } |