RFR: 8361214: An anonymous class is erroneously being classify as an abstract class

Chen Liang liach at openjdk.org
Wed Jul 2 23:18:37 UTC 2025


On Wed, 2 Jul 2025 18:01:15 GMT, Vicente Romero <vromero at openjdk.org> wrote:

> Javac is failing to compile this code:
> 
> abstract class Base<T> {}
> abstract class Derived1<T> extends Base<T> {}
> abstract class Derived2<T> extends Base<T> {
>     Derived2(Derived1<T> obj) {}
> }
> 
> class Test {
>     Base<String> obj = new Derived2<>(new Derived1<>() { /* not abstract */ }) { /* not abstract */ };
> }
> 
> issuing error message:
> 
> Test.java:8: error: Derived1 is abstract; cannot be instantiated
>     Base<String> obj = new Derived2<>(new Derived1<>() { /* not abstract */ }) { /* not abstract */ };
> 
> basically during speculative attribution we make a copy of the new class expression but the class body is nuked to avoid side-effects during the process. Javac is checking the error condition on a speculative version of the AST and thus it seems to it that the user is trying to create an abstract class. The proposed fix is to use an already existing predicate that indicates if the class body has been removed or not,
> 
> TIA

Looks reasonable.

I see there are two sites of `cdef != null && clazztype.tsym.isInterface()`; do they need to check this too?

-------------

Marked as reviewed by liach (Reviewer).

PR Review: https://git.openjdk.org/jdk/pull/26103#pullrequestreview-2980889360


More information about the compiler-dev mailing list