<div dir="ltr"><div>Thanks Dan and Fred for the clarification on the current spec and Hotspot behaviour and John for suggesting we remove the attribute.</div><div><br></div><div>I think the problem with the current status quo for the preload attribute is that we're trying to treat it like an optimization - a "we can have our cake" (know which classes to load at some indeterminate point) and "eat it too" (not promise users anything about when or if those classes will be loaded).</div><div><br></div><div>As it stands, based just on the spec, it's hard for users to know what the preload attribute will do for them.  There's nothing they can depend on in the spec and are at the mercy of whatever behaviour VM implementers pick on a given day.  Which means they will depend on the current Hotspot behaviour (defacto standardization - yuck!) or expect the behaviour to change all the time.</div><div><br></div><div>If we decouple the list of preloadable classes from the classfile, how would non-jdk classes be handled?  Many applications are a mix of multiple jar files from different maintenance domains which would make having a combined list difficult.  We'd also need to think through the classloader implications vs today's approach which attempts to load on the same loader as the class with the preload attribute.</div><div><br></div><div>What if instead of ditching the attribute, or treating it like an optimization, we firmed up the contract and treated it as a guarantee similar to those of superclasses and superinterfaces as in the first line in section 5.4 "Linking"?  The new text would read something like:</div><div>   > <span style="color:rgb(0,0,0);font-size:12px">Linking a class or interface involves verifying and preparing that class or interface, its direct superclass, its direct superinterfaces, and its element type (if it is an array type), if necessary.</span><span style="color:rgb(0,0,0);font-size:12px"> Any classes listed in the preload attribute will be loaded at this point.</span></div><div><span style="color:rgb(0,0,0);font-size:12px"><br></span></div><div><span style="color:rgb(0,0,0);font-size:12px">We don't need to say in the JVMS why the classes are in the attribute, but we should be explicit about where the attempt to load them occurs and that errors are ignored.  This provides stability to the users and allows for independent implementation while avoiding de facto standardization of today's behaviour.</span></div><div><span style="color:rgb(0,0,0);font-size:12px"><br></span></div><div>Before responding, I built the latest lworld branch of the Valhalla repo and played with the preload attribute to try and force a classloader-related deadlock.  I was surprised to find that the attribute doesn't seem to have an effect on user-defined loaders and with the current spec, I can't even say if that's a bug or not.  Example classfiles for this exploration are in <a href="https://github.com/DanHeidinga/valhalla-preload-example">https://github.com/DanHeidinga/valhalla-preload-example</a></div><div><br></div><div>--Dan</div></div><br><div class="gmail_quote"><div dir="ltr" class="gmail_attr">On Mon, Jun 5, 2023 at 9:52 PM John Rose <<a href="mailto:john.r.rose@oracle.com">john.r.rose@oracle.com</a>> wrote:<br></div><blockquote class="gmail_quote" style="margin:0px 0px 0px 0.8ex;border-left:1px solid rgb(204,204,204);padding-left:1ex"><u></u>


<div><div style="font-family:sans-serif"><div style="white-space:normal">
<p dir="auto">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.</p>
<p dir="auto">On 1 Jun 2023, at 11:24, Dan Smith wrote:</p>
</div><div style="white-space:normal"><blockquote style="margin:0px 0px 5px;padding-left:5px;border-left:2px solid rgb(119,119,119);color:rgb(119,119,119)"><blockquote style="margin:0px 0px 5px;padding-left:5px;border-left:2px solid rgb(153,153,153);color:rgb(153,153,153)"><p dir="auto">On Jun 1, 2023, at 10:53 AM, Dan Heidinga <<a href="mailto:heidinga@redhat.com" target="_blank">heidinga@redhat.com</a>> wrote:</p>
<p dir="auto">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."</p>
<p dir="auto">The Preload attribute removes one need for Q modifiers while allowing calling convention optimizations and layout decisions to be made early.</p>
<p dir="auto">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).</p>
</blockquote><p dir="auto">FWIW, the JEP has more detail about when javac is expected to include classes in Preload.</p>
<blockquote style="margin:0px 0px 5px;padding-left:5px;border-left:2px solid rgb(153,153,153);color:rgb(153,153,153)"><p dir="auto">I think it's time to tighten up the spec for Preload attribute and specify:
<br>
* what the VM will do with classes listed in the attribute</p>
</blockquote><p dir="auto">It is intentional that the VM may choose to do nothing. So anything it does is purely an optimization.</p>
</blockquote></div>
<div style="white-space:normal">
<p dir="auto">Looks like a nop…</p>
<p dir="auto">(In particular, it should not <em>reject</em> any inputs, because that would destabilize separate compilability in unpredictable ways.)</p>
</div><div style="white-space:normal"><blockquote style="margin:0px 0px 5px;padding-left:5px;border-left:2px solid rgb(119,119,119);color:rgb(119,119,119)"><blockquote style="margin:0px 0px 5px;padding-left:5px;border-left:2px solid rgb(153,153,153);color:rgb(153,153,153)"><p dir="auto">* when those classes will be loaded (ie: somewhere in JVMS 5.3)</p>
</blockquote><p dir="auto">If the VM chooses to load Preload classes, then our thinking was that JVMS 5.4 already describes the details of timing:</p>
<p dir="auto"><a href="https://docs.oracle.com/javase/specs/jvms/se20/html/jvms-5.html#jvms-5.4" style="color:rgb(119,119,119)" target="_blank">https://docs.oracle.com/javase/specs/jvms/se20/html/jvms-5.html#jvms-5.4</a></p>
<p dir="auto">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.</p>
<p dir="auto">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. :-)</p>
</blockquote></div>
<div style="white-space:normal">
<p dir="auto">Sometimes you want them early (for instance layout) and sometimes you need to wait (vtable layout or even just before <clinit>).</p>
</div><div style="white-space:normal"><blockquote style="margin:0px 0px 5px;padding-left:5px;border-left:2px solid rgb(119,119,119);color:rgb(119,119,119)"><blockquote style="margin:0px 0px 5px;padding-left:5px;border-left:2px solid rgb(153,153,153);color:rgb(153,153,153)"><p dir="auto">* how invalid cases are handled, including circularities (Class A's Preload mentions B <: A)</p>
</blockquote></blockquote></div>
<div style="white-space:normal">
<p dir="auto">Silent supression of errors, if any.  Again, like a nop…</p>
</div><div style="white-space:normal"><blockquote style="margin:0px 0px 5px;padding-left:5px;border-left:2px solid rgb(119,119,119);color:rgb(119,119,119)"><p dir="auto">"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."</p>
<p dir="auto">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.)</p>
<blockquote style="margin:0px 0px 5px;padding-left:5px;border-left:2px solid rgb(153,153,153);color:rgb(153,153,153)"><p dir="auto">* what types of classes can be listed (any? only values?)</p>
</blockquote><p dir="auto">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.</p>
<p dir="auto">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.</p>
<blockquote style="margin:0px 0px 5px;padding-left:5px;border-left:2px solid rgb(153,153,153);color:rgb(153,153,153)"><p dir="auto">It probably makes sense to start from the current Hotspot handling of the attribute and fine tune that into the spec?</p>
</blockquote><p dir="auto">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...</p>
</blockquote></div>
<div style="white-space:normal">
<p dir="auto">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.</p>
<p dir="auto">As you see, I’m kind of sour on a Preload attribute these days.</p>

</div></div></div>


</blockquote></div>