eclipse-jdt / eclipse-jdt/eclipse.jdt.core

ECJ omits synthetic parameters from RuntimeIn/VisibleAnnotations array

Open
#2,787 6 comments 0 reactions 0 assignees View on GitHub
Dominant language
Java
Stars
237
Forks
195
Avg merge
1d 10h
Merged PRs (30d)
49

Description

Consider input program:

Test.java:
```java
public enum Test {

A("A"), B("B"), C("C");

private Test(@Ann String x) { }

}

@interface Ann {}
```

Test2.java:
```java
public class Test2 { Test t; }
```

If the former is built with ECJ and the latter with `javac`, like:

```
ecj Test.java -source 8 -d out
javac Test2.java -cp out
```

Then `ecj` will emit a constructor for `Test` with method signature `(int, String, String)` (adding two synthetic parameters for the enum ordinal and description), but a `RuntimeInvisibleAnnotations` array of length 1 (omitting the synthetic parameters).

`javac` will hit an array OOB due to this and thus throw a `BadClassFile` error.

The JVMS as of Java 9 says at https://docs.oracle.com/javase/specs/jvms/se21/html/jvms-4.html#jvms-4.7.17 that the annotations array does not have to declare exactly one entry per parameter, but `javac` has never actually respected this (https://bugs.openjdk.org/browse/JDK-8334871 intends to remedy this in Java 24, but older Javas will continue to have problems with `ecj`-generated class files).

By ensuring the generated array always matches the actual method parameter list length (including synthetics), you would improve compatibility with `javac` and `javac`-derived tooling.

Contributor guide

Open the contributing guide

Assessment

This issue has not been assessed yet.

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.