JDK-8330037 : Compiler produces invalid bytecode for method class creation from static method
  • Type: Bug
  • Component: tools
  • Sub-Component: javac
  • Affected Version: 17,21,22,23
  • Priority: P4
  • Status: Resolved
  • Resolution: Fixed
  • OS: generic
  • CPU: generic
  • Submitted: 2024-04-10
  • Updated: 2024-11-27
  • Resolved: 2024-11-15
The Version table provides details related to the release that this issue/RFE will be addressed.

Unresolved : Release in which this issue/RFE will be addressed.
Resolved: Release in which this issue/RFE has been resolved.
Fixed : Release in which this issue/RFE has been fixed. The release containing this fix may be available for download as an Early Access Release or a General Availability Release.

To download the current JDK release, click here.
JDK 24
24 b25Fixed
Related Reports
Blocks :  
Description
A DESCRIPTION OF THE PROBLEM :
Run the attached source code, and observe an error at runtime: "java.lang.VerifyError: Bad type on operand stack".

STEPS TO FOLLOW TO REPRODUCE THE PROBLEM :
Download the source code and run it with the `java` command.

EXPECTED VERSUS ACTUAL BEHAVIOR :
EXPECTED -
I would expect a single line to be printed and the terminate to terminate successfully. Or alternatively that the program would not compile (which seems to make more sense to me).
ACTUAL -
The program crashes with the following stacktrace:

Exception in thread "main" java.lang.VerifyError: Bad type on operand stack
Exception Details:
  Location:
    MainClass$1InnerClass.create(Ljava/lang/String;)LMainClass$1InnerClass; @6: getfield
  Reason:
    Type 'java/lang/String' (current frame, stack[3]) is not assignable to 'MainClass$1InnerClass'
  Current Frame:
    bci: @6
    flags: { }
    locals: { 'java/lang/String' }
    stack: { uninitialized 0, uninitialized 0, 'java/lang/String', 'java/lang/String' }
  Bytecode:
    0000000: bb00 0259 2a2a b400 01b7 001b b0

        at MainClass.main(repro.java:22)

The error comes from a compiler-inserted `aload` instruction that tries to load the string from the outer method despite being in an inner method.

---------- BEGIN SOURCE ----------
public class MainClass {
    public static void main(String[] args) {
        Object variable = "world";

        class InnerClass {
            private final String part1;

            InnerClass(String part1) {
                this.part1 = part1;
            }

            @Override
            public String toString() {
                return this.part1 + " " + variable;
            }

            static InnerClass create(String part1) {
                return new InnerClass(part1);
            }
        }

        System.out.println(InnerClass.create("hello,").toString());
    }
}
---------- END SOURCE ----------


Comments
Changeset: 5b9932f8 Branch: master Author: Maurizio Cimadamore <mcimadamore@openjdk.org> Date: 2024-11-15 10:07:18 +0000 URL: https://git.openjdk.org/jdk/commit/5b9932f8f3c320f1d2c95403478a6069d05da52a
15-11-2024

this one will be fixed once fix for JDK-8338288 gets pushed
24-10-2024

A pull request was submitted for review. Branch: master URL: https://git.openjdk.org/jdk/pull/21410 Date: 2024-10-08 14:42:19 +0000
21-10-2024

Possibly related to JDK-8322882.
10-04-2024

Observation on Windows 11 ------------------------------------- JDK 23-ea+9-639 : Failed JDK 22.0.1+7-15 : Failed JDK 17.0.10+11-LTS-240 : Failed
10-04-2024