Submitted by: Jay Glanville <jayglanville@home.com> git-svn-id: https://svn.apache.org/repos/asf/ant/core/trunk@268444 13f79535-47bb-0310-9956-ffa450edef68master
@@ -9,6 +9,10 @@ Changes that could break older environments: | |||
* <perforce> has been replaced by a number of new tasks. | |||
* <javac> is now implemented using a factory. This makes extending | |||
javac to use a new compiler a lot easier but may break custom | |||
versions of this task that rely on the old implementation. | |||
Other changes: | |||
-------------- | |||
@@ -3170,7 +3170,12 @@ inclusion/exclusion of files works, and how to write patterns.</p> | |||
<li>jvc (the Command-Line Compiler from Microsoft's SDK for Java / | |||
Visual J++)</li> | |||
</ul> | |||
<p>For JDK 1.1/1.2 is classic the default. For JDK 1.3 is modern the default.</p> | |||
<p>For JDK 1.1/1.2 is classic the default. For JDK 1.3 is modern the default. | |||
If you whish to use a different compiler interface then one of the four | |||
supplied, then write a class that implements the CompilerAdapter interface | |||
(package org.apache.tools.ant.taskdefs.compilers). Supply the full | |||
classname in the "build.compiler" property. | |||
</p> | |||
<h3>Parameters</h3> | |||
<table border="1" cellpadding="2" cellspacing="0"> | |||
<tr> | |||
@@ -3284,6 +3289,18 @@ inclusion/exclusion of files works, and how to write patterns.</p> | |||
tracking for compilers that support this (jikes and classic)</td> | |||
<td align="center" valign="top">No</td> | |||
</tr> | |||
<tr> | |||
<td valign="top">includeAntRuntime</td> | |||
<td valign="top">whether or not to include the ant runtime libraries. | |||
Default is no.</td> | |||
<td align="center" valign="top">No</td> | |||
</tr> | |||
<tr> | |||
<td valign="top">includeJavaRuntim</td> | |||
<td valign="top">whether or not to include the default runtime | |||
libraries from the executing virtual machine. Default is no.</td> | |||
<td align="center" valign="top">No</td> | |||
</tr> | |||
<tr> | |||
<td valign="top">failonerror</td> <td valign="top"> | |||
If set to false, the build will continue even if there are compilation errors. | |||
@@ -355,7 +355,7 @@ public class Execute { | |||
exitValue = value; | |||
} | |||
protected int getExitValue() { | |||
public int getExitValue() { | |||
return exitValue; | |||
} | |||
@@ -59,11 +59,9 @@ import org.apache.tools.ant.DirectoryScanner; | |||
import org.apache.tools.ant.Project; | |||
import org.apache.tools.ant.types.*; | |||
import org.apache.tools.ant.util.*; | |||
import org.apache.tools.ant.taskdefs.compilers.*; | |||
import java.lang.reflect.Method; | |||
import java.lang.reflect.Constructor; | |||
import java.io.*; | |||
import java.util.*; | |||
import java.io.File; | |||
/** | |||
* Task to compile Java source files. This task can take the following | |||
@@ -81,6 +79,9 @@ import java.util.*; | |||
* <li>target | |||
* <li>depend | |||
* <li>vebose | |||
* <li>failonerror | |||
* <li>includeantruntime | |||
* <li>includejavaruntime | |||
* </ul> | |||
* Of these arguments, the <b>sourcedir</b> and <b>destdir</b> are required. | |||
* <p> | |||
@@ -91,16 +92,13 @@ import java.util.*; | |||
* @author James Davidson <a href="mailto:duncan@x180.com">duncan@x180.com</a> | |||
* @author Robin Green <a href="mailto:greenrd@hotmail.com">greenrd@hotmail.com</a> | |||
* @author <a href="mailto:stefan.bodewig@epost.de">Stefan Bodewig</a> | |||
* @author <a href="mailto:jayglanville@home.com">J D Glanville</a> | |||
*/ | |||
public class Javac extends MatchingTask { | |||
/** | |||
* Integer returned by the "Modern" jdk1.3 compiler to indicate success. | |||
*/ | |||
private static final int | |||
MODERN_COMPILER_SUCCESS = 0; | |||
private static final String FAIL_MSG = "Compile failed, messages should have been provided."; | |||
private static final String FAIL_MSG | |||
= "Compile failed, messages should have been provided."; | |||
private Path src; | |||
private File destDir; | |||
@@ -114,7 +112,8 @@ public class Javac extends MatchingTask { | |||
private String target; | |||
private Path bootclasspath; | |||
private Path extdirs; | |||
private static String lSep = System.getProperty("line.separator"); | |||
private boolean includeAntRuntime = true; | |||
private boolean includeJavaRuntime = false; | |||
protected boolean failOnError = true; | |||
protected File[] compileList = new File[0]; | |||
@@ -143,6 +142,11 @@ public class Javac extends MatchingTask { | |||
} | |||
} | |||
/** Gets the source dirs to find the source java files. */ | |||
public Path getSrcdir() { | |||
return src; | |||
} | |||
/** | |||
* Set the destination directory into which the Java source | |||
* files should be compiled. | |||
@@ -151,6 +155,14 @@ public class Javac extends MatchingTask { | |||
this.destDir = destDir; | |||
} | |||
/** | |||
* Gets the destination directory into which the java source files | |||
* should be compiled. | |||
*/ | |||
public File getDestdir() { | |||
return destDir; | |||
} | |||
/** | |||
* Set the classpath to be used for this compilation. | |||
*/ | |||
@@ -162,6 +174,11 @@ public class Javac extends MatchingTask { | |||
} | |||
} | |||
/** Gets the classpath to be used for this compilation. */ | |||
public Path getClasspath() { | |||
return compileClasspath; | |||
} | |||
/** | |||
* Maybe creates a nested classpath element. | |||
*/ | |||
@@ -191,6 +208,14 @@ public class Javac extends MatchingTask { | |||
} | |||
} | |||
/** | |||
* Gets the bootclasspath that will be used to compile the classes | |||
* against. | |||
*/ | |||
public Path getBootclasspath() { | |||
return bootclasspath; | |||
} | |||
/** | |||
* Maybe creates a nested classpath element. | |||
*/ | |||
@@ -220,6 +245,14 @@ public class Javac extends MatchingTask { | |||
} | |||
} | |||
/** | |||
* Gets the extension directories that will be used during the | |||
* compilation. | |||
*/ | |||
public Path getExtdirs() { | |||
return extdirs; | |||
} | |||
/** | |||
* Maybe creates a nested classpath element. | |||
*/ | |||
@@ -244,6 +277,13 @@ public class Javac extends MatchingTask { | |||
failOnError = !proceed; | |||
} | |||
/** | |||
* Gets the failonerror flag. | |||
*/ | |||
public boolean getFailonerror() { | |||
return failOnError; | |||
} | |||
/** | |||
* Set the deprecation flag. | |||
*/ | |||
@@ -251,6 +291,11 @@ public class Javac extends MatchingTask { | |||
this.deprecation = deprecation; | |||
} | |||
/** Gets the deprecation flag. */ | |||
public boolean getDeprecation() { | |||
return deprecation; | |||
} | |||
/** | |||
* Set the Java source file encoding name. | |||
*/ | |||
@@ -258,6 +303,11 @@ public class Javac extends MatchingTask { | |||
this.encoding = encoding; | |||
} | |||
/** Gets the java source file encoding name. */ | |||
public String getEncoding() { | |||
return encoding; | |||
} | |||
/** | |||
* Set the debug flag. | |||
*/ | |||
@@ -265,26 +315,46 @@ public class Javac extends MatchingTask { | |||
this.debug = debug; | |||
} | |||
/** Gets the debug flag. */ | |||
public boolean getDebug() { | |||
return debug; | |||
} | |||
/** | |||
* Set the optimize flag. | |||
*/ | |||
public void setOptimize(boolean optimize) { | |||
this.optimize = optimize; | |||
} | |||
public void setOptimize(boolean optimize) { | |||
this.optimize = optimize; | |||
} | |||
/** Gets the optimize flag. */ | |||
public boolean getOptimize() { | |||
return optimize; | |||
} | |||
/** | |||
* Set the depend flag. | |||
*/ | |||
public void setDepend(boolean depend) { | |||
this.depend = depend; | |||
} | |||
public void setDepend(boolean depend) { | |||
this.depend = depend; | |||
} | |||
/** Gets the depend flag. */ | |||
public boolean getDepend() { | |||
return depend; | |||
} | |||
/** | |||
* Set the verbose flag. | |||
*/ | |||
public void setVerbose(boolean verbose) { | |||
this.verbose = verbose; | |||
} | |||
public void setVerbose(boolean verbose) { | |||
this.verbose = verbose; | |||
} | |||
/** Gets the verbose flag. */ | |||
public boolean getVerbose() { | |||
return verbose; | |||
} | |||
/** | |||
* Sets the target VM that the classes will be compiled for. Valid | |||
@@ -294,6 +364,42 @@ public class Javac extends MatchingTask { | |||
this.target = target; | |||
} | |||
/** Gets the target VM that the classes will be compiled for. */ | |||
public String getTarget() { | |||
return target; | |||
} | |||
/** | |||
* Include ant's own classpath in this task's classpath? | |||
*/ | |||
public void setIncludeantruntime( boolean include ) { | |||
includeAntRuntime = include; | |||
} | |||
/** | |||
* Gets whether or not the ant classpath is to be included in the | |||
* task's classpath. | |||
*/ | |||
public boolean getIncludeantruntime() { | |||
return includeAntRuntime; | |||
} | |||
/** | |||
* Sets whether or not to include the java runtime libraries to this | |||
* task's classpath. | |||
*/ | |||
public void setIncludejavaruntime( boolean include ) { | |||
includeJavaRuntime = include; | |||
} | |||
/** | |||
* Gets whether or not the java runtime should be included in this | |||
* task's classpath. | |||
*/ | |||
public boolean getIncludejavaruntime() { | |||
return includeJavaRuntime; | |||
} | |||
/** | |||
* Executes the task. | |||
*/ | |||
@@ -312,7 +418,7 @@ public class Javac extends MatchingTask { | |||
throw new BuildException("destination directory \"" + destDir + "\" does not exist or is not a directory", location); | |||
} | |||
// scan source directories and dest directory to build up both copy lists and | |||
// scan source directories and dest directory to build up | |||
// compile lists | |||
resetFileLists(); | |||
for (int i=0; i<list.length; i++) { | |||
@@ -340,27 +446,19 @@ public class Javac extends MatchingTask { | |||
} | |||
if (compileList.length > 0) { | |||
CompilerAdapter adapter = CompilerAdapterFactory.getCompiler( | |||
compiler, this ); | |||
log("Compiling " + compileList.length + | |||
" source file" | |||
+ (compileList.length == 1 ? "" : "s") | |||
+ (destDir != null ? " to " + destDir : "")); | |||
boolean compileSucceeded = false; | |||
if (compiler.equalsIgnoreCase("classic")) { | |||
compileSucceeded = doClassicCompile(); | |||
} else if (compiler.equalsIgnoreCase("modern")) { | |||
compileSucceeded = doModernCompile(); | |||
} else if (compiler.equalsIgnoreCase("jikes")) { | |||
compileSucceeded = doJikesCompile(); | |||
} else if (compiler.equalsIgnoreCase("jvc")) { | |||
compileSucceeded = doJvcCompile(); | |||
} else { | |||
String msg = "Don't know how to use compiler " + compiler; | |||
throw new BuildException(msg, location); | |||
} | |||
// now we need to populate the compiler adapter | |||
adapter.setJavac( this ); | |||
if (!compileSucceeded) { | |||
// finally, lets execute the compiler!! | |||
if (!adapter.execute()) { | |||
if (failOnError) { | |||
throw new BuildException(FAIL_MSG, location); | |||
} | |||
@@ -382,7 +480,6 @@ public class Javac extends MatchingTask { | |||
* Scans the directory looking for source files to be compiled. | |||
* The results are returned in the class variable compileList | |||
*/ | |||
protected void scanDir(File srcDir, File destDir, String files[]) { | |||
GlobPatternMapper m = new GlobPatternMapper(); | |||
m.setFrom("*.java"); | |||
@@ -391,527 +488,19 @@ public class Javac extends MatchingTask { | |||
File[] newFiles = sfs.restrictAsFiles(files, srcDir, destDir, m); | |||
if (newFiles.length > 0) { | |||
File[] newCompileList = new File[compileList.length + newFiles.length]; | |||
System.arraycopy(compileList, 0, newCompileList, 0, compileList.length); | |||
System.arraycopy(newFiles, 0, newCompileList, compileList.length, newFiles.length); | |||
File[] newCompileList = new File[compileList.length + | |||
newFiles.length]; | |||
System.arraycopy(compileList, 0, newCompileList, 0, | |||
compileList.length); | |||
System.arraycopy(newFiles, 0, newCompileList, | |||
compileList.length, newFiles.length); | |||
compileList = newCompileList; | |||
} | |||
} | |||
/** | |||
* Builds the compilation classpath. | |||
* | |||
* @param addRuntime Shall <code>rt.jar</code> or | |||
* <code>classes.zip</code> be added to the classpath. | |||
*/ | |||
protected Path getCompileClasspath(boolean addRuntime) { | |||
Path classpath = new Path(project); | |||
// add dest dir to classpath so that previously compiled and | |||
// untouched classes are on classpath | |||
if (destDir != null) { | |||
classpath.setLocation(destDir); | |||
} | |||
// Combine the build classpath with the system classpath, in an | |||
// order determined by the value of build.classpath | |||
if (compileClasspath == null) { | |||
classpath.addExisting(Path.systemClasspath); | |||
} else { | |||
classpath.addExisting(compileClasspath.concatSystemClasspath()); | |||
} | |||
// optionally add the runtime classes | |||
if (addRuntime) { | |||
if (System.getProperty("java.vendor").toLowerCase().indexOf("microsoft") >= 0) { | |||
// Pull in *.zip from packages directory | |||
FileSet msZipFiles = new FileSet(); | |||
msZipFiles.setDir(new File(System.getProperty("java.home") + File.separator + "Packages")); | |||
msZipFiles.setIncludes("*.ZIP"); | |||
classpath.addFileset(msZipFiles); | |||
} | |||
else if (Project.getJavaVersion() == Project.JAVA_1_1) { | |||
classpath.addExisting(new Path(null, | |||
System.getProperty("java.home") | |||
+ File.separator + "lib" | |||
+ File.separator | |||
+ "classes.zip")); | |||
} else { | |||
// JDK > 1.1 seems to set java.home to the JRE directory. | |||
classpath.addExisting(new Path(null, | |||
System.getProperty("java.home") | |||
+ File.separator + "lib" | |||
+ File.separator + "rt.jar")); | |||
// Just keep the old version as well and let addExistingToPath | |||
// sort it out. | |||
classpath.addExisting(new Path(null, | |||
System.getProperty("java.home") | |||
+ File.separator +"jre" | |||
+ File.separator + "lib" | |||
+ File.separator + "rt.jar")); | |||
} | |||
} | |||
return classpath; | |||
} | |||
/** | |||
* Peforms a compile using the classic compiler that shipped with | |||
* JDK 1.1 and 1.2. | |||
* | |||
* @return true if the compile succeeded | |||
*/ | |||
private boolean doClassicCompile() throws BuildException { | |||
log("Using classic compiler", Project.MSG_VERBOSE); | |||
Commandline cmd = setupJavacCommand(); | |||
// Use reflection to be able to build on all JDKs | |||
/* | |||
// provide the compiler a different message sink - namely our own | |||
sun.tools.javac.Main compiler = | |||
new sun.tools.javac.Main(new LogOutputStream(this, Project.MSG_WARN), "javac"); | |||
if (!compiler.compile(cmd.getArguments())) { | |||
throw new BuildException("Compile failed"); | |||
} | |||
*/ | |||
try { | |||
// Create an instance of the compiler, redirecting output to | |||
// the project log | |||
OutputStream logstr = new LogOutputStream(this, Project.MSG_WARN); | |||
Class c = Class.forName("sun.tools.javac.Main"); | |||
Constructor cons = c.getConstructor(new Class[] { OutputStream.class, String.class }); | |||
Object compiler = cons.newInstance(new Object[] { logstr, "javac" }); | |||
// Call the compile() method | |||
Method compile = c.getMethod("compile", new Class [] { String[].class }); | |||
Boolean ok = (Boolean)compile.invoke(compiler, new Object[] {cmd.getArguments()}); | |||
return ok.booleanValue(); | |||
} | |||
catch (ClassNotFoundException ex) { | |||
throw new BuildException("Cannot use classic compiler, as it is not available"+ | |||
" A common solution is to set the environment variable"+ | |||
" JAVA_HOME to your jdk directory.", location); | |||
} | |||
catch (Exception ex) { | |||
if (ex instanceof BuildException) { | |||
throw (BuildException) ex; | |||
} else { | |||
throw new BuildException("Error starting classic compiler: ", ex, location); | |||
} | |||
} | |||
} | |||
/** | |||
* Performs a compile using the newer compiler that ships with JDK 1.3 | |||
* | |||
* @return true if the compile succeeded | |||
*/ | |||
private boolean doModernCompile() throws BuildException { | |||
try { | |||
Class.forName("com.sun.tools.javac.Main"); | |||
} catch (ClassNotFoundException cnfe) { | |||
log("Modern compiler is not available - using classic compiler", Project.MSG_WARN); | |||
return doClassicCompile(); | |||
} | |||
log("Using modern compiler", Project.MSG_VERBOSE); | |||
Commandline cmd = setupJavacCommand(); | |||
PrintStream err = System.err; | |||
PrintStream out = System.out; | |||
// Use reflection to be able to build on all JDKs >= 1.1: | |||
try { | |||
PrintStream logstr = | |||
new PrintStream(new LogOutputStream(this, Project.MSG_WARN)); | |||
System.setOut(logstr); | |||
System.setErr(logstr); | |||
Class c = Class.forName ("com.sun.tools.javac.Main"); | |||
Object compiler = c.newInstance (); | |||
Method compile = c.getMethod ("compile", | |||
new Class [] {(new String [] {}).getClass ()}); | |||
int result = ((Integer) compile.invoke | |||
(compiler, new Object[] {cmd.getArguments()})) .intValue (); | |||
return (result == MODERN_COMPILER_SUCCESS); | |||
} catch (Exception ex) { | |||
if (ex instanceof BuildException) { | |||
throw (BuildException) ex; | |||
} else { | |||
throw new BuildException("Error starting modern compiler", ex, location); | |||
} | |||
} finally { | |||
System.setErr(err); | |||
System.setOut(out); | |||
} | |||
/** Gets the list of files to be compiled. */ | |||
public File[] getFileList() { | |||
return compileList; | |||
} | |||
/** | |||
* Does the command line argument processing common to classic and | |||
* modern. | |||
*/ | |||
private Commandline setupJavacCommand() { | |||
Commandline cmd = new Commandline(); | |||
Path classpath = getCompileClasspath(false); | |||
if (deprecation == true) { | |||
cmd.createArgument().setValue("-deprecation"); | |||
} | |||
if (destDir != null) { | |||
cmd.createArgument().setValue("-d"); | |||
cmd.createArgument().setFile(destDir); | |||
} | |||
cmd.createArgument().setValue("-classpath"); | |||
// Just add "sourcepath" to classpath ( for JDK1.1 ) | |||
if (Project.getJavaVersion().startsWith("1.1")) { | |||
cmd.createArgument().setValue(classpath.toString() | |||
+ File.pathSeparator | |||
+ src.toString()); | |||
} else { | |||
cmd.createArgument().setPath(classpath); | |||
cmd.createArgument().setValue("-sourcepath"); | |||
cmd.createArgument().setPath(src); | |||
if (target != null) { | |||
cmd.createArgument().setValue("-target"); | |||
cmd.createArgument().setValue(target); | |||
} | |||
} | |||
if (encoding != null) { | |||
cmd.createArgument().setValue("-encoding"); | |||
cmd.createArgument().setValue(encoding); | |||
} | |||
if (debug) { | |||
cmd.createArgument().setValue("-g"); | |||
} | |||
if (optimize) { | |||
cmd.createArgument().setValue("-O"); | |||
} | |||
if (bootclasspath != null) { | |||
cmd.createArgument().setValue("-bootclasspath"); | |||
cmd.createArgument().setPath(bootclasspath); | |||
} | |||
if (extdirs != null) { | |||
cmd.createArgument().setValue("-extdirs"); | |||
cmd.createArgument().setPath(extdirs); | |||
} | |||
if (depend) { | |||
if (Project.getJavaVersion().startsWith("1.1")) { | |||
cmd.createArgument().setValue("-depend"); | |||
} else if (Project.getJavaVersion().startsWith("1.2")) { | |||
cmd.createArgument().setValue("-Xdepend"); | |||
} else { | |||
log("depend attribute is not supported by the modern compiler", | |||
Project.MSG_WARN); | |||
} | |||
} | |||
if (verbose) { | |||
cmd.createArgument().setValue("-verbose"); | |||
} | |||
logAndAddFilesToCompile(cmd); | |||
return cmd; | |||
} | |||
/** | |||
* Logs the compilation parameters, adds the files to compile and logs the | |||
* &qout;niceSourceList" | |||
*/ | |||
protected void logAndAddFilesToCompile(Commandline cmd) { | |||
log("Compilation args: " + cmd.toString(), | |||
Project.MSG_VERBOSE); | |||
StringBuffer niceSourceList = new StringBuffer("File"); | |||
if (compileList.length != 1) { | |||
niceSourceList.append("s"); | |||
} | |||
niceSourceList.append(" to be compiled:"); | |||
niceSourceList.append(lSep); | |||
for (int i=0; i < compileList.length; i++) { | |||
String arg = compileList[i].getAbsolutePath(); | |||
cmd.createArgument().setValue(arg); | |||
niceSourceList.append(" " + arg + lSep); | |||
} | |||
log(niceSourceList.toString(), Project.MSG_VERBOSE); | |||
} | |||
/** | |||
* Performs a compile using the Jikes compiler from IBM.. | |||
* Mostly of this code is identical to doClassicCompile() | |||
* However, it does not support all options like | |||
* bootclasspath, extdirs, deprecation and so on, because | |||
* there is no option in jikes and I don't understand | |||
* what they should do. | |||
* | |||
* It has been successfully tested with jikes >1.10 | |||
* | |||
* @author skanthak@muehlheim.de | |||
* | |||
* @return true if the compile succeeded | |||
*/ | |||
private boolean doJikesCompile() throws BuildException { | |||
log("Using jikes compiler", Project.MSG_VERBOSE); | |||
Path classpath = new Path(project); | |||
// Jikes doesn't support bootclasspath dir (-bootclasspath) | |||
// so we'll emulate it for compatibility and convenience. | |||
if (bootclasspath != null) { | |||
classpath.append(bootclasspath); | |||
} | |||
// Jikes doesn't support an extension dir (-extdir) | |||
// so we'll emulate it for compatibility and convenience. | |||
addExtdirsToClasspath(classpath); | |||
classpath.append(getCompileClasspath(true)); | |||
// Jikes has no option for source-path so we | |||
// will add it to classpath. | |||
classpath.append(src); | |||
// if the user has set JIKESPATH we should add the contents as well | |||
String jikesPath = System.getProperty("jikes.class.path"); | |||
if (jikesPath != null) { | |||
classpath.append(new Path(project, jikesPath)); | |||
} | |||
Commandline cmd = new Commandline(); | |||
cmd.setExecutable("jikes"); | |||
if (deprecation == true) | |||
cmd.createArgument().setValue("-deprecation"); | |||
if (destDir != null) { | |||
cmd.createArgument().setValue("-d"); | |||
cmd.createArgument().setFile(destDir); | |||
} | |||
cmd.createArgument().setValue("-classpath"); | |||
cmd.createArgument().setPath(classpath); | |||
if (encoding != null) { | |||
cmd.createArgument().setValue("-encoding"); | |||
cmd.createArgument().setValue(encoding); | |||
} | |||
if (debug) { | |||
cmd.createArgument().setValue("-g"); | |||
} | |||
if (optimize) { | |||
cmd.createArgument().setValue("-O"); | |||
} | |||
if (verbose) { | |||
cmd.createArgument().setValue("-verbose"); | |||
} | |||
if (depend) { | |||
cmd.createArgument().setValue("-depend"); | |||
} | |||
/** | |||
* XXX | |||
* Perhaps we shouldn't use properties for these | |||
* three options (emacs mode, warnings and pedantic), | |||
* but include it in the javac directive? | |||
*/ | |||
/** | |||
* Jikes has the nice feature to print error | |||
* messages in a form readable by emacs, so | |||
* that emacs can directly set the cursor | |||
* to the place, where the error occured. | |||
*/ | |||
String emacsProperty = project.getProperty("build.compiler.emacs"); | |||
if (emacsProperty != null && Project.toBoolean(emacsProperty)) { | |||
cmd.createArgument().setValue("+E"); | |||
} | |||
/** | |||
* Jikes issues more warnings that javac, for | |||
* example, when you have files in your classpath | |||
* that don't exist. As this is often the case, these | |||
* warning can be pretty annoying. | |||
*/ | |||
String warningsProperty = project.getProperty("build.compiler.warnings"); | |||
if (warningsProperty != null && !Project.toBoolean(warningsProperty)) { | |||
cmd.createArgument().setValue("-nowarn"); | |||
} | |||
/** | |||
* Jikes can issue pedantic warnings. | |||
*/ | |||
String pedanticProperty = project.getProperty("build.compiler.pedantic"); | |||
if (pedanticProperty != null && Project.toBoolean(pedanticProperty)) { | |||
cmd.createArgument().setValue("+P"); | |||
} | |||
/** | |||
* Jikes supports something it calls "full dependency | |||
* checking", see the jikes documentation for differences | |||
* between -depend and +F. | |||
*/ | |||
String fullDependProperty = project.getProperty("build.compiler.fulldepend"); | |||
if (fullDependProperty != null && Project.toBoolean(fullDependProperty)) { | |||
cmd.createArgument().setValue("+F"); | |||
} | |||
int firstFileName = cmd.size(); | |||
logAndAddFilesToCompile(cmd); | |||
return executeExternalCompile(cmd.getCommandline(), firstFileName) == 0; | |||
} | |||
/** | |||
* Do the compile with the specified arguments. | |||
* @param args - arguments to pass to process on command line | |||
* @param firstFileName - index of the first source file in args | |||
*/ | |||
protected int executeExternalCompile(String[] args, int firstFileName) { | |||
String[] commandArray = null; | |||
File tmpFile = null; | |||
try { | |||
/* | |||
* Many system have been reported to get into trouble with | |||
* long command lines - no, not only Windows ;-). | |||
* | |||
* POSIX seems to define a lower limit of 4k, so use a temporary | |||
* file if the total length of the command line exceeds this limit. | |||
*/ | |||
if (Commandline.toString(args).length() > 4096) { | |||
PrintWriter out = null; | |||
try { | |||
tmpFile = new File("jikes"+(new Random(System.currentTimeMillis())).nextLong()); | |||
out = new PrintWriter(new FileWriter(tmpFile)); | |||
for (int i = firstFileName; i < args.length; i++) { | |||
out.println(args[i]); | |||
} | |||
out.flush(); | |||
commandArray = new String[firstFileName+1]; | |||
System.arraycopy(args, 0, commandArray, 0, firstFileName); | |||
commandArray[firstFileName] = "@" + tmpFile.getAbsolutePath(); | |||
} catch (IOException e) { | |||
throw new BuildException("Error creating temporary file", e, location); | |||
} finally { | |||
if (out != null) { | |||
try {out.close();} catch (Throwable t) {} | |||
} | |||
} | |||
} else { | |||
commandArray = args; | |||
} | |||
try { | |||
Execute exe = new Execute(new LogStreamHandler(this, | |||
Project.MSG_INFO, | |||
Project.MSG_WARN)); | |||
exe.setAntRun(project); | |||
exe.setWorkingDirectory(project.getBaseDir()); | |||
exe.setCommandline(commandArray); | |||
exe.execute(); | |||
return exe.getExitValue(); | |||
} catch (IOException e) { | |||
throw new BuildException("Error running Jikes compiler", e, location); | |||
} | |||
} finally { | |||
if (tmpFile != null) { | |||
tmpFile.delete(); | |||
} | |||
} | |||
} | |||
/** | |||
* Emulation of extdirs feature in java >= 1.2. | |||
* This method adds all files in the given | |||
* directories (but not in sub-directories!) to the classpath, | |||
* so that you don't have to specify them all one by one. | |||
* @param classpath - Path to append files to | |||
*/ | |||
protected void addExtdirsToClasspath(Path classpath) { | |||
if (extdirs == null) { | |||
String extProp = System.getProperty("java.ext.dirs"); | |||
if (extProp != null) { | |||
extdirs = new Path(project, extProp); | |||
} else { | |||
return; | |||
} | |||
} | |||
String[] dirs = extdirs.list(); | |||
for (int i=0; i<dirs.length; i++) { | |||
if (!dirs[i].endsWith(File.separator)) { | |||
dirs[i] += File.separator; | |||
} | |||
File dir = project.resolveFile(dirs[i]); | |||
FileSet fs = new FileSet(); | |||
fs.setDir(dir); | |||
fs.setIncludes("*"); | |||
classpath.addFileset(fs); | |||
} | |||
} | |||
/* | |||
* | |||
* @return true if the compile succeeded | |||
*/ | |||
private boolean doJvcCompile() throws BuildException { | |||
log("Using jvc compiler", Project.MSG_VERBOSE); | |||
Path classpath = new Path(project); | |||
// jvc doesn't support bootclasspath dir (-bootclasspath) | |||
// so we'll emulate it for compatibility and convenience. | |||
if (bootclasspath != null) { | |||
classpath.append(bootclasspath); | |||
} | |||
// jvc doesn't support an extension dir (-extdir) | |||
// so we'll emulate it for compatibility and convenience. | |||
addExtdirsToClasspath(classpath); | |||
classpath.append(getCompileClasspath(true)); | |||
// jvc has no option for source-path so we | |||
// will add it to classpath. | |||
classpath.append(src); | |||
Commandline cmd = new Commandline(); | |||
cmd.setExecutable("jvc"); | |||
if (destDir != null) { | |||
cmd.createArgument().setValue("/d"); | |||
cmd.createArgument().setFile(destDir); | |||
} | |||
// Add the Classpath before the "internal" one. | |||
cmd.createArgument().setValue("/cp:p"); | |||
cmd.createArgument().setPath(classpath); | |||
// Enable MS-Extensions and ... | |||
cmd.createArgument().setValue("/x-"); | |||
// ... do not display a Message about this. | |||
cmd.createArgument().setValue("/nomessage"); | |||
// Do not display Logo | |||
cmd.createArgument().setValue("/nologo"); | |||
if (debug) { | |||
cmd.createArgument().setValue("/g"); | |||
} | |||
if (optimize) { | |||
cmd.createArgument().setValue("/O"); | |||
} | |||
int firstFileName = cmd.size(); | |||
logAndAddFilesToCompile(cmd); | |||
return executeExternalCompile(cmd.getCommandline(), firstFileName) == 0; | |||
} | |||
} | |||
@@ -0,0 +1,86 @@ | |||
/* | |||
* The Apache Software License, Version 1.1 | |||
* | |||
* Copyright (c) 2001 The Apache Software Foundation. All rights | |||
* reserved. | |||
* | |||
* Redistribution and use in source and binary forms, with or without | |||
* modification, are permitted provided that the following conditions | |||
* are met: | |||
* | |||
* 1. Redistributions of source code must retain the above copyright | |||
* notice, this list of conditions and the following disclaimer. | |||
* | |||
* 2. Redistributions in binary form must reproduce the above copyright | |||
* notice, this list of conditions and the following disclaimer in | |||
* the documentation and/or other materials provided with the | |||
* distribution. | |||
* | |||
* 3. The end-user documentation included with the redistribution, if | |||
* any, must include the following acknowlegement: | |||
* "This product includes software developed by the | |||
* Apache Software Foundation (http://www.apache.org/)." | |||
* Alternately, this acknowlegement may appear in the software itself, | |||
* if and wherever such third-party acknowlegements normally appear. | |||
* | |||
* 4. The names "The Jakarta Project", "Ant", and "Apache Software | |||
* Foundation" must not be used to endorse or promote products derived | |||
* from this software without prior written permission. For written | |||
* permission, please contact apache@apache.org. | |||
* | |||
* 5. Products derived from this software may not be called "Apache" | |||
* nor may "Apache" appear in their names without prior written | |||
* permission of the Apache Group. | |||
* | |||
* THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED | |||
* WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES | |||
* OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE | |||
* DISCLAIMED. IN NO EVENT SHALL THE APACHE SOFTWARE FOUNDATION OR | |||
* ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, | |||
* SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT | |||
* LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF | |||
* USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND | |||
* ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, | |||
* OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT | |||
* OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF | |||
* SUCH DAMAGE. | |||
* ==================================================================== | |||
* | |||
* This software consists of voluntary contributions made by many | |||
* individuals on behalf of the Apache Software Foundation. For more | |||
* information on the Apache Software Foundation, please see | |||
* <http://www.apache.org/>. | |||
*/ | |||
package org.apache.tools.ant.taskdefs.compilers; | |||
import org.apache.tools.ant.BuildException; | |||
import org.apache.tools.ant.taskdefs.Javac; | |||
/** | |||
* The interface that all compiler adapters must adher to. | |||
* | |||
* <p>A compiler adapter is an adapter that interprets the javac's | |||
* parameters in preperation to be passed off to the compier this | |||
* adapter represents. As all the necessary values are stored in the | |||
* Javac task itself, the only thing all adapters need is the javac | |||
* task, the execute command and a parameterless constructor (for | |||
* reflection).</p> | |||
* | |||
* @author Jay Dickon Glanville <a href="mailto:jayglanville@home.com">jayglanville@home.com</a> | |||
*/ | |||
public interface CompilerAdapter { | |||
/** | |||
* Sets the compiler attributes, which are stored in the Javac task. | |||
*/ | |||
public void setJavac( Javac attributes ); | |||
/** | |||
* Executes the task. | |||
* | |||
* @return has the compilation been successful | |||
*/ | |||
public boolean execute() throws BuildException; | |||
} |
@@ -0,0 +1,151 @@ | |||
/* | |||
* The Apache Software License, Version 1.1 | |||
* | |||
* Copyright (c) 2001 The Apache Software Foundation. All rights | |||
* reserved. | |||
* | |||
* Redistribution and use in source and binary forms, with or without | |||
* modification, are permitted provided that the following conditions | |||
* are met: | |||
* | |||
* 1. Redistributions of source code must retain the above copyright | |||
* notice, this list of conditions and the following disclaimer. | |||
* | |||
* 2. Redistributions in binary form must reproduce the above copyright | |||
* notice, this list of conditions and the following disclaimer in | |||
* the documentation and/or other materials provided with the | |||
* distribution. | |||
* | |||
* 3. The end-user documentation included with the redistribution, if | |||
* any, must include the following acknowlegement: | |||
* "This product includes software developed by the | |||
* Apache Software Foundation (http://www.apache.org/)." | |||
* Alternately, this acknowlegement may appear in the software itself, | |||
* if and wherever such third-party acknowlegements normally appear. | |||
* | |||
* 4. The names "The Jakarta Project", "Ant", and "Apache Software | |||
* Foundation" must not be used to endorse or promote products derived | |||
* from this software without prior written permission. For written | |||
* permission, please contact apache@apache.org. | |||
* | |||
* 5. Products derived from this software may not be called "Apache" | |||
* nor may "Apache" appear in their names without prior written | |||
* permission of the Apache Group. | |||
* | |||
* THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED | |||
* WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES | |||
* OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE | |||
* DISCLAIMED. IN NO EVENT SHALL THE APACHE SOFTWARE FOUNDATION OR | |||
* ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, | |||
* SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT | |||
* LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF | |||
* USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND | |||
* ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, | |||
* OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT | |||
* OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF | |||
* SUCH DAMAGE. | |||
* ==================================================================== | |||
* | |||
* This software consists of voluntary contributions made by many | |||
* individuals on behalf of the Apache Software Foundation. For more | |||
* information on the Apache Software Foundation, please see | |||
* <http://www.apache.org/>. | |||
*/ | |||
package org.apache.tools.ant.taskdefs.compilers; | |||
import org.apache.tools.ant.BuildException; | |||
import org.apache.tools.ant.Task; | |||
import org.apache.tools.ant.Project; | |||
/** | |||
* Creates the necessary compiler adapter, given basic criteria. | |||
* | |||
* @author <a href="mailto:jayglanville@home.com">J D Glanville</a> | |||
*/ | |||
public class CompilerAdapterFactory { | |||
/** This is a singlton -- can't create instances!! */ | |||
private CompilerAdapterFactory() { | |||
} | |||
/** | |||
* Based on the parameter passed in, this method creates the necessary | |||
* factory desired. | |||
* | |||
* The current mapping for compiler names are as follows: | |||
* <ul><li>jikes = jikes compiler | |||
* <li>classic, javac1.1, javac1.2 = the standard compiler from JDK | |||
* 1.1/1.2 | |||
* <li>modern, javac1.3 = the new compiler of JDK 1.3 | |||
* <li>jvc, microsoft = the command line compiler from Microsoft's SDK | |||
* for Java / Visual J++ | |||
* <li><i>a fully quallified classname</i> = the name of a compiler | |||
* adapter | |||
* </ul> | |||
* | |||
* @param compilerType either the name of the desired compiler, or the | |||
* full classname of the compiler's adapter. | |||
* @param task a task to log through. | |||
* @throws BuildException if the compiler type could not be resolved into | |||
* a compiler adapter. | |||
*/ | |||
public static CompilerAdapter getCompiler( String compilerType, Task task ) | |||
throws BuildException { | |||
/* If I've done things right, this should be the extent of the | |||
* conditional statements required. | |||
*/ | |||
if ( compilerType.equalsIgnoreCase("jikes") ) { | |||
return new Jikes(); | |||
} | |||
if ( compilerType.equalsIgnoreCase("classic") || | |||
compilerType.equalsIgnoreCase("javac1.1") || | |||
compilerType.equalsIgnoreCase("javac1.2")) { | |||
return new Javac12(); | |||
} | |||
if ( compilerType.equalsIgnoreCase("modern") || | |||
compilerType.equalsIgnoreCase("javac1.3")) { | |||
// does the modern compiler exist? | |||
try { | |||
Class.forName("com.sun.tools.javac.Main"); | |||
} catch (ClassNotFoundException cnfe) { | |||
task.log("Modern compiler is not available - using " | |||
+ "classic compiler", Project.MSG_WARN); | |||
return new Javac12(); | |||
} | |||
return new Javac13(); | |||
} | |||
if ( compilerType.equalsIgnoreCase("jvc") || | |||
compilerType.equalsIgnoreCase("microsoft")) { | |||
return new Jvc(); | |||
} | |||
return resolveClassName( compilerType ); | |||
} | |||
/** | |||
* Tries to resolve the given classname into a compiler adapter. | |||
* Throws a fit if it can't. | |||
* | |||
* @param className The fully qualified classname to be created. | |||
* @throws BuildException This is the fit that is thrown if className | |||
* isn't an instance of CompilerAdapter. | |||
*/ | |||
private static CompilerAdapter resolveClassName( String className ) | |||
throws BuildException { | |||
try { | |||
Class c = Class.forName( className ); | |||
Object o = c.newInstance(); | |||
return (CompilerAdapter) o; | |||
} catch ( ClassNotFoundException cnfe ) { | |||
throw new BuildException( className + " can\'t be found.", cnfe ); | |||
} catch ( ClassCastException cce ) { | |||
throw new BuildException(className + " isn\'t the classname of " | |||
+ "a compiler adapter.", cce); | |||
} catch ( Throwable t ) { | |||
// for all other possibilities | |||
throw new BuildException(className + " caused an interesting " | |||
+ "exception.", t); | |||
} | |||
} | |||
} |
@@ -0,0 +1,373 @@ | |||
/* | |||
* The Apache Software License, Version 1.1 | |||
* | |||
* Copyright (c) 2001 The Apache Software Foundation. All rights | |||
* reserved. | |||
* | |||
* Redistribution and use in source and binary forms, with or without | |||
* modification, are permitted provided that the following conditions | |||
* are met: | |||
* | |||
* 1. Redistributions of source code must retain the above copyright | |||
* notice, this list of conditions and the following disclaimer. | |||
* | |||
* 2. Redistributions in binary form must reproduce the above copyright | |||
* notice, this list of conditions and the following disclaimer in | |||
* the documentation and/or other materials provided with the | |||
* distribution. | |||
* | |||
* 3. The end-user documentation included with the redistribution, if | |||
* any, must include the following acknowlegement: | |||
* "This product includes software developed by the | |||
* Apache Software Foundation (http://www.apache.org/)." | |||
* Alternately, this acknowlegement may appear in the software itself, | |||
* if and wherever such third-party acknowlegements normally appear. | |||
* | |||
* 4. The names "The Jakarta Project", "Ant", and "Apache Software | |||
* Foundation" must not be used to endorse or promote products derived | |||
* from this software without prior written permission. For written | |||
* permission, please contact apache@apache.org. | |||
* | |||
* 5. Products derived from this software may not be called "Apache" | |||
* nor may "Apache" appear in their names without prior written | |||
* permission of the Apache Group. | |||
* | |||
* THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED | |||
* WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES | |||
* OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE | |||
* DISCLAIMED. IN NO EVENT SHALL THE APACHE SOFTWARE FOUNDATION OR | |||
* ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, | |||
* SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT | |||
* LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF | |||
* USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND | |||
* ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, | |||
* OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT | |||
* OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF | |||
* SUCH DAMAGE. | |||
* ==================================================================== | |||
* | |||
* This software consists of voluntary contributions made by many | |||
* individuals on behalf of the Apache Software Foundation. For more | |||
* information on the Apache Software Foundation, please see | |||
* <http://www.apache.org/>. | |||
*/ | |||
package org.apache.tools.ant.taskdefs.compilers; | |||
import org.apache.tools.ant.*; | |||
import org.apache.tools.ant.taskdefs.*; | |||
import org.apache.tools.ant.types.*; | |||
import java.io.*; | |||
import java.util.Random; | |||
/** | |||
* This is the default implementation for the CompilerAdapter interface. | |||
* Currently, this is a cut-and-paste of the original javac task. | |||
* | |||
* @author James Davidson <a href="mailto:duncan@x180.com">duncan@x180.com</a> | |||
* @author Robin Green <a href="mailto:greenrd@hotmail.com">greenrd@hotmail.com</a> | |||
* @author <a href="mailto:stefan.bodewig@epost.de">Stefan Bodewig</a> | |||
* @author <a href="mailto:jayglanville@home.com">J D Glanville</a> | |||
*/ | |||
public abstract class DefaultCompilerAdapter implements CompilerAdapter { | |||
/* jdg - TODO - all these attributes are currently protected, but they | |||
* should probably be private in the near future. | |||
*/ | |||
protected Path src; | |||
protected File destDir; | |||
protected String encoding; | |||
protected boolean debug = false; | |||
protected boolean optimize = false; | |||
protected boolean deprecation = false; | |||
protected boolean depend = false; | |||
protected boolean verbose = false; | |||
protected String target; | |||
protected Path bootclasspath; | |||
protected Path extdirs; | |||
protected Path compileClasspath; | |||
protected Project project; | |||
protected Location location; | |||
protected boolean includeAntRuntime; | |||
protected boolean includeJavaRuntime; | |||
protected File[] compileList; | |||
protected static String lSep = System.getProperty("line.separator"); | |||
protected Javac attributes; | |||
public void setJavac( Javac attributes ) { | |||
this.attributes = attributes; | |||
src = attributes.getSrcdir(); | |||
destDir = attributes.getDestdir(); | |||
encoding = attributes.getEncoding(); | |||
debug = attributes.getDebug(); | |||
optimize = attributes.getOptimize(); | |||
deprecation = attributes.getDeprecation(); | |||
depend = attributes.getDepend(); | |||
verbose = attributes.getVerbose(); | |||
target = attributes.getTarget(); | |||
bootclasspath = attributes.getBootclasspath(); | |||
extdirs = attributes.getExtdirs(); | |||
compileList = attributes.getFileList(); | |||
compileClasspath = attributes.getClasspath(); | |||
project = attributes.getProject(); | |||
location = attributes.getLocation(); | |||
includeAntRuntime = attributes.getIncludeantruntime(); | |||
includeJavaRuntime = attributes.getIncludejavaruntime(); | |||
} | |||
public Javac getJavac() { | |||
return attributes; | |||
} | |||
/** | |||
* Builds the compilation classpath. | |||
* | |||
*/ | |||
protected Path getCompileClasspath() { | |||
Path classpath = new Path(project); | |||
// add dest dir to classpath so that previously compiled and | |||
// untouched classes are on classpath | |||
if (destDir != null) { | |||
classpath.setLocation(destDir); | |||
} | |||
// Combine the build classpath with the system classpath, in an | |||
// order determined by the value of build.classpath | |||
if (compileClasspath == null) { | |||
if ( includeAntRuntime ) { | |||
classpath.addExisting(Path.systemClasspath); | |||
} | |||
} else { | |||
if ( includeAntRuntime ) { | |||
classpath.addExisting(compileClasspath.concatSystemClasspath("last")); | |||
} else { | |||
classpath.addExisting(compileClasspath.concatSystemClasspath("ignore")); | |||
} | |||
} | |||
if (includeJavaRuntime) { | |||
if (System.getProperty("java.vendor").toLowerCase().indexOf("microsoft") >= 0) { | |||
// Pull in *.zip from packages directory | |||
FileSet msZipFiles = new FileSet(); | |||
msZipFiles.setDir(new File(System.getProperty("java.home") + File.separator + "Packages")); | |||
msZipFiles.setIncludes("*.ZIP"); | |||
classpath.addFileset(msZipFiles); | |||
} | |||
else if (Project.getJavaVersion() == Project.JAVA_1_1) { | |||
classpath.addExisting(new Path(null, | |||
System.getProperty("java.home") | |||
+ File.separator + "lib" | |||
+ File.separator | |||
+ "classes.zip")); | |||
} else { | |||
// JDK > 1.1 seems to set java.home to the JRE directory. | |||
classpath.addExisting(new Path(null, | |||
System.getProperty("java.home") | |||
+ File.separator + "lib" | |||
+ File.separator + "rt.jar")); | |||
// Just keep the old version as well and let addExistingToPath | |||
// sort it out. | |||
classpath.addExisting(new Path(null, | |||
System.getProperty("java.home") | |||
+ File.separator +"jre" | |||
+ File.separator + "lib" | |||
+ File.separator + "rt.jar")); | |||
} | |||
} | |||
return classpath; | |||
} | |||
/** | |||
* Does the command line argument processing common to classic and | |||
* modern. | |||
*/ | |||
protected Commandline setupJavacCommand() { | |||
Commandline cmd = new Commandline(); | |||
Path classpath = getCompileClasspath(); | |||
if (deprecation == true) { | |||
cmd.createArgument().setValue("-deprecation"); | |||
} | |||
if (destDir != null) { | |||
cmd.createArgument().setValue("-d"); | |||
cmd.createArgument().setFile(destDir); | |||
} | |||
cmd.createArgument().setValue("-classpath"); | |||
// Just add "sourcepath" to classpath ( for JDK1.1 ) | |||
if (Project.getJavaVersion().startsWith("1.1")) { | |||
cmd.createArgument().setValue(classpath.toString() | |||
+ File.pathSeparator | |||
+ src.toString()); | |||
} else { | |||
cmd.createArgument().setPath(classpath); | |||
cmd.createArgument().setValue("-sourcepath"); | |||
cmd.createArgument().setPath(src); | |||
if (target != null) { | |||
cmd.createArgument().setValue("-target"); | |||
cmd.createArgument().setValue(target); | |||
} | |||
} | |||
if (encoding != null) { | |||
cmd.createArgument().setValue("-encoding"); | |||
cmd.createArgument().setValue(encoding); | |||
} | |||
if (debug) { | |||
cmd.createArgument().setValue("-g"); | |||
} | |||
if (optimize) { | |||
cmd.createArgument().setValue("-O"); | |||
} | |||
if (bootclasspath != null) { | |||
cmd.createArgument().setValue("-bootclasspath"); | |||
cmd.createArgument().setPath(bootclasspath); | |||
} | |||
if (extdirs != null) { | |||
cmd.createArgument().setValue("-extdirs"); | |||
cmd.createArgument().setPath(extdirs); | |||
} | |||
if (depend) { | |||
if (Project.getJavaVersion().startsWith("1.1")) { | |||
cmd.createArgument().setValue("-depend"); | |||
} else if (Project.getJavaVersion().startsWith("1.2")) { | |||
cmd.createArgument().setValue("-Xdepend"); | |||
} else { | |||
attributes.log("depend attribute is not supported by the modern compiler", | |||
Project.MSG_WARN); | |||
} | |||
} | |||
if (verbose) { | |||
cmd.createArgument().setValue("-verbose"); | |||
} | |||
logAndAddFilesToCompile(cmd); | |||
return cmd; | |||
} | |||
/** | |||
* Logs the compilation parameters, adds the files to compile and logs the | |||
* &qout;niceSourceList" | |||
*/ | |||
protected void logAndAddFilesToCompile(Commandline cmd) { | |||
attributes.log("Compilation args: " + cmd.toString(), | |||
Project.MSG_VERBOSE); | |||
StringBuffer niceSourceList = new StringBuffer("File"); | |||
if (compileList.length != 1) { | |||
niceSourceList.append("s"); | |||
} | |||
niceSourceList.append(" to be compiled:"); | |||
niceSourceList.append(lSep); | |||
for (int i=0; i < compileList.length; i++) { | |||
String arg = compileList[i].getAbsolutePath(); | |||
cmd.createArgument().setValue(arg); | |||
niceSourceList.append(" " + arg + lSep); | |||
} | |||
attributes.log(niceSourceList.toString(), Project.MSG_VERBOSE); | |||
} | |||
/** | |||
* Do the compile with the specified arguments. | |||
* @param args - arguments to pass to process on command line | |||
* @param firstFileName - index of the first source file in args | |||
*/ | |||
protected int executeExternalCompile(String[] args, int firstFileName) { | |||
String[] commandArray = null; | |||
File tmpFile = null; | |||
try { | |||
/* | |||
* Many system have been reported to get into trouble with | |||
* long command lines - no, not only Windows ;-). | |||
* | |||
* POSIX seems to define a lower limit of 4k, so use a temporary | |||
* file if the total length of the command line exceeds this limit. | |||
*/ | |||
if (Commandline.toString(args).length() > 4096) { | |||
PrintWriter out = null; | |||
try { | |||
tmpFile = new File("jikes"+(new Random(System.currentTimeMillis())).nextLong()); | |||
out = new PrintWriter(new FileWriter(tmpFile)); | |||
for (int i = firstFileName; i < args.length; i++) { | |||
out.println(args[i]); | |||
} | |||
out.flush(); | |||
commandArray = new String[firstFileName+1]; | |||
System.arraycopy(args, 0, commandArray, 0, firstFileName); | |||
commandArray[firstFileName] = "@" + tmpFile.getAbsolutePath(); | |||
} catch (IOException e) { | |||
throw new BuildException("Error creating temporary file", e, location); | |||
} finally { | |||
if (out != null) { | |||
try {out.close();} catch (Throwable t) {} | |||
} | |||
} | |||
} else { | |||
commandArray = args; | |||
} | |||
try { | |||
Execute exe = new Execute(new LogStreamHandler(attributes, | |||
Project.MSG_INFO, | |||
Project.MSG_WARN)); | |||
exe.setAntRun(project); | |||
exe.setWorkingDirectory(project.getBaseDir()); | |||
exe.setCommandline(commandArray); | |||
exe.execute(); | |||
return exe.getExitValue(); | |||
} catch (IOException e) { | |||
throw new BuildException("Error running " + args[0] | |||
+ " compiler", e, location); | |||
} | |||
} finally { | |||
if (tmpFile != null) { | |||
tmpFile.delete(); | |||
} | |||
} | |||
} | |||
/** | |||
* Emulation of extdirs feature in java >= 1.2. | |||
* This method adds all files in the given | |||
* directories (but not in sub-directories!) to the classpath, | |||
* so that you don't have to specify them all one by one. | |||
* @param classpath - Path to append files to | |||
*/ | |||
protected void addExtdirsToClasspath(Path classpath) { | |||
if (extdirs == null) { | |||
String extProp = System.getProperty("java.ext.dirs"); | |||
if (extProp != null) { | |||
extdirs = new Path(project, extProp); | |||
} else { | |||
return; | |||
} | |||
} | |||
String[] dirs = extdirs.list(); | |||
for (int i=0; i<dirs.length; i++) { | |||
if (!dirs[i].endsWith(File.separator)) { | |||
dirs[i] += File.separator; | |||
} | |||
File dir = project.resolveFile(dirs[i]); | |||
FileSet fs = new FileSet(); | |||
fs.setDir(dir); | |||
fs.setIncludes("*"); | |||
classpath.addFileset(fs); | |||
} | |||
} | |||
} | |||
@@ -0,0 +1,108 @@ | |||
/* | |||
* The Apache Software License, Version 1.1 | |||
* | |||
* Copyright (c) 2001 The Apache Software Foundation. All rights | |||
* reserved. | |||
* | |||
* Redistribution and use in source and binary forms, with or without | |||
* modification, are permitted provided that the following conditions | |||
* are met: | |||
* | |||
* 1. Redistributions of source code must retain the above copyright | |||
* notice, this list of conditions and the following disclaimer. | |||
* | |||
* 2. Redistributions in binary form must reproduce the above copyright | |||
* notice, this list of conditions and the following disclaimer in | |||
* the documentation and/or other materials provided with the | |||
* distribution. | |||
* | |||
* 3. The end-user documentation included with the redistribution, if | |||
* any, must include the following acknowlegement: | |||
* "This product includes software developed by the | |||
* Apache Software Foundation (http://www.apache.org/)." | |||
* Alternately, this acknowlegement may appear in the software itself, | |||
* if and wherever such third-party acknowlegements normally appear. | |||
* | |||
* 4. The names "The Jakarta Project", "Ant", and "Apache Software | |||
* Foundation" must not be used to endorse or promote products derived | |||
* from this software without prior written permission. For written | |||
* permission, please contact apache@apache.org. | |||
* | |||
* 5. Products derived from this software may not be called "Apache" | |||
* nor may "Apache" appear in their names without prior written | |||
* permission of the Apache Group. | |||
* | |||
* THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED | |||
* WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES | |||
* OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE | |||
* DISCLAIMED. IN NO EVENT SHALL THE APACHE SOFTWARE FOUNDATION OR | |||
* ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, | |||
* SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT | |||
* LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF | |||
* USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND | |||
* ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, | |||
* OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT | |||
* OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF | |||
* SUCH DAMAGE. | |||
* ==================================================================== | |||
* | |||
* This software consists of voluntary contributions made by many | |||
* individuals on behalf of the Apache Software Foundation. For more | |||
* information on the Apache Software Foundation, please see | |||
* <http://www.apache.org/>. | |||
*/ | |||
package org.apache.tools.ant.taskdefs.compilers; | |||
import org.apache.tools.ant.BuildException; | |||
import org.apache.tools.ant.Project; | |||
import org.apache.tools.ant.taskdefs.LogOutputStream; | |||
import org.apache.tools.ant.types.Commandline; | |||
import java.io.*; | |||
import java.lang.reflect.Constructor; | |||
import java.lang.reflect.Method; | |||
/** | |||
* The implementation of the javac compiler for JDK 1.2 | |||
* This is primarily a cut-and-paste from the original javac task before it | |||
* was refactored. | |||
* | |||
* @author James Davidson <a href="mailto:duncan@x180.com">duncan@x180.com</a> | |||
* @author Robin Green <a href="mailto:greenrd@hotmail.com">greenrd@hotmail.com</a> | |||
* @author <a href="mailto:stefan.bodewig@epost.de">Stefan Bodewig</a> | |||
* @author <a href="mailto:jayglanville@home.com">J D Glanville</a> | |||
*/ | |||
public class Javac12 extends DefaultCompilerAdapter { | |||
public boolean execute() throws BuildException { | |||
attributes.log("Using classic compiler", Project.MSG_VERBOSE); | |||
Commandline cmd = setupJavacCommand(); | |||
try { | |||
// Create an instance of the compiler, redirecting output to | |||
// the project log | |||
OutputStream logstr = new LogOutputStream(attributes, Project.MSG_WARN); | |||
Class c = Class.forName("sun.tools.javac.Main"); | |||
Constructor cons = c.getConstructor(new Class[] { OutputStream.class, String.class }); | |||
Object compiler = cons.newInstance(new Object[] { logstr, "javac" }); | |||
// Call the compile() method | |||
Method compile = c.getMethod("compile", new Class [] { String[].class }); | |||
Boolean ok = (Boolean)compile.invoke(compiler, new Object[] {cmd.getArguments()}); | |||
return ok.booleanValue(); | |||
} | |||
catch (ClassNotFoundException ex) { | |||
throw new BuildException("Cannot use classic compiler, as it is not available"+ | |||
" A common solution is to set the environment variable"+ | |||
" JAVA_HOME to your jdk directory.", location); | |||
} | |||
catch (Exception ex) { | |||
if (ex instanceof BuildException) { | |||
throw (BuildException) ex; | |||
} else { | |||
throw new BuildException("Error starting classic compiler: ", ex, location); | |||
} | |||
} | |||
} | |||
} |
@@ -0,0 +1,113 @@ | |||
/* | |||
* The Apache Software License, Version 1.1 | |||
* | |||
* Copyright (c) 2001 The Apache Software Foundation. All rights | |||
* reserved. | |||
* | |||
* Redistribution and use in source and binary forms, with or without | |||
* modification, are permitted provided that the following conditions | |||
* are met: | |||
* | |||
* 1. Redistributions of source code must retain the above copyright | |||
* notice, this list of conditions and the following disclaimer. | |||
* | |||
* 2. Redistributions in binary form must reproduce the above copyright | |||
* notice, this list of conditions and the following disclaimer in | |||
* the documentation and/or other materials provided with the | |||
* distribution. | |||
* | |||
* 3. The end-user documentation included with the redistribution, if | |||
* any, must include the following acknowlegement: | |||
* "This product includes software developed by the | |||
* Apache Software Foundation (http://www.apache.org/)." | |||
* Alternately, this acknowlegement may appear in the software itself, | |||
* if and wherever such third-party acknowlegements normally appear. | |||
* | |||
* 4. The names "The Jakarta Project", "Ant", and "Apache Software | |||
* Foundation" must not be used to endorse or promote products derived | |||
* from this software without prior written permission. For written | |||
* permission, please contact apache@apache.org. | |||
* | |||
* 5. Products derived from this software may not be called "Apache" | |||
* nor may "Apache" appear in their names without prior written | |||
* permission of the Apache Group. | |||
* | |||
* THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED | |||
* WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES | |||
* OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE | |||
* DISCLAIMED. IN NO EVENT SHALL THE APACHE SOFTWARE FOUNDATION OR | |||
* ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, | |||
* SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT | |||
* LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF | |||
* USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND | |||
* ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, | |||
* OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT | |||
* OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF | |||
* SUCH DAMAGE. | |||
* ==================================================================== | |||
* | |||
* This software consists of voluntary contributions made by many | |||
* individuals on behalf of the Apache Software Foundation. For more | |||
* information on the Apache Software Foundation, please see | |||
* <http://www.apache.org/>. | |||
*/ | |||
package org.apache.tools.ant.taskdefs.compilers; | |||
import org.apache.tools.ant.BuildException; | |||
import org.apache.tools.ant.Project; | |||
import org.apache.tools.ant.taskdefs.LogOutputStream; | |||
import org.apache.tools.ant.types.Commandline; | |||
import java.lang.reflect.Method; | |||
import java.io.*; | |||
/** | |||
* The implementation of the javac compiler for JDK 1.3 | |||
* This is primarily a cut-and-paste from the original javac task before it | |||
* was refactored. | |||
* | |||
* @author James Davidson <a href="mailto:duncan@x180.com">duncan@x180.com</a> | |||
* @author Robin Green <a href="mailto:greenrd@hotmail.com">greenrd@hotmail.com</a> | |||
* @author <a href="mailto:stefan.bodewig@epost.de">Stefan Bodewig</a> | |||
* @author <a href="mailto:jayglanville@home.com">J D Glanville</a> | |||
*/ | |||
public class Javac13 extends DefaultCompilerAdapter { | |||
/** | |||
* Integer returned by the "Modern" jdk1.3 compiler to indicate success. | |||
*/ | |||
private static final int MODERN_COMPILER_SUCCESS = 0; | |||
public boolean execute() throws BuildException { | |||
attributes.log("Using modern compiler", Project.MSG_VERBOSE); | |||
Commandline cmd = setupJavacCommand(); | |||
PrintStream err = System.err; | |||
PrintStream out = System.out; | |||
// Use reflection to be able to build on all JDKs >= 1.1: | |||
try { | |||
PrintStream logstr = | |||
new PrintStream(new LogOutputStream(attributes, Project.MSG_WARN)); | |||
System.setOut(logstr); | |||
System.setErr(logstr); | |||
Class c = Class.forName ("com.sun.tools.javac.Main"); | |||
Object compiler = c.newInstance (); | |||
Method compile = c.getMethod ("compile", | |||
new Class [] {(new String [] {}).getClass ()}); | |||
int result = ((Integer) compile.invoke | |||
(compiler, new Object[] {cmd.getArguments()})) .intValue (); | |||
return (result == MODERN_COMPILER_SUCCESS); | |||
} catch (Exception ex) { | |||
if (ex instanceof BuildException) { | |||
throw (BuildException) ex; | |||
} else { | |||
throw new BuildException("Error starting modern compiler", ex, location); | |||
} | |||
} finally { | |||
System.setErr(err); | |||
System.setOut(out); | |||
} | |||
} | |||
} |
@@ -0,0 +1,205 @@ | |||
/* | |||
* The Apache Software License, Version 1.1 | |||
* | |||
* Copyright (c) 2001 The Apache Software Foundation. All rights | |||
* reserved. | |||
* | |||
* Redistribution and use in source and binary forms, with or without | |||
* modification, are permitted provided that the following conditions | |||
* are met: | |||
* | |||
* 1. Redistributions of source code must retain the above copyright | |||
* notice, this list of conditions and the following disclaimer. | |||
* | |||
* 2. Redistributions in binary form must reproduce the above copyright | |||
* notice, this list of conditions and the following disclaimer in | |||
* the documentation and/or other materials provided with the | |||
* distribution. | |||
* | |||
* 3. The end-user documentation included with the redistribution, if | |||
* any, must include the following acknowlegement: | |||
* "This product includes software developed by the | |||
* Apache Software Foundation (http://www.apache.org/)." | |||
* Alternately, this acknowlegement may appear in the software itself, | |||
* if and wherever such third-party acknowlegements normally appear. | |||
* | |||
* 4. The names "The Jakarta Project", "Ant", and "Apache Software | |||
* Foundation" must not be used to endorse or promote products derived | |||
* from this software without prior written permission. For written | |||
* permission, please contact apache@apache.org. | |||
* | |||
* 5. Products derived from this software may not be called "Apache" | |||
* nor may "Apache" appear in their names without prior written | |||
* permission of the Apache Group. | |||
* | |||
* THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED | |||
* WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES | |||
* OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE | |||
* DISCLAIMED. IN NO EVENT SHALL THE APACHE SOFTWARE FOUNDATION OR | |||
* ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, | |||
* SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT | |||
* LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF | |||
* USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND | |||
* ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, | |||
* OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT | |||
* OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF | |||
* SUCH DAMAGE. | |||
* ==================================================================== | |||
* | |||
* This software consists of voluntary contributions made by many | |||
* individuals on behalf of the Apache Software Foundation. For more | |||
* information on the Apache Software Foundation, please see | |||
* <http://www.apache.org/>. | |||
*/ | |||
package org.apache.tools.ant.taskdefs.compilers; | |||
import org.apache.tools.ant.BuildException; | |||
import org.apache.tools.ant.Project; | |||
import org.apache.tools.ant.types.*; | |||
/** | |||
* The implementation of the jikes compiler. | |||
* This is primarily a cut-and-paste from the original javac task before it | |||
* was refactored. | |||
* | |||
* @author James Davidson <a href="mailto:duncan@x180.com">duncan@x180.com</a> | |||
* @author Robin Green <a href="mailto:greenrd@hotmail.com">greenrd@hotmail.com</a> | |||
* @author <a href="mailto:stefan.bodewig@epost.de">Stefan Bodewig</a> | |||
* @author <a href="mailto:jayglanville@home.com">J D Glanville</a> | |||
*/ | |||
public class Jikes extends DefaultCompilerAdapter { | |||
/** | |||
* Performs a compile using the Jikes compiler from IBM.. | |||
* Mostly of this code is identical to doClassicCompile() | |||
* However, it does not support all options like | |||
* bootclasspath, extdirs, deprecation and so on, because | |||
* there is no option in jikes and I don't understand | |||
* what they should do. | |||
* | |||
* It has been successfully tested with jikes >1.10 | |||
* | |||
* @author skanthak@muehlheim.de | |||
*/ | |||
public boolean execute() throws BuildException { | |||
attributes.log("Using jikes compiler", Project.MSG_VERBOSE); | |||
Path classpath = new Path(project); | |||
// Jikes doesn't support bootclasspath dir (-bootclasspath) | |||
// so we'll emulate it for compatibility and convenience. | |||
if (bootclasspath != null) { | |||
classpath.append(bootclasspath); | |||
} | |||
// Jikes doesn't support an extension dir (-extdir) | |||
// so we'll emulate it for compatibility and convenience. | |||
addExtdirsToClasspath(classpath); | |||
if ( (bootclasspath == null) || (bootclasspath.size() == 0) ) { | |||
// no bootclasspath, therefore, get one from the java runtime | |||
includeJavaRuntime = true; | |||
} else { | |||
// there is a bootclasspath stated. By default, the | |||
// includeJavaRuntime is false. If the user has stated a | |||
// bootclasspath and said to include the java runtime, it's on | |||
// their head! | |||
} | |||
classpath.append(getCompileClasspath()); | |||
// Jikes has no option for source-path so we | |||
// will add it to classpath. | |||
classpath.append(src); | |||
// if the user has set JIKESPATH we should add the contents as well | |||
String jikesPath = System.getProperty("jikes.class.path"); | |||
if (jikesPath != null) { | |||
classpath.append(new Path(project, jikesPath)); | |||
} | |||
Commandline cmd = new Commandline(); | |||
cmd.setExecutable("jikes"); | |||
if (deprecation == true) | |||
cmd.createArgument().setValue("-deprecation"); | |||
if (destDir != null) { | |||
cmd.createArgument().setValue("-d"); | |||
cmd.createArgument().setFile(destDir); | |||
} | |||
cmd.createArgument().setValue("-classpath"); | |||
cmd.createArgument().setPath(classpath); | |||
if (encoding != null) { | |||
cmd.createArgument().setValue("-encoding"); | |||
cmd.createArgument().setValue(encoding); | |||
} | |||
if (debug) { | |||
cmd.createArgument().setValue("-g"); | |||
} | |||
if (optimize) { | |||
cmd.createArgument().setValue("-O"); | |||
} | |||
if (verbose) { | |||
cmd.createArgument().setValue("-verbose"); | |||
} | |||
if (depend) { | |||
cmd.createArgument().setValue("-depend"); | |||
} | |||
/** | |||
* XXX | |||
* Perhaps we shouldn't use properties for these | |||
* three options (emacs mode, warnings and pedantic), | |||
* but include it in the javac directive? | |||
*/ | |||
/** | |||
* Jikes has the nice feature to print error | |||
* messages in a form readable by emacs, so | |||
* that emacs can directly set the cursor | |||
* to the place, where the error occured. | |||
*/ | |||
String emacsProperty = project.getProperty("build.compiler.emacs"); | |||
if (emacsProperty != null && Project.toBoolean(emacsProperty)) { | |||
cmd.createArgument().setValue("+E"); | |||
} | |||
/** | |||
* Jikes issues more warnings that javac, for | |||
* example, when you have files in your classpath | |||
* that don't exist. As this is often the case, these | |||
* warning can be pretty annoying. | |||
*/ | |||
String warningsProperty = project.getProperty("build.compiler.warnings"); | |||
if (warningsProperty != null && !Project.toBoolean(warningsProperty)) { | |||
cmd.createArgument().setValue("-nowarn"); | |||
} | |||
/** | |||
* Jikes can issue pedantic warnings. | |||
*/ | |||
String pedanticProperty = project.getProperty("build.compiler.pedantic"); | |||
if (pedanticProperty != null && Project.toBoolean(pedanticProperty)) { | |||
cmd.createArgument().setValue("+P"); | |||
} | |||
/** | |||
* Jikes supports something it calls "full dependency | |||
* checking", see the jikes documentation for differences | |||
* between -depend and +F. | |||
*/ | |||
String fullDependProperty = project.getProperty("build.compiler.fulldepend"); | |||
if (fullDependProperty != null && Project.toBoolean(fullDependProperty)) { | |||
cmd.createArgument().setValue("+F"); | |||
} | |||
int firstFileName = cmd.size(); | |||
logAndAddFilesToCompile(cmd); | |||
return executeExternalCompile(cmd.getCommandline(), firstFileName) == 0; | |||
} | |||
} |
@@ -0,0 +1,134 @@ | |||
/* | |||
* The Apache Software License, Version 1.1 | |||
* | |||
* Copyright (c) 2001 The Apache Software Foundation. All rights | |||
* reserved. | |||
* | |||
* Redistribution and use in source and binary forms, with or without | |||
* modification, are permitted provided that the following conditions | |||
* are met: | |||
* | |||
* 1. Redistributions of source code must retain the above copyright | |||
* notice, this list of conditions and the following disclaimer. | |||
* | |||
* 2. Redistributions in binary form must reproduce the above copyright | |||
* notice, this list of conditions and the following disclaimer in | |||
* the documentation and/or other materials provided with the | |||
* distribution. | |||
* | |||
* 3. The end-user documentation included with the redistribution, if | |||
* any, must include the following acknowlegement: | |||
* "This product includes software developed by the | |||
* Apache Software Foundation (http://www.apache.org/)." | |||
* Alternately, this acknowlegement may appear in the software itself, | |||
* if and wherever such third-party acknowlegements normally appear. | |||
* | |||
* 4. The names "The Jakarta Project", "Ant", and "Apache Software | |||
* Foundation" must not be used to endorse or promote products derived | |||
* from this software without prior written permission. For written | |||
* permission, please contact apache@apache.org. | |||
* | |||
* 5. Products derived from this software may not be called "Apache" | |||
* nor may "Apache" appear in their names without prior written | |||
* permission of the Apache Group. | |||
* | |||
* THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED | |||
* WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES | |||
* OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE | |||
* DISCLAIMED. IN NO EVENT SHALL THE APACHE SOFTWARE FOUNDATION OR | |||
* ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, | |||
* SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT | |||
* LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF | |||
* USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND | |||
* ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, | |||
* OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT | |||
* OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF | |||
* SUCH DAMAGE. | |||
* ==================================================================== | |||
* | |||
* This software consists of voluntary contributions made by many | |||
* individuals on behalf of the Apache Software Foundation. For more | |||
* information on the Apache Software Foundation, please see | |||
* <http://www.apache.org/>. | |||
*/ | |||
package org.apache.tools.ant.taskdefs.compilers; | |||
import org.apache.tools.ant.BuildException; | |||
import org.apache.tools.ant.Project; | |||
import org.apache.tools.ant.types.*; | |||
/** | |||
* The implementation of the jvc compiler from microsoft. | |||
* This is primarily a cut-and-paste from the original javac task before it | |||
* was refactored. | |||
* | |||
* @author James Davidson <a href="mailto:duncan@x180.com">duncan@x180.com</a> | |||
* @author Robin Green <a href="mailto:greenrd@hotmail.com">greenrd@hotmail.com</a> | |||
* @author <a href="mailto:stefan.bodewig@epost.de">Stefan Bodewig</a> | |||
* @author <a href="mailto:jayglanville@home.com">J D Glanville</a> | |||
*/ | |||
public class Jvc extends DefaultCompilerAdapter { | |||
public boolean execute() throws BuildException { | |||
attributes.log("Using jvc compiler", Project.MSG_VERBOSE); | |||
Path classpath = new Path(project); | |||
// jvc doesn't support bootclasspath dir (-bootclasspath) | |||
// so we'll emulate it for compatibility and convenience. | |||
if (bootclasspath != null) { | |||
classpath.append(bootclasspath); | |||
} | |||
// jvc doesn't support an extension dir (-extdir) | |||
// so we'll emulate it for compatibility and convenience. | |||
addExtdirsToClasspath(classpath); | |||
if ( (bootclasspath == null) || (bootclasspath.size() == 0) ) { | |||
// no bootclasspath, therefore, get one from the java runtime | |||
includeJavaRuntime = true; | |||
} else { | |||
// there is a bootclasspath stated. By default, the | |||
// includeJavaRuntime is false. If the user has stated a | |||
// bootclasspath and said to include the java runtime, it's on | |||
// their head! | |||
} | |||
classpath.append(getCompileClasspath()); | |||
// jvc has no option for source-path so we | |||
// will add it to classpath. | |||
classpath.append(src); | |||
Commandline cmd = new Commandline(); | |||
cmd.setExecutable("jvc"); | |||
if (destDir != null) { | |||
cmd.createArgument().setValue("/d"); | |||
cmd.createArgument().setFile(destDir); | |||
} | |||
// Add the Classpath before the "internal" one. | |||
cmd.createArgument().setValue("/cp:p"); | |||
cmd.createArgument().setPath(classpath); | |||
// Enable MS-Extensions and ... | |||
cmd.createArgument().setValue("/x-"); | |||
// ... do not display a Message about this. | |||
cmd.createArgument().setValue("/nomessage"); | |||
// Do not display Logo | |||
cmd.createArgument().setValue("/nologo"); | |||
if (debug) { | |||
cmd.createArgument().setValue("/g"); | |||
} | |||
if (optimize) { | |||
cmd.createArgument().setValue("/O"); | |||
} | |||
int firstFileName = cmd.size(); | |||
logAndAddFilesToCompile(cmd); | |||
return executeExternalCompile(cmd.getCommandline(), firstFileName) == 0; | |||
} | |||
} |
@@ -467,15 +467,25 @@ public class Path extends DataType implements Cloneable { | |||
} | |||
/** | |||
* Concatenates the system class path in the order specified | |||
* by the ${build.sysclasspath} property. | |||
* Concatenates the system class path in the order specified by | |||
* the ${build.sysclasspath} property - using "last" as | |||
* default value. | |||
*/ | |||
public Path concatSystemClasspath() { | |||
return concatSystemClasspath("last"); | |||
} | |||
/** | |||
* Concatenates the system class path in the order specified by | |||
* the ${build.sysclasspath} property - using the supplied value | |||
* if ${build.sysclasspath} has not been set. | |||
*/ | |||
public Path concatSystemClasspath(String defValue) { | |||
Path result = new Path(project); | |||
String order = project.getProperty("build.sysclasspath"); | |||
if (order == null) order="last"; | |||
if (order == null) order=defValue; | |||
if (order.equals("only")) { | |||
// only: the developer knows what (s)he is doing | |||