Core Java

The Class-File API Replacing ASM: What It Means for Frameworks

Almost every Java developer has seen this error after a JDK upgrade: “Unsupported class file major version.” Behind it sits a quiet dependency. Many frameworks read and rewrite bytecode, and they usually rely on ASM to do it.

Starting with JDK 24, the JDK ships its own answer. In this article, we look at the Class-File API, check which release finalized it, measure what the old problem looks like on JDK 25, and see what frameworks should do next.

Which JDK Made It Final?

The Class-File API became a standard, final feature in JDK 24. According to JEP 484, it first appeared as a preview in JDK 22 (JEP 457), was refined in JDK 23 (JEP 466), and was finalized in JDK 24 with minor changes. It lives in the java.lang.classfile package.

JDKJEPStatus
22457Preview
23466Second preview
24484Final

The Problem ASM Could Not Solve Alone

A format that moves every six months

Frameworks that process class files usually bundle a library such as ASM, BCEL, or Javassist. However, JEP 484 points out that the class-file format now evolves faster, because of the six-month release cadence. As a result, framework authors need a library that is always up to date with the running JDK.

ASM has a structural delay here. The JEP explains that the ASM version for JDK N cannot be finalized until JDK N is finalized. Consequently, tools inside the JDK cannot use class-file features new in JDK N, and even javac must wait until JDK N+1 to emit them.

Why the JDK built its own

The JDK already carried several internal class-file implementations. The INNOQ overview notes that ASM looked like an obvious choice, yet its older codebase no longer meets modern API needs. Likewise, the InfoQ news roundup describes the new API as starting out as an internal replacement for ASM in the JDK, with plans to open it as a public API.

What the Numbers Say

To see the lag in practice, I ran a small experiment on JDK 25. First, I read every class in the java.base module (7,406 classes) with ASM 9.7, the version packaged by Ubuntu. Then I did the same with the Class-File API.

Figure 1. Classes parsed on JDK 25 (class-file major version 69). Data note: my own run. ASM 9.7 predates JDK 25, and newer ASM releases do support newer class files, so this shows the lag pattern, not a permanent limit.

ASM 9.7 rejected 7,405 of the 7,406 classes with “Unsupported class file major version 69.” The Class-File API parsed all of them, because it ships with the JDK it describes.

Next, I compared speed on a fair footing: JDK 21’s java.base (7,567 classes), which ASM 9.7 can read. Each run walked every method and its code. I repeated the run three times.

Figure 2. Median of 7 timed passes per run, in milliseconds. Data note: single machine, no isolated benchmark harness. The two walkers do not do identical work, so read this as “same ballpark”, not as a speed claim.

The Class-File API landed around 105 ms and ASM around 120 ms, with one noisy ASM run. Therefore, performance is not a reason to avoid the switch. Compatibility is the real story.

What It Means for Frameworks

AreaWith a bundled ASMWith the Class-File API
New JDK releaseWait for a new ASM, then upgrade the dependencyWorks with the running JDK
Dependency treeOne more library, often repackagedPart of the platform
Older JDKsFully supportedUnavailable below JDK 24
StyleVisitor-based streamingImmutable models and transformations

Importantly, the catch is the baseline. Most frameworks still support JDK 17 or 21, where the API does not exist. For example, an Apache Maven compiler plugin discussion suggests detecting JDK 24 or newer at runtime and preferring the Class-File API, with ASM as the fallback.

That dual path is a sensible middle road. Frameworks keep ASM for older runtimes, and they use the built-in API where it exists. Over time, as baselines move forward, the ASM path can be removed.

Quick checklist

  • Check which JDK your framework baseline requires.
  • List every place your project reads or writes bytecode.
  • Upgrade ASM before testing a new JDK, if you still use it.
  • Prefer java.lang.classfile in code that only targets JDK 24+.
  • Test the JDK early-access builds to catch format changes sooner.

What We Have Learned

The Class-File API was finalized in JDK 24, after previews in JDK 22 and 23. It exists because the class-file format now changes every six months, and an external library such as ASM can only catch up after each JDK release. Our measurement showed this clearly: ASM 9.7 rejected nearly every JDK 25 class, while the built-in API read them all. Speed was comparable, so the benefit is trust, not raw performance. In practice, frameworks should adopt a dual path today and drop ASM once their baseline reaches JDK 24.

Eleftheria Drosopoulou

Eleftheria is an Experienced Business Analyst with a robust background in the computer software industry. Proficient in Computer Software Training, Digital Marketing, HTML Scripting, and Microsoft Office, they bring a wealth of technical skills to the table. Additionally, she has a love for writing articles on various tech subjects, showcasing a talent for translating complex concepts into accessible content.
Subscribe
Notify of
guest

This site uses Akismet to reduce spam. Learn how your comment data is processed.

0 Comments
Oldest
Newest Most Voted
Back to top button