Repeated calls to javax.tools....compile() with -d give unexpected results.

Example session:

C:\Java\sandbox>ls

JavaxTest.java JavaxTestInA.java JavaxTestInB.java

C:\Java\sandbox>head -n 999 *

==> JavaxTest.java <==

import java.util.List;

import java.util.ArrayList;

import java.io.File;

import java.io.PrintWriter;

import javax.tools.*;

class JavaxTest

{

publicstaticvoid main(String[] args)

{

JavaCompiler compiler = ToolProvider.getSystemJavaCompiler();

if (compiler ==null)

thrownew RuntimeException("No compiler");

StandardJavaFileManager fileManager =

compiler.getStandardFileManager(null, null,null);

{

Iterable<?extends JavaFileObject> compilationUnits =

fileManager.getJavaFileObjects(

new File[]{new File("JavaxTestInA.java")} );

List<String> options =new ArrayList<String>();

options.add("-d");

options.add("foo");

System.out.println(compiler.getTask(new PrintWriter(System.out), fileManager, null, options, null, compilationUnits).call());

}

{

Iterable<?extends JavaFileObject> compilationUnits =

fileManager.getJavaFileObjects(

new File[]{new File("JavaxTestInB.java")} );

List<String> options =new ArrayList<String>();

options.add("-d");

options.add("bar");

System.out.println(compiler.getTask(new PrintWriter(System.out), fileManager, null, options, null, compilationUnits).call());

}

}

}

==> JavaxTestInA.java <==

package something.stupid;

publicclass JavaxTestInA{}

==> JavaxTestInB.java <==

package something.notstupid;

publicclass JavaxTestInB{}

C:\Java\sandbox>javac JavaxTest.java & java JavaxTest

true

true

C:\Java\sandbox>ls -R

.:

foo JavaxTest.class JavaxTest.java JavaxTestInA.java JavaxTestInB.java

./foo:

something

./foo/something:

notstupid stupid

./foo/something/notstupid:

JavaxTestInB.class

./foo/something/stupid:

JavaxTestInA.class

C:\Java\sandbox>

The above session was run on WinXP SP2 32 with:

>java -version

java version"1.6.0-rc"

Java(TM) SE Runtime Environment (build 1.6.0-rc-b95)

Java HotSpot(TM) Client VM (build 1.6.0-rc-b95, mixed mode)

.

This issue also occours (on the same machine) with:

>java -version

java version"1.6.0-rc"

Java(TM) SE Runtime Environment (build 1.6.0-rc-b104)

Java HotSpot(TM) Client VM (build 1.6.0-rc-b104, mixed mode, sharing)

Under b104, however, it requires the directories "foo"and "bar" to be present before the testcase is executed.

The unexpected behaviour/results here is that, despite the second invocation of a task being given someoptions with "-d bar", it outputs to foo, even after checking bar exists.

Recreating the compiler in-between calls functions as expected (ie. ./bar/something/notstupid/JavaxTestInB.class exists).

import java.util.List;

import java.util.ArrayList;

import java.io.File;

import java.io.PrintWriter;

import javax.tools.*;

class JavaxTest

{

publicstaticvoid main(String[] args)

{

{

JavaCompiler compiler = ToolProvider.getSystemJavaCompiler();

if (compiler ==null)

thrownew RuntimeException("No compiler");

StandardJavaFileManager fileManager =

compiler.getStandardFileManager(null, null,null);

Iterable<?extends JavaFileObject> compilationUnits =

fileManager.getJavaFileObjects(

new File[]{new File("JavaxTestInA.java")} );

List<String> options =new ArrayList<String>();

options.add("-d");

options.add("foo");

System.out.println(compiler.getTask(new PrintWriter(System.out), fileManager, null, options, null, compilationUnits).call());

}

{

JavaCompiler compiler = ToolProvider.getSystemJavaCompiler();

if (compiler ==null)

thrownew RuntimeException("No compiler");

StandardJavaFileManager fileManager =

compiler.getStandardFileManager(null, null,null);

Iterable<?extends JavaFileObject> compilationUnits =

fileManager.getJavaFileObjects(

new File[]{new File("JavaxTestInB.java")} );

List<String> options =new ArrayList<String>();

options.add("-d");

options.add("bar");

System.out.println(compiler.getTask(new PrintWriter(System.out), fileManager, null, options, null, compilationUnits).call());

}

}

}

Apologies for both the code-duplication in the above test-cases (I felt the code was clearer this way) and if this is the wrong forum to post in.

In summary, my question is: Is this the intended behaviour, and, if so, is there a work-around that doesn't involve (assumably costly) tear-down and rebuilding the compiler?

Thanks.

[8217 byte] By [Fauxa] at [2007-10-3 11:27:04]
# 1

Duplicated on Debian Unstable with b104:

faux@debunstvm:~/sandbox$ javac -version

javac 1.6.0-rc

faux@debunstvm:~/sandbox$ java -version

java version "1.6.0-rc"

Java(TM) SE Runtime Environment (build 1.6.0-rc-b104)

Java HotSpot(TM) Client VM (build 1.6.0-rc-b104, mixed mode, sharing)

faux@debunstvm:~/sandbox$ uname -a

Linux debunstvm 2.6.18-2-686 #1 SMP Wed Nov 8 19:52:12 UTC 2006 i686 GNU/Linux

Fauxa at 2007-7-15 13:53:04 > top of Java-index,Developer Tools,Java Compiler...
# 2

Insisting that the directories are created is the intended behavior

and matches that of JDK 5.0.

You can use StandardJavaFileManager.setLocation if you wish to

change any locations after a file manager has been used. The

options like "-d foo" are only used as defaults to initialize the

locations lazily. See also StandardLocation.

Here is a trick for more conveniently obtaining a list of file objects:

compilationUnits = fileManager.getJavaFileObjects("JavaxTestInA.java");

Also check out the draft version of the Java Compiler API guide:

https://openjdk.dev.java.net/nonav/compiler/guide/compilerAPI.html

PeterAhea at 2007-7-15 13:53:04 > top of Java-index,Developer Tools,Java Compiler...
# 3
I know the guide isn't much yet. I have gotten a bit further with the examples than with the prose:https://openjdk.dev.java.net/source/browse/openjdk/trunk/www/compiler/staging-area/guides/examples/
PeterAhea at 2007-7-15 13:53:04 > top of Java-index,Developer Tools,Java Compiler...