RFR: JDK-8205549 JDK-8205698 Support of flattened values in Unsafe
John Rose
john.r.rose at oracle.com
Fri Jun 29 22:08:13 UTC 2018
On Jun 29, 2018, at 2:40 PM, Karen Kinnear <karen.kinnear at oracle.com> wrote:
>
> Thank you all for the rapid responses and prototyping.
>
> Based on John/Paul/Remi’s suggestions - this is what I propose we do for LW1:
> (Roland, Tobias - intrinsics questions embedded please)
>
> I. … III.
Yes, that's a good breakdown into steps.
> IV. Immutability
> Immutability is not just a good idea, …
> Immutability is not the same as final - sorry - we actually count on it.
> I highly recommend that even through unsafe - value types are immutable.
I have to disagree on this one. Immutability is a stronger invariant than
final, but Unsafe is stronger than both.
Unsafe has to be able to bend all those rules. The design constraint
for Unsafe is that there has to be a safe way to use it. Other than that,
there are no constraints on what Unsafe is allowed to touch. It is the
Java way to scribble on memory like C++ can do.
I claim adding the makePrivateBuffer/finishPrivateBuffer API points will
enable us to preserve immutability invariants around the private buffer,
while accurately collecting the required side effects. I *think* there is an
efficient way to implement those API points; if I'm wrong we'll have to
come up with an alternative API point for Unsafe.
> V. Nullability
> In LW1, all instance fields of value types are flattenable and non-nullable.
> We have the option in putValue of not allowing writing null to an value type instance field.
> Let’s start with that assumption.
I agree. As with Tobias' latest JIT work on nullability, the detection of nulls
is a caller responsibility. We don't have any future work on the books to
fold nullability into flattened fields, only non-flattened fields. This could
change, but then we'd need to make adjustments throughout the system,
not just Unsafe.
> We intend to add flattenable static fields shortly after LW1, so we should disallow writing
> null to flattenable value type static fields.
Yes, where "disallow" has the usual meaning for Unsafe: It is a caller
responsibility to check for this, and if the caller makes a mistake, then
you might get a good diagnosis of this, but if the code was optimized,
you'll get unpredictable results. NPE or InternalError if you are lucky.
So, nulls are never correctly written (via Unsafe) to flattened variables,
and if they are incorrectly written, we get the usual unpredictable behavior
from Unsafe.
Loading a null *from* a non-flattened variable is open to interpretation
(as in Tobias' JIT work), but I would lean towards requiring the user
to call getReference and explicitly test for null and replace with T.default
if that is what was intended. Having getValue automatically replace
null with T.default (for an invisible non-flattened variable) is a little too
indirect for Unsafe, although it might be the right call in this case,
if the value type is *never* flattened.
> Open Questions:
> 1. atomic/volatile/etc. What can you do at the java level?
> We don’t currently support atomic flattenable value types.
I think this is the plan of record: Translate volatile value fields to non-flattened
non-nullable fields; do this transparently in the class loader. Later on: Experiment
with SeqLock-based protocols. Overlay the SeqLock in the containing object
header if possible. Perhaps use split locks with flattened arrays.
The interaction with Unsafe would be as follows: If a value field is translated
to a non-flattened field, we can detect this with a metadata query, and use
get/putReference instead of get/putValue. (Or we can make it automagic
inside of get/putValue, as long as the operands to get/putValue distinguish
correctly between flattened and non-flattened fields.) My assumption here
is that every field can be fully described as either flattened or not, with
nullability as an extra bit if it is not flattened. If we get fancier with field
representations, then the Unsafe API points might need to take more
arguments to reflect the new fancy degrees of freedom, along with the
rest of the JVM internals. Unsafe is part of the JVM internals.
— John
More information about the valhalla-dev
mailing list