United StatesChange Country, Oracle Worldwide Web Sites Communities I am a... I want to...
Bug ID: JDK-7160084 javac fails to compile an apparently valid class/interface combination
JDK-7160084 : javac fails to compile an apparently valid class/interface combination

Details
Type:
Bug
Submit Date:
2012-04-09
Status:
Closed
Updated Date:
2012-07-11
Project Name:
JDK
Resolved Date:
2012-07-11
Component:
tools
OS:
generic
Sub-Component:
javac
CPU:
generic
Priority:
P4
Resolution:
Fixed
Affected Versions:
7
Fixed Versions:

Related Reports
Backport:

Sub Tasks

Description
SYNOPSIS
--------
javac fails to compile an apparently valid class/interface combination

OPERATING SYSTEMS
-----------------
All

FULL JDK VERSIONS
-----------------
All (tested on latest 5.0, 6, 7 and 8)

PROBLEM DESCRIPTION
-------------------
javac fails to compile a enum type if it implements an interface which contains an enum with the same name as that of the implementor.

In the testcase provided below, interface TestInterface has a enum type "enumA", while the class TestClass also has an enum type "enumA" which implements TestInterface. During compilation, javac appears to encounter a name resolution issue and an error occurs.

The same code compiles with no issues under Eclipse, although this scenario does not seem to be explicitly described in the Java Language Specification.

REPRODUCTION INSTRUCTIONS
-------------------------
1. Create the files as provided below
2. Attempt to compile the class:  javac TestClass.java

Expected behaviour
Class should compile with no errors

Actual behaviour
Compilation fails with the following error:

TestClass.java:4: enumA(java.lang.String) has private access in TestInterface.enumA
        A("AAA");
        ^
1 error

TESTCASE
--------
------------------------------------------------------------------------
TestInterface.java
------------------------------------------------------------------------
public interface TestInterface {
    public enum enumA implements TestInterface {
        I("III");

        private enumA(String s) {
            System.out.println(s);
        }
    }
}

------------------------------------------------------------------------
TestClass.java
------------------------------------------------------------------------
public final class TestClass {
    // This causes an error
    public enum enumA implements TestInterface {
        A("AAA");
       
        private enumA(String s) {
            System.out.println(s);
        }
    }
       
    // This doesn't cause an error
    public enum enumB implements TestInterface {
        B("BBB");
       
        private enumB(String s) {
            System.out.println(s);
        }
    }
}

                                    

Comments
EVALUATION

Hi David,
here's a more detailed analysis on this bug. A source that can be used to reproduce the problem is the following:

interface Intf {
     enum MyEnumA {
        AA("");

        private MyEnumA(String s) { }
     }
}

class Test {
      enum MyEnumA implements Intf {
          AA("");

          private MyEnumA(String s) { }
     }
}

When javac compiles this source, it transforms it into the following program (enum are replaced by classes/enum values by static fields):

interface Intf {

      public static class MyEnumA {
          public static final MyEnumA AA = new MyEnumA("");

          private MyEnumA(String s) {     }
      }
}

class Test {

      Test() {
          super();
      }

      static class MyEnumA implements Intf {
          public static final MyEnumA AA = new MyEnumA("");

          private MyEnumA(String s) {        }
      }
}

Which is an illegal source - we should generate qualified name for enum in synthetized enum fields, so that scoping issues are properly addressed.
                                     
2012-05-31
SUGGESTED FIX

A webrev of this fix is avalable at the following URL:
http://hg.openjdk.java.net/jdk8/tl/langtools/rev/37dc15c68760
                                     
2012-05-31



Hardware and Software, Engineered to Work Together