Uploaded image for project: 'JDK'
  1. JDK
  2. JDK-4274357

Regression: bad classfile due to synthetic/explicit name clash

XMLWordPrintable

    • generic
    • generic



      Name: inc88864 Date: 09/22/99



      Javac (build 1.3.0-G) does not prohibit use of names like 'val$argv' and
      'access$000'. Compiler uses such names for synthetic members, which it creates
      to provide inner class semantics. Section "How do inner classes work?" of
      Inner Class Specification reads :

      " It must be emphasized that these oddly-named "this$" and "val$" fields and
      extra constructor arguments are added by the compiler to the generated bytecodes,
      and cannot be directly referenced by Java source code. "

      After compiling of V.java (below) classfile V$1$Inn.class contains two fields
      'val$argv' of type "[Ljava/lang/String;", therefore ClassFormatError occurs
      while starting the V class (see trace below).

      After compiling of A.java (below) classfile A.class contains two methods
      'access$000' of signature "(LA;)I". First of them is non-static so
      IncompatibleClassChangeError occurs while starting the A class (see trace below).

      Note, that compiler does not allow use of name 'this$0', which also is name of synthetic
      member, that compiler add to inner class.
       
      Oldjavac and javacs in JDK 1.2.2, 1.2.1 compile the sources without errors.

      --------------------------------------=== trace
      % java V
      Exception in thread "main" java.lang.ClassFormatError: V$1$Inn (Repeative field name/signature)
      at java.lang.ClassLoader.defineClass0(Native Method)
      at java.lang.ClassLoader.defineClass(ClassLoader.java:453)
      ......
      % java A
      Exception in thread "main" java.lang.IncompatibleClassChangeError
      at A$A2.x(A.java:5)
      at A.main(A.java:11)
      %
      --------------------------------------=== V.java
      class V {
      // int this$0 = 15;
          interface I {
      String s();
          }
          static I iv;

          public static void main( final String argv[] ) {
      class Inn implements I {
      String val$argv[] = {"+45"};
      public String s() {
      return argv[0] + val$argv[0];
      }
      }
      iv = new Inn();
      System.out.println("iv.s() : " + iv.s());
          }
      }
      --------------------------------------=== A.java
      class A {
          private int X=17;

          class A2 {
      int x() { return X; }
          }

          int access$000(A a) { return 22; }

          public static void main( final String argv[] ) {
      System.out.println("X (==17) : " + new A().new A2().x() );
          }

      }
      --------------------------------------===

      ======================================================================

            gafter Neal Gafter
            duke J. Duke
            Votes:
            0 Vote for this issue
            Watchers:
            0 Start watching this issue

              Created:
              Updated:
              Resolved:
              Imported:
              Indexed: