New JEP: Classfile Processing API

Brian Goetz brian.goetz at oracle.com
Sun Jun 19 14:11:38 UTC 2022


Generation, parsing, and transformation of classfiles is ubiquitous in 
the Java ecosystem.  Frameworks transform classfiles on the fly by 
hooking into classloaders or using `java.lang.instrument`; compilers and 
IDEs for all sorts of languages read and write classfiles; static 
analysis tools read classfiles; migration tools transform classfiles.  
In the JDK, we have a static compiler (`javac`) and other tools 
(`javap`, `jlink`) that read or transform classfiles, and numerous 
platform features that operate by classfile generation (reflection, 
lambdas, dynamic proxies, method handles), as well as many tests that 
generate classfiles.  In fact, the JDK contains at least three libraries 
for processing classfiles: an internal one (used by JDK tools such as 
`javac`); a fork of ASM (used by lambdas and many other platform 
features), and a fork of BCEL (contained inside a fork of Xalan). And of 
course the ecosystem has many such libraries: ASM, javassist, cglib, 
BCEL, gnu.bytecode, ByteBuddy, and many others.

Over the years, there have been many calls for Java to have an 
"official" classfile library, and there are numerous practical reasons 
to create one, and the shift to the six-month cadence has added two new 
reasons.  Firstly, tools that bundle classfile libraries are more likely 
to encounter classfile versions "from the future", because they use a 
classfile library that knows about Java N, but the customer may be 
running it on Java N+1, which was released only six months later.  
Second, the pace of classfile format evolution has picked up 
significantly in recent years, with a significant fraction of releases 
having at least some change to the classfile format (new attributes, new 
constant pool forms, new bytecodes, new combinations of flags, etc).  
Having an official classfile library would mean that applications and 
tools are guaranteed to have access to a library that is up-to-date to 
the latest classfile version that will run on the current JDK.

It might seem an "obvious" choice to "just" standardize on ASM, but 
there are many reasons not to do so.  ASM is an old codebase with plenty 
of legacy baggage; the design priorities that informed its architecture 
are not ideal for the JDK in 2022; and the language has improved 
substantially since them (lambdas, records and sealed classes, pattern 
matching.)  What were the best possible API idioms in 2002 (visitors) 
may not be ideal two decades later.

A draft JEP can be found here:

https://openjdk.org/jeps/8280389

Such an API will have many consumers, both internal to the JDK and 
external: compilers, analysis tools, platform implementation, 3rd party 
libraries, tests, etc.  We will focus initially on the internal JDK 
consumers, incrementally migrating them off of the existing libraries 
and onto the new library.  Eventually, once all the internal consumers 
are migrated, we will be able to remove ASM from the JDK entirely.  
Initially, the library will be internal-only (non-exported), to gain 
experience with and refine the API before committing to a public 
version. When the API is sufficiently stable, it will be exported for 
public use, first as a preview API and eventually as a permanent API.

Comments on the JEP itself -- the concept, motivation, and design goals 
-- are invited for discussion.  The JEP includes some code examples, 
which are hopefully illustrative, but I will request that people hold 
off on API discussions for the time being, to make room for discussion 
on the JEP itself first.
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <https://mail.openjdk.org/pipermail/discuss/attachments/20220619/9dd4048f/attachment-0001.htm>


More information about the discuss mailing list