FULL PRODUCT VERSION :
java version "1.6.0_20"
Java(TM) SE Runtime Environment (build 1.6.0_20-b02)
Java HotSpot(TM) Server VM (build 16.3-b01, mixed mode)
ADDITIONAL OS VERSION INFORMATION :
Linux thirtyseven 2.6.32-5-686-bigmem #1 SMP Tue Jun 1 05:38:08 UTC 2010 i686 GNU/Linux
A DESCRIPTION OF THE PROBLEM :
Consider a case in which three files exist in the source tree: foo/Main.java, foo/Test.java, and bar/Test.java . Suppose foo/Main.java contains an import statement "import bar.*". Suppose also that foo/Main.java contains a reference to a type named "Test".
If foo/Test.java contains a top-level class declaration named "Test", the reference in Main means the type contained in foo/Test.java (JLS v3 S6.5.5, S7.5.2). Specifically, the import statement, because it is on-demand, has no impact on that reference. This is correct behavior.
However, it is possible for Test.java to contain no top-level type declarations (S7.3). If no such top-level type declaration appears and bar/Test.java contains a top-level type named "Test", the name "Test" refers to the type declared in bar/Test.java . In practice, however, compilation fails because the compiler expects to find a class foo.Test.
This bug was discovered while I was confirming my understanding of how the type namespace works in Java.
STEPS TO FOLLOW TO REPRODUCE THE PROBLEM :
Create a new source directory (termed $src henceforth) and create subdirectories $src/example and $src/example2. Create a file $src/example/Main.java containing the following code:
package example;
import example2.*;
public class Main
{
public static void main(String[] arg)
{
Test t = new Test();
System.out.println(t.getClass());
}
}
Create a file $src/example/Test.java containing the following code:
package example;
//public class Test {}
Create a file $src/example2/Test.java containing the following code:
package example2;
public class Test {}
Attempt to compile all three source files.
EXPECTED VERSUS ACTUAL BEHAVIOR :
EXPECTED -
The three source files should compile successfully. The output file example/Main.class should refer to the class contained in example2/Test.class.
ACTUAL -
Compilation fails; no binary output is produced.
ERROR MESSAGES/STACK TRACES THAT OCCUR :
./example/Main.java:9: cannot access example.Test
bad class file: ./example/Test.java
file does not contain class example.Test
Please remove or make sure it appears in the correct subdirectory of the classpath.
Test t = new Test();
^
1 error
REPRODUCIBILITY :
This bug can be reproduced always.
---------- BEGIN SOURCE ----------
Contents of example/Main.java:
package example;
import example2.*;
public class Main
{
public static void main(String[] arg)
{
Test t = new Test();
System.out.println(t.getClass());
}
}
Contents of example/Test.java:
package example;
//public class Test {}
Contents of example2/Test.java:
package example2;
public class Test {}
---------- END SOURCE ----------
CUSTOMER SUBMITTED WORKAROUND :
No workaround is currently available short of deleting or moving the offending source file (example/Test.java). This is a bug because the source file meets the requirements, both syntactic and semantic, of the Java Language Specification.
java version "1.6.0_20"
Java(TM) SE Runtime Environment (build 1.6.0_20-b02)
Java HotSpot(TM) Server VM (build 16.3-b01, mixed mode)
ADDITIONAL OS VERSION INFORMATION :
Linux thirtyseven 2.6.32-5-686-bigmem #1 SMP Tue Jun 1 05:38:08 UTC 2010 i686 GNU/Linux
A DESCRIPTION OF THE PROBLEM :
Consider a case in which three files exist in the source tree: foo/Main.java, foo/Test.java, and bar/Test.java . Suppose foo/Main.java contains an import statement "import bar.*". Suppose also that foo/Main.java contains a reference to a type named "Test".
If foo/Test.java contains a top-level class declaration named "Test", the reference in Main means the type contained in foo/Test.java (JLS v3 S6.5.5, S7.5.2). Specifically, the import statement, because it is on-demand, has no impact on that reference. This is correct behavior.
However, it is possible for Test.java to contain no top-level type declarations (S7.3). If no such top-level type declaration appears and bar/Test.java contains a top-level type named "Test", the name "Test" refers to the type declared in bar/Test.java . In practice, however, compilation fails because the compiler expects to find a class foo.Test.
This bug was discovered while I was confirming my understanding of how the type namespace works in Java.
STEPS TO FOLLOW TO REPRODUCE THE PROBLEM :
Create a new source directory (termed $src henceforth) and create subdirectories $src/example and $src/example2. Create a file $src/example/Main.java containing the following code:
package example;
import example2.*;
public class Main
{
public static void main(String[] arg)
{
Test t = new Test();
System.out.println(t.getClass());
}
}
Create a file $src/example/Test.java containing the following code:
package example;
//public class Test {}
Create a file $src/example2/Test.java containing the following code:
package example2;
public class Test {}
Attempt to compile all three source files.
EXPECTED VERSUS ACTUAL BEHAVIOR :
EXPECTED -
The three source files should compile successfully. The output file example/Main.class should refer to the class contained in example2/Test.class.
ACTUAL -
Compilation fails; no binary output is produced.
ERROR MESSAGES/STACK TRACES THAT OCCUR :
./example/Main.java:9: cannot access example.Test
bad class file: ./example/Test.java
file does not contain class example.Test
Please remove or make sure it appears in the correct subdirectory of the classpath.
Test t = new Test();
^
1 error
REPRODUCIBILITY :
This bug can be reproduced always.
---------- BEGIN SOURCE ----------
Contents of example/Main.java:
package example;
import example2.*;
public class Main
{
public static void main(String[] arg)
{
Test t = new Test();
System.out.println(t.getClass());
}
}
Contents of example/Test.java:
package example;
//public class Test {}
Contents of example2/Test.java:
package example2;
public class Test {}
---------- END SOURCE ----------
CUSTOMER SUBMITTED WORKAROUND :
No workaround is currently available short of deleting or moving the offending source file (example/Test.java). This is a bug because the source file meets the requirements, both syntactic and semantic, of the Java Language Specification.