-
Bug
-
Resolution: Not an Issue
-
P4
-
None
-
1.4.0
-
generic
-
generic
Name: vsR10008 Date: 07/27/2000
JVM rejects a class which implements the same interface twice.
Howevere we can't find in JVMS (Second Edition) that this is prohibited.
We are not sure if this is a bug in implementation or an omission in the spec.
Something should be fixed.
Let's consider the following example:
interface A {...}
interface A1 extends A {}
interface A2 extends A {}
class B implements A1,A2 {...}
class C implements A,A {...}
Class B and C are semantically equal; so
JVM should accept both B and C or reject them both.
Meanwhile JVM accepts "B" but rejects "C".
Note, that JLS explicitly prohibits such usage of interfaces
(JLS, 2nd edition, "8.1.4 Superinterfaces"):
A compile-time error occurs if the same interface is mentioned two or
more times in a single "implements" clause.
We cannot compile class C from the example above with usual Java compiler,
so we use jcod utility to make appropriate classfile.
The following sources demonstrate the bug:
--------------------------------------------------------------- D.java ---
interface A {
void m() {}
}
interface A1 extends A {}
interface A2 extends A {}
class B implements A1,A2 {
public void m() {}
}
// class C implements A,A {} -- see C.jcod
public class D {
public void m() {}
public static void main(String[] argv) {
String[] cn={"B","C"};
for(int i=0;i<cn.length;i++) {
try {
System.out.print("Loading class "+cn[i]+"...");
Class.forName(cn[i]);
System.out.println("Loaded!");
} catch (Throwable t) {
System.out.println("ERROR:"+t);
}
}
}
}
--------------------------------------------------------------- C.jcod ---
class C {
0xCAFEBABE;
3; // minor version
45; // version
[] { // Constant Pool
; // first element is empty
Method #3 #11; // #1
class #12; // #2
class #13; // #3
class #14; // #4
Utf8 "<init>"; // #5
Utf8 "()V"; // #6
Utf8 "Code"; // #7
Utf8 "LineNumberTable"; // #8
Utf8 "SourceFile"; // #9
Utf8 "D.java"; // #10
NameAndType #5 #6; // #11
Utf8 "C"; // #12
Utf8 "java/lang/Object"; // #13
Utf8 "A"; // #14
} // Constant Pool
0x0020; // access
#2;// this_cpx
#3;// super_cpx
[] { // Interfaces
// ... implements A,A
#4;
#4;
} // Interfaces
[] { // fields
} // fields
[] { // methods
{ // Member
0x0000; // access
#5; // name_cpx
#6; // sig_cpx
[] { // Attributes
Attr(#7) { // Code
1; // max_stack
1; // max_locals
Bytes[] {
0x2AB70001B1;
};
[] { // Traps
} // end Traps
[] { // Attributes
Attr(#8) { // LineNumberTable
[] { // LineNumberTable
0 5;
}
} // end LineNumberTable
} // Attributes
} // end Code
} // Attributes
} // Member
} // methods
[] { // Attributes
Attr(#9) { // SourceFile
#10;
} // end SourceFile
} // Attributes
} // end class C
--------------------------------------------------------------------------
Execution log:
> uname -a
SunOS novo12 5.7 Generic_Patch sun4u sparc SUNW,Ultra-2
> java -version
java version "1.4.0beta"
Java(TM) 2 Runtime Environment, Standard Edition (build 1.4.0beta-b25)
Java HotSpot(TM) Core VM (build 1.3-internal, interpreted mode)
> java -classic -version
java version "1.4.0beta"
Java(TM) 2 Runtime Environment, Standard Edition (build 1.4.0beta-b25)
Classic VM (build 1.4.0beta-b25, green threads, nojit)
> jcod C.jcod
> javac D.java
> java D
Loading class B...Loaded!
Loading class C...ERROR:java.lang.ClassFormatError: C (Repeative interface name)
> java -classic D
Loading class B...Loaded!
Loading class C...ERROR:java.lang.ClassFormatError: C (Repeative interface name)
This bug doesn't occur in JDK1.0, JDK1.0.1, JDK1.0.2
In JDK 1.1-1.1.2 JVM rejects class "C" throwing
"java.lang.IllegalAccessError: Unimplemented interface method".
In JDK 1.1.3-1.1.5 JVM rejects class "C" throwing
"java.lang.VerifyError: Bad interface index"
In JDK 1.1.6-1.1.8 JVM rejects class "C" throwing
java.lang.ClassFormatError: Bad interface index
In JDK 1.2-1.4 JVMs (both classic and HotSpot) reject class "C" throwing
java.lang.ClassFormatError: C (Repeative interface name)
======================================================================
In the above example, class B is legal and class C is not. The VM is doing the right thing.
###@###.### 2002-04-11