Overall, as we look at Preload, it is looking more and more like a
no-op, as far as the JLS and JVMS is concerned. Perhaps that is a
signal that it should be placed somewhere outside of the JVMS, such as
in a Leyden-specific mechanism (a preload list) produced in a way
decoupled from any transactions between the JLS and JVMS.
On 1 Jun 2023, at 11:24, Dan Smith wrote:
On Jun 1, 2023, at 10:53 AM, Dan Heidinga <[email protected]>
wrote:
A couple of questions about the spec for the Preload attribute[0].
The current spec says it indicates "certain classes contain
information that may be of interest during linkage."
The Preload attribute removes one need for Q modifiers while allowing
calling convention optimizations and layout decisions to be made
early.
The current spec is quite vague on what classes should be included in
the attribute and on when / what the VM will do with those classes
(or even if it does anything).
FWIW, the JEP has more detail about when javac is expected to include
classes in Preload.
I think it's time to tighten up the spec for Preload attribute and
specify:
* what the VM will do with classes listed in the attribute
It is intentional that the VM may choose to do nothing. So anything it
does is purely an optimization.
Looks like a nop…
(In particular, it should not *reject* any inputs, because that would
destabilize separate compilability in unpredictable ways.)
* when those classes will be loaded (ie: somewhere in JVMS 5.3)
If the VM chooses to load Preload classes, then our thinking was that
JVMS 5.4 already describes the details of timing:
https://docs.oracle.com/javase/specs/jvms/se20/html/jvms-5.html#jvms-5.4
So, for example, "Alternatively, an implementation may choose an
"eager" linkage strategy, where all symbolic references are resolved
at once when the class or interface is being verified." That is, the
Preload classes could all be loaded during verification, or at some
other stage of linking.
My expectation is that the natural point for processing Preload is
during preparation as vtables are set up, but sometimes I get these
things wrong. :-)
Sometimes you want them early (for instance layout) and sometimes you
need to wait (vtable layout or even just before <clinit>).
* how invalid cases are handled, including circularities (Class A's
Preload mentions B <: A)
Silent supression of errors, if any. Again, like a nop…
"Errors detected during linkage are thrown at a point in the program
where some action is taken by the program that might, directly or
indirectly, require linkage to the class or interface involved in the
error."
I've always found this rule super vague, but I think "require" is the
key word, and implies that errors caused by Preload resolution should
just be ignored. (Because Preload isn't "required" to be processed at
all.)
* what types of classes can be listed (any? only values?)
Definitely intend to support any classes of interest. Say a future
optimization wants to know about a sealed superinterface, for
example—it would be fine to tweak javac to add that interface to
Preload, and then use the information to facilitate the optimization.
There's a lot of nondeterminism here—can a compliant system trigger
changes to class loading timing, but just on my birthday?—but I
think it's within the scope of JVMS 5.4, which provides a lot of
latitude for loading classes whenever it's convenient.
It probably makes sense to start from the current Hotspot handling of
the attribute and fine tune that into the spec?
So I've outlined our hands-off stake in the ground above. The spec
would definitely benefit, at least, from a non-normative
cross-reference to 5.4 and short explanation. Beyond that, I think
we'd be open to specifying more if we can agree something more is
needed...
I think we could get the benefits in Fred’s prototype (as he
describes) with a list that is decoupled from any particular class file,
and Leyden could deliver this list.
As you see, I’m kind of sour on a Preload attribute these days.