/*******************************************************************************
* Copyright (c) 2000, 2004 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
*******************************************************************************/
package org.eclipse.jdt.core.tests.compiler.regression;
import java.io.File;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.PrintWriter;
import java.text.MessageFormat;
import junit.framework.Test;
import org.eclipse.jdt.core.tests.util.Util;
import org.eclipse.jdt.internal.compiler.batch.Main;
public class BatchCompilerTest extends AbstractRegressionTest {
public static final String OUTPUT_DIR_PLACEHOLDER = "---OUTPUT_DIR_PLACEHOLDER---";
static final String JRE_HOME_DIR = Util.getJREDirectory();
static {
// TESTS_NAMES = new String[] { "test000" };
// TESTS_NUMBERS = new int[] { 27 };
// TESTS_RANGE = new int[] { 11, -1 };
}
public BatchCompilerTest(String name) {
super(name);
}
public static Test suite() {
return buildTestSuiteUniqueCompliance(testClass(), COMPLIANCE_1_5);
}
/**
* Run a compilation test that is expected to complete successfully and
* compare the outputs to expected ones.
*
* @param testFiles
* the source files, given as a suite of file name, file content;
* file names are relative to the output directory
* @param commandLine
* the command line to pass to
* {@link Main#compile(String) Main#compile}
* @param expectedSuccessOutOutputString
* the expected contents of the standard output stream; pass null
* to bypass the comparison
* @param expectedSuccessErrOutputString
* the expected contents of the standard error output stream;
* pass null to bypass the comparison
* @param shouldFlushOutputDirectory
* pass true to get the output directory flushed before the test
* runs
*/
protected void runConformTest(String[] testFiles, String commandLine,
String expectedSuccessOutOutputString,
String expectedSuccessErrOutputString,
boolean shouldFlushOutputDirectory) {
runTest(true, testFiles, commandLine, expectedSuccessOutOutputString,
expectedSuccessErrOutputString, shouldFlushOutputDirectory);
}
/**
* Run a compilation test that is expected to fail and compare the outputs
* to expected ones.
*
* @param testFiles
* the source files, given as a suite of file name, file content;
* file names are relative to the output directory
* @param commandLine
* the command line to pass to
* {@link Main#compile(String) Main#compile}
* @param expectedFailureOutOutputString
* the expected contents of the standard output stream; pass null
* to bypass the comparison
* @param expectedFailureErrOutputString
* the expected contents of the standard error output stream;
* pass null to bypass the comparison
* @param shouldFlushOutputDirectory
* pass true to get the output directory flushed before the test
* runs
*/
protected void runNegativeTest(String[] testFiles, String commandLine,
String expectedFailureOutOutputString,
String expectedFailureErrOutputString,
boolean shouldFlushOutputDirectory) {
runTest(false, testFiles, commandLine, expectedFailureOutOutputString,
expectedFailureErrOutputString, shouldFlushOutputDirectory);
}
/**
* Worker method for runConformTest and runNegativeTest.
*
* @param shouldCompileOK
* set to true if the compiler should compile the given sources
* without errors
* @param testFiles
* the source files, given as a suite of file name, file content;
* file names are relative to the output directory
* @param commandLine
* the command line to pass to
* {@link Main#compile(String) Main#compile}
* @param expectedOutOutputString
* the expected contents of the standard output stream; pass null
* to bypass the comparison
* @param expectedErrOutputString
* the expected contents of the standard error output stream;
* pass null to bypass the comparison
* @param shouldFlushOutputDirectory
* pass true to get the output directory flushed before the test
* runs
*/
private void runTest(boolean shouldCompileOK, String[] testFiles, String commandLine,
String expectedOutOutputString,
String expectedErrOutputString,
boolean shouldFlushOutputDirectory) {
File outputDirectory = new File(OUTPUT_DIR);
if (shouldFlushOutputDirectory)
Util.flushDirectoryContent(outputDirectory);
try {
if (!outputDirectory.isDirectory()) {
outputDirectory.mkdirs();
}
PrintWriter sourceFileWriter;
for (int i = 0; i < testFiles.length; i += 2) {
String fileName = OUTPUT_DIR + File.separator + testFiles[i];
File file = new File(fileName), innerOutputDirectory = file
.getParentFile();
if (!innerOutputDirectory.isDirectory()) {
innerOutputDirectory.mkdirs();
}
sourceFileWriter = new PrintWriter(new FileOutputStream(file));
sourceFileWriter.write(testFiles[i + 1]);
sourceFileWriter.close();
}
} catch (FileNotFoundException e) {
e.printStackTrace();
throw new RuntimeException(e);
}
String printerWritersNameRoot = OUTPUT_DIR + File.separator + testName();
String outFileName = printerWritersNameRoot + "out.txt",
errFileName = printerWritersNameRoot + "err.txt";
Main batchCompiler;
try {
batchCompiler = new Main(new PrintWriter(new FileOutputStream(
outFileName)), new PrintWriter(new FileOutputStream(
errFileName)), false);
} catch (FileNotFoundException e) {
System.out.println(getClass().getName() + '#' + getName());
e.printStackTrace();
throw new RuntimeException(e);
}
boolean compileOK;
try {
final String[] tokenizeCommandLine = Main.tokenize(commandLine);
compileOK = batchCompiler.compile(tokenizeCommandLine);
} catch (RuntimeException e) {
compileOK = false;
System.out.println(getClass().getName() + '#' + getName());
e.printStackTrace();
throw e;
}
String outOutputString = Util.fileContent(outFileName),
errOutputString = Util.fileContent(errFileName);
boolean compareOK = false;
if (compileOK == shouldCompileOK) {
compareOK = semiNormalizedComparison(expectedOutOutputString,
outOutputString, outputDirNormalizer)
&& semiNormalizedComparison(expectedErrOutputString,
errOutputString, outputDirNormalizer);
}
if (compileOK != shouldCompileOK || !compareOK) {
System.out.println(getClass().getName() + '#' + getName());
for (int i = 0; i < testFiles.length; i += 2) {
System.out.print(testFiles[i]);
System.out.println(" [");
System.out.println(testFiles[i + 1]);
System.out.println("]");
}
}
if (compileOK != shouldCompileOK)
System.out.println(errOutputString);
if (compileOK == shouldCompileOK && !compareOK) {
System.out.println(
"------------ [START OUT] ------------\n"
+ "------------- Expected: -------------\n"
+ expectedOutOutputString
+ "\n------------- but was: -------------\n"
+ outOutputString
+ "\n--------- (cut and paste:) ----------\n"
+ Util.displayString(outputDirNormalizer
.normalized(outOutputString))
+ "\n------------- [END OUT] -------------\n"
+ "------------ [START ERR] ------------\n"
+ "------------- Expected: -------------\n"
+ expectedErrOutputString
+ "\n------------- but was: -------------\n"
+ errOutputString
+ "\n--------- (cut and paste:) ----------\n"
+ Util.displayString(outputDirNormalizer
.normalized(errOutputString))
+ "\n------------- [END ERR] -------------\n");
}
if (shouldCompileOK)
assertTrue("Unexpected problems: " + errOutputString, compileOK);
else
assertTrue("Unexpected success: " + errOutputString, !compileOK);
assertTrue("Unexpected output for invocation with arguments ["
+ commandLine + "]:\n--[START]--\n" + outOutputString + "\n"
+ errOutputString + "\n---[END]---\n", compareOK);
}
/**
* Abstract normalizer for output comparison. This class merely embodies a
* chain of responsibility, plus the signature of the method of interest
* here, that is {@link #normalized(String) normalized}.
*/
private static abstract class Normalizer {
private Normalizer nextInChain;
Normalizer(Normalizer nextInChain) {
this.nextInChain = nextInChain;
}
String normalized(String originalValue) {
String result;
if (nextInChain == null)
result = Util.convertToIndependantLineDelimiter(originalValue);
else
result = nextInChain.normalized(originalValue);
return result;
}
}
/**
* This normalizer replaces occurrences of a given string with a given
* placeholder.
*/
private static class StringNormalizer extends Normalizer {
private String match;
private int matchLength;
private String placeholder;
StringNormalizer(Normalizer nextInChain, String match, String placeholder) {
super(nextInChain);
this.match = match;
this.matchLength = match.length();
this.placeholder = placeholder;
}
String normalized(String originalValue) {
String result;
StringBuffer normalizedValueBuffer = new StringBuffer(originalValue);
int nextOccurrenceIndex;
while ((nextOccurrenceIndex = normalizedValueBuffer.indexOf(match)) != -1)
normalizedValueBuffer.replace(nextOccurrenceIndex,
nextOccurrenceIndex + matchLength, placeholder);
result = super.normalized(normalizedValueBuffer.toString());
return result;
}
}
/**
* This normalizer replaces the whole classpaths section of a log file with
* a normalized placeholder.
*/
private static class XMLClasspathsSectionNormalizer extends Normalizer {
XMLClasspathsSectionNormalizer() {
super(null);
}
XMLClasspathsSectionNormalizer(Normalizer nextInChain) {
super(nextInChain);
}
String normalized(String originalValue) {
String result;
StringBuffer normalizedValueBuffer = new StringBuffer(originalValue);
int classpathsStartTagStart = normalizedValueBuffer
.indexOf(""), classpathsEndTagStart = normalizedValueBuffer
.indexOf("");
if (classpathsStartTagStart != -1 && classpathsEndTagStart != -1
&& classpathsStartTagStart < classpathsEndTagStart)
normalizedValueBuffer.replace(classpathsStartTagStart + 12,
classpathsEndTagStart, "NORMALIZED SECTION");
result = super.normalized(normalizedValueBuffer.toString());
return result;
}
}
/**
* This normalizer removes a selected range of lines from a log file.
*/
private static class LinesRangeNormalizer extends Normalizer {
private int first, number;
LinesRangeNormalizer() {
super(null);
first = number = 0;
}
LinesRangeNormalizer(Normalizer nextInChain) {
super(nextInChain);
first = number = 0;
}
/**
* Make a new normalizer able to suppress a range of lines delimited by
* "\n" sequences from a log file (or another string).
*
* @param nextInChain
* the next normalizer in the chain of responsibility; pass
* null if none is needed
* @param firstLineToRemove
* the index of the first line to remove, starting at 0
* @param linesNumber
* the number or lines to remove; if 0, no other
* transformation occurs than those operated by nextInChain
* (if any)
*/
LinesRangeNormalizer(Normalizer nextInChain, int firstLineToRemove,
int linesNumber) {
super(nextInChain);
first = firstLineToRemove;
number = linesNumber >= 0 ? linesNumber : 0;
}
String normalized(String originalValue) {
String result;
if (number == 0 || originalValue.length() == 0)
result = super.normalized(originalValue);
else {
final int START = 0, KEEPING = 1, KEEPING_R = 2, SKIPING = 3, SKIPING_R = 4, END = 5, ERROR = 6;
int state = START, currentLineIndex = 0, currentCharIndex = 0, sourceLength;
char currentChar = '\0';
if (first <= 0)
state = SKIPING;
else
state = KEEPING;
StringBuffer normalizedValueBuffer = new StringBuffer(), source = new StringBuffer(
originalValue);
sourceLength = source.length();
while (state != END && state != ERROR) {
if (currentCharIndex < sourceLength) {
currentChar = source.charAt(currentCharIndex++);
switch (currentChar) {
case '\r':
switch (state) {
case KEEPING:
normalizedValueBuffer.append(currentChar);
state = KEEPING_R;
break;
case SKIPING:
state = SKIPING_R;
break;
default:
state = ERROR;
}
break;
case '\n':
currentLineIndex++;
switch (state) {
case KEEPING: // tolerate Linux line delimiters
case KEEPING_R:
normalizedValueBuffer.append(currentChar);
if (currentLineIndex == first) {
state = SKIPING;
}
break;
case SKIPING: // tolerate Linux line delimiters
case SKIPING_R:
// in effect, we tolerate too big first and number
// values
if (currentLineIndex >= first + number) {
if (currentCharIndex < sourceLength)
normalizedValueBuffer.append(source
.substring(currentCharIndex));
state = END;
} else {
state = SKIPING;
}
break;
default:
state = ERROR;
}
break;
default:
switch (state) {
case KEEPING:
normalizedValueBuffer.append(currentChar);
break;
case SKIPING:
break;
default:
state = ERROR;
}
}
}
else if (currentChar == '\n')
state = END;
else
state = ERROR;
}
if (state == ERROR)
normalizedValueBuffer
.append("UNEXPECTED ERROR in LinesRangeNormalizer");
result = super.normalized(normalizedValueBuffer.toString());
}
return result;
}
}
/**
* Normalizer instance that replaces occurrences of OUTPUT_DIR with
* OUTPUT_DIR_PLACEHOLDER.
*/
private static Normalizer outputDirNormalizer = new StringNormalizer(null,
OUTPUT_DIR, OUTPUT_DIR_PLACEHOLDER);
/**
* Normalizer instance for non XML log files.
*/
private static Normalizer textLogsNormalizer = new StringNormalizer(
new XMLClasspathsSectionNormalizer(new LinesRangeNormalizer(null,
0, 2)), OUTPUT_DIR, OUTPUT_DIR_PLACEHOLDER);
/**
* Normalizer instance for XML log files.
*/
private static Normalizer xmlLogsNormalizer = new StringNormalizer(
new XMLClasspathsSectionNormalizer(new LinesRangeNormalizer(null,
1, 1)), OUTPUT_DIR, OUTPUT_DIR_PLACEHOLDER);
/**
* Return true if and only if the two strings passed as parameters compare
* equal, modulo the transformation of the second string by a normalizer
* passed in parameter. This is meant to erase the variations of subparts of
* the compared strings in function of the test machine, the user account,
* etc.
*
* @param keep
* the first string to compare, gets compared as it is
* @param normalize
* the second string to compare, passed through the normalizer
* before comparison
* @param normalizer
* the transformation applied to normalize
* @return true if keep and normalize compare equal after normalize has been
* normalized
*/
private boolean semiNormalizedComparison(String keep, String normalize,
Normalizer normalizer) {
if (keep == null)
return normalize == null;
if (normalize == null)
return false;
// return keep.equals(normalizer.normalized(normalize));
return equals(keep, normalizer.normalized(normalize));
}
private static boolean equals(String a, String b) {
StringBuffer aBuffer = new StringBuffer(a), bBuffer = new StringBuffer(b);
int length = aBuffer.length();
if (length != bBuffer.length()) {
System.err.println("a and b lengths differ");
return false;
}
for (int i = 0; i < length; i++)
if (aBuffer.charAt(i) != bBuffer.charAt(i)) {
int beforeStart = i - 5, beforeEnd = i - 1, afterStart = i + 1, afterEnd = i + 5;
if (beforeStart < 0) {
beforeStart = 0;
if (beforeEnd < 0)
beforeEnd = 0;
}
if (afterEnd >= length) {
afterEnd = length - 1;
if (afterStart >= length)
afterStart = length - 1;
}
System.err.println("a and b differ at rank: " + i
+ " a: ..." + aBuffer.substring(beforeStart, beforeEnd)
+ "<" + aBuffer.charAt(i) + ">"
+ aBuffer.substring(afterStart, afterEnd) + "..."
+ " b: ..." + bBuffer.substring(beforeStart, beforeEnd)
+ "<" + bBuffer.charAt(i) + ">"
+ bBuffer.substring(afterStart, afterEnd) + "...");
return false;
}
return true;
}
public void test001() {
String commandLine = "-classpath \"D:/a folder\";d:/jdk1.4/jre/lib/rt.jar -1.4 -preserveAllLocals -g -verbose d:/eclipse/workspaces/development2.0/plugins/Bar/src2/ -d d:/test";
String expected = " <-classpath> <-1.4> <-preserveAllLocals> <-g> <-verbose> <-d> ";
String[] args = Main.tokenize(commandLine);
StringBuffer buffer = new StringBuffer(30);
for (int i = 0; i < args.length; i++){
buffer.append(" <"+args[i]+">");
}
String result = buffer.toString();
//System.out.println(Util.displayString(result, 2));
assertEquals("incorrect tokenized command line",
expected,
result);
}
public void test002() {
String commandLine = "-classpath \"a folder\";\"b folder\"";
String expected = " <-classpath> ";
String[] args = Main.tokenize(commandLine);
StringBuffer buffer = new StringBuffer(30);
for (int i = 0; i < args.length; i++){
buffer.append(" <"+args[i]+">");
}
String result = buffer.toString();
//System.out.println(Util.displayString(result, 2));
assertEquals("incorrect tokenized command line",
expected,
result);
}
public void test003() {
String commandLine = "-classpath \"a folder;b folder\"";
String expected = " <-classpath> ";
String[] args = Main.tokenize(commandLine);
StringBuffer buffer = new StringBuffer(30);
for (int i = 0; i < args.length; i++){
buffer.append(" <"+args[i]+">");
}
String result = buffer.toString();
//System.out.println(Util.displayString(result, 2));
assertEquals("incorrect tokenized command line",
expected,
result);
}
public void test004() {
String commandLine = "\"d:/tmp A/\"A.java -classpath \"d:/tmp A\";d:/jars/rt.jar -nowarn -time -g -d d:/tmp";
String expected = " <-classpath> <-nowarn> <-time> <-g> <-d> ";
String[] args = Main.tokenize(commandLine);
StringBuffer buffer = new StringBuffer(30);
for (int i = 0; i < args.length; i++){
buffer.append(" <"+args[i]+">");
}
String result = buffer.toString();
//System.out.println(Util.displayString(result, 2));
assertEquals("incorrect tokenized command line",
expected,
result);
}
public void test005() {
String commandLine = "\"d:/tmp A/\"A.java -classpath d:/jars/rt.jar;\"d:/tmp A\";\"toto\" -nowarn -time -g -d d:/tmp";
String expected = " <-classpath> <-nowarn> <-time> <-g> <-d> ";
String[] args = Main.tokenize(commandLine);
StringBuffer buffer = new StringBuffer(30);
for (int i = 0; i < args.length; i++){
buffer.append(" <"+args[i]+">");
}
String result = buffer.toString();
//System.out.println(Util.displayString(result, 2));
assertEquals("incorrect tokenized command line",
expected,
result);
}
public void test006() {
String commandLine = "\"d:/tmp A/A.java\" -classpath d:/jars/rt.jar;\"d:/tmp A\";d:/tmpB/ -nowarn -time -g -d d:/tmp";
String expected = " <-classpath> <-nowarn> <-time> <-g> <-d> ";
String[] args = Main.tokenize(commandLine);
StringBuffer buffer = new StringBuffer(30);
for (int i = 0; i < args.length; i++){
buffer.append(" <"+args[i]+">");
}
String result = buffer.toString();
//System.out.println(Util.displayString(result, 2));
assertEquals("incorrect tokenized command line",
expected,
result);
}
// test the tester - runConformTest
public void _test007(){
this.runConformTest(
new String[] {
"X.java",
"import java.util.List;\n" +
"\n" +
"@SuppressWarnings(\"all\"//$NON-NLS-1$\n" +
")\n" +
"public class X {\n" +
" public static void main(String[] args) {\n" +
" if (false) {\n" +
" ;\n" +
" } else {\n" +
" }\n" +
" // Zork z;\n" +
" }\n" +
"}"
},
"\"" + OUTPUT_DIR + File.separator + "X.java\""
+ " -1.5 -g -preserveAllLocals"
+ " -bootclasspath " + JRE_HOME_DIR + "/lib/rt.jar"
+ " -cp " + JRE_HOME_DIR + "/lib/jce.jar"
+ " -verbose -warn:+deprecation,syntheticAccess,uselessTypeCheck,unsafe,finalBound,unusedLocal"
+ " -proceedOnError -referenceInfo -d \"" + OUTPUT_DIR + "\"",
"[1 .class file generated]\n",
"----------\n" +
"1. WARNING in ---OUTPUT_DIR_PLACEHOLDER---" + File.separator + "X.java\n" +
" (at line 1)\n" +
" import java.util.List;\n" +
" ^^^^^^^^^^^^^^\n" +
"The import java.util.List is never used\n" +
"----------\n" +
"1 problem (1 warning)", true);
}
// test the tester - runNegativeTest
public void _test008(){
this.runNegativeTest(
new String[] {
"X.java",
"import java.util.List;\n" +
"\n" +
"@SuppressWarnings(\"all\"//$NON-NLS-1$\n" +
")\n" +
"public class X {\n" +
" public static void main(String[] args) {\n" +
" if (false) {\n" +
" ;\n" +
" } else {\n" +
" }\n" +
" Zork z;\n" +
" }\n" +
"}"
},
"\"" + OUTPUT_DIR + File.separator + "X.java\""
+ " -1.5 -g -preserveAllLocals"
+ " -bootclasspath " + JRE_HOME_DIR + "/lib/rt.jar"
+ " -cp " + JRE_HOME_DIR + "/lib/jce.jar"
+ " -verbose -warn:+deprecation,syntheticAccess,uselessTypeCheck,unsafe,finalBound,unusedLocal"
+ " -proceedOnError -referenceInfo -d \"" + OUTPUT_DIR + "\"",
"[1 .class file generated]\n",
"----------\n" +
"1. ERROR in ---OUTPUT_DIR_PLACEHOLDER---" + File.separator + "X.java\n" +
" (at line 11)\n" +
" Zork z;\n" +
" ^^^^\n" +
"Zork cannot be resolved to a type\n" +
"----------\n" +
"1 problem (1 error)", true);
}
// https://bugs.eclipse.org/bugs/show_bug.cgi?id=92398 -- a case that works, another that does not
// revisit this test case depending on https://bugs.eclipse.org/bugs/show_bug.cgi?id=95349
public void _test009(){
this.runNegativeTest(
new String[] {
"X.java",
"/** */\n" +
"public class X {\n" +
" OK1 ok1;\n" +
" OK2 ok2;\n" +
" Warn warn;\n" +
" KO ko;\n" +
" Zork z;\n" +
"}",
"OK1.java",
"/** */\n" +
"public class OK1 {\n" +
" // empty\n" +
"}",
"OK2.java",
"/** */\n" +
"public class OK2 {\n" +
" // empty\n" +
"}",
"Warn.java",
"/** */\n" +
"public class Warn {\n" +
" // empty\n" +
"}",
"KO.java",
"/** */\n" +
"public class KO {\n" +
" // empty\n" +
"}",
},
"\"" + OUTPUT_DIR + File.separator + "X.java\""
+ " -1.5 -g -preserveAllLocals"
+ " -cp \"" + OUTPUT_DIR + "[+OK2" + File.pathSeparator + "~Warn"
+ File.pathSeparator + "-KO]\""
+ " -verbose -warn:+deprecation,syntheticAccess,uselessTypeCheck,unsafe,finalBound,unusedLocal"
+ " -proceedOnError -referenceInfo -d \"" + OUTPUT_DIR + "\"",
"[5 .class files generated]\n",
"----------\n" +
"1. WARNING in ---OUTPUT_DIR_PLACEHOLDER---" + File.separator + "X.java\n" +
" (at line 5)\n" +
" Warn warn;\n" +
" ^^^^\n" +
"Discouraged access: Warn\n" +
"----------\n" +
"----------\n" +
"2. WARNING in ---OUTPUT_DIR_PLACEHOLDER---" + File.separator + "X.java\n" +
" (at line 6)\n" +
" KO ko;\n" +
" ^^\n" +
"Access restriction: KO\n" +
"----------\n" +
"----------\n" +
"3. ERROR in ---OUTPUT_DIR_PLACEHOLDER---" + File.separator + "X.java\n" +
" (at line 7)\n" +
" Zork z;\n" +
" ^^^^\n" +
"Zork cannot be resolved to a type\n" +
"----------\n" +
"3 problems (1 error, 2 warnings)",
true);
}
// command line - no user classpath nor bootclasspath
public void _test010(){
this.runConformTest(
new String[] {
"X.java",
"import java.util.List;\n" +
"\n" +
"@SuppressWarnings(\"all\"//$NON-NLS-1$\n" +
")\n" +
"public class X {\n" +
" public static void main(String[] args) {\n" +
" if (false) {\n" +
" ;\n" +
" } else {\n" +
" }\n" +
" // Zork z;\n" +
" }\n" +
"}"
},
"\"" + OUTPUT_DIR + File.separator + "X.java\""
+ " -1.5 -g -preserveAllLocals"
+ " -verbose -warn:+deprecation,syntheticAccess,uselessTypeCheck,unsafe,finalBound,unusedLocal"
+ " -proceedOnError -referenceInfo -d \"" + OUTPUT_DIR + "\"",
"[1 .class file generated]\n",
"----------\n" +
"1. WARNING in ---OUTPUT_DIR_PLACEHOLDER---" + File.separator + "X.java\n" +
" (at line 1)\n" +
" import java.util.List;\n" +
" ^^^^^^^^^^^^^^\n" +
"The import java.util.List is never used\n" +
"----------\n" +
"1 problem (1 warning)", true);
}
// command line - unusual classpath (ends with ';', still OK)
public void test011(){
this.runConformTest(
new String[] {
"X.java",
"/** */\n" +
"public class X {\n" +
"}",
},
"\"" + OUTPUT_DIR + File.separator + "X.java\""
+ " -1.5 -g -preserveAllLocals"
+ " -cp \"" + OUTPUT_DIR + "[+**/OK2;~**/Warn;-KO]"
+ "\"" + File.pathSeparator
+ " -proceedOnError -referenceInfo -d \"" + OUTPUT_DIR + "\"",
"",
"",
true);
}
// command line - help
public void _test012(){
final String expectedOutput =
"{0}\n" +
" \n" +
" Usage: \n" +
" If directories are specified, then their source contents are compiled.\n" +
" Possible options are listed below. Options enabled by default are prefixed with \'\'+\'\'\n" +
" \n" +
" Classpath options:\n" +
" -cp -classpath \n" +
" specify location for application classes and sources. Each\n" +
" directory or file can specify access rules for types between\n" +
" \'\'[\'\' and \'\']\'\' (e.g. [-X.java] to deny access to type X)\n" +
" -bootclasspath \n" +
" specify location for system classes. Each directory or file can\n" +
" specify access rules for types between \'\'[\'\' and \'\']\'\' (e.g. [-X.java]\n" +
" to deny access to type X)\n" +
" -sourcepath \n" +
" specify location for application sources. Each directory or file can\n" +
" specify access rules for types between \'\'[\'\' and \'\']\'\' (e.g. [-X.java]\n" +
" to deny access to type X)\n" +
" -extdirs \n" +
" specify location for extension zip/jar files\n" +
" -d destination directory (if omitted, no directory is created)\n" +
" -d none generate no .class files\n" +
" -encoding specify custom encoding for all sources. Each file/directory can override it\n" +
" when suffixed with \'\'[\'\'\'\']\'\' (e.g. X.java[utf8])\n" +
" \n" +
" Compliance options:\n" +
" -1.3 use 1.3 compliance level (implicit -source 1.3 -target 1.1)\n" +
" -1.4 + use 1.4 compliance level (implicit -source 1.3 -target 1.2)\n" +
" -1.5 use 1.5 compliance level (implicit -source 1.5 -target 1.5)\n" +
" -source set source level: 1.3 to 1.5 (or 5 or 5.0)\n" +
" -target set classfile target level: 1.1 to 1.5 (or 5 or 5.0)\n" +
" \n" +
" Warning options:\n" +
" -deprecation + deprecation outside deprecated code\n" +
" -nowarn disable all warnings\n" +
" -warn:none disable all warnings\n" +
" -warn: enable exactly the listed warnings\n" +
" -warn:+ enable additional warnings\n" +
" -warn:- disable specific warnings\n" +
" allDeprecation deprecation including inside deprecated code\n" +
" allJavadoc invalid or missing javadoc\n" +
" assertIdentifier + \'\'assert\'\' used as identifier\n" +
" boxing autoboxing conversion\n" +
" charConcat + char[] in String concat\n" +
" conditionAssign possible accidental boolean assignment\n" +
" constructorName + method with constructor name\n" +
" dep-ann missing @Deprecated annotation\n" +
" deprecation + deprecation outside deprecated code\n" +
" emptyBlock undocumented empty block\n" +
" enumSwitch incomplete enum switch\n" +
" fieldHiding field hiding another variable\n" +
" finalBound type parameter with final bound\n" +
" finally + finally block not completing normally\n" +
" indirectStatic indirect reference to static member\n" +
" intfAnnotation + annotation type used as super interface\n" +
" intfNonInherited + interface non-inherited method compatibility\n" +
" javadoc invalid javadoc\n" +
" localHiding local variable hiding another variable\n" +
" maskedCatchBlock + hidden catch block\n" +
" nls string literal lacking non-nls tag //$NON-NLS-$\n" +
" noEffectAssign + assignment without effect\n" +
" null missing or redundant null check\n" +
" over-ann missing @Override annotation\n" +
" pkgDefaultMethod + attempt to override package-default method\n" +
" semicolon unnecessary semicolon, empty statement\n" +
" serial + missing serialVersionUID\n" +
" suppress + enable @SuppressWarnings\n" +
" unqualifiedField unqualified reference to field\n" +
" unchecked + unchecked type operation\n" +
" unusedArgument unread method parameter\n" +
" unusedImport + unused import declaration\n" +
" unusedLocal unread local variable\n" +
" unusedPrivate unused private member declaration\n" +
" unusedThrown unused declared thrown exception\n" +
" unnecessaryElse unnecessary else clause\n" +
" uselessTypeCheck unnecessary cast/instanceof operation\n" +
" specialParamHiding constructor or setter parameter hiding another field\n" +
" staticReceiver + non-static reference to static member\n" +
" syntheticAccess synthetic access for innerclass\n" +
" tasks() tasks identified by tags inside comments\n" +
" typeHiding + type parameter hiding another type\n" +
" varargsCast + varargs argument need explicit cast\n" +
" warningToken + unhandled warning token in @SuppressWarnings\n" +
" \n" +
" Debug options:\n" +
" -g[:lines,vars,source] custom debug info\n" +
" -g:lines,source + both lines table and source debug info\n" +
" -g all debug info\n" +
" -g:none no debug info\n" +
" -preserveAllLocals preserve unused local vars for debug purpose\n" +
" \n" +
" Ignored options:\n" +
" -J