Idea how to implement VT/VO compatibility in JVM
Brian Goetz
brian.goetz at oracle.com
Fri Jan 9 17:50:42 UTC 2015
Short answer: yes.
See Albert Noll's post about heisenboxes, which is one piece of a story
that could address one piece of this.
Where this approach runs out of gas is when data hits the heap: layout
of flattened value fields in objects, and layout of flattened value
elements in arrays. (These are the same challenges as the "erase to
Any" approach.)
The VM let's you override methods, and with bridge methods or other
techniques, we can effectively "override" method signatures. But the VM
doesn't have any such capability for fields. Once you say a field is of
type Object, that's the type.
Think about Box:
class Box<any T> {
T t;
}
We want Box<int> to have a single field that behaves like an 'int'
without boxing and without taking more than four bytes of data payload.
That's the fundamental sticking point with most of the alternate
suggestions; they don't have a path to get there.
On 1/9/2015 12:37 PM, Palo Marton wrote:
> (See this thread:
> http://mail.openjdk.java.net/pipermail/valhalla-dev/2015-January/000710.html)
>
> Main idea is to move information about using VT from method descriptors
> to metadata.
>
> E.g. for method
>
> double distanceTo(point p);
>
> the corresponding method descriptor will “pretend” that the actual
> parameter is boxed object reference, like (LPoint;)D. But in metadata
> (could be eg. parameter annotation in class that declares the method) it
> will indicate that this is actually value type. This way the method
> descriptor for VT and VO will be the same and VO based code should
> actually be able to call VT based method. (note: this “VT erasure”
> should not be done for arguments like ‘point p[]’ as array of VT is very
> different from array of VO).
>
> Of course such change will require a bit different implementation of VT
> in JVM.
>
> One big issue with such implementation is that when mixing VT/VO code,
> situation may arise where one method overrides other method and they
> have different VT flags for their arguments/result, which means that
> they have also different calling convention for JITed code. The same may
> happen when implementing interface. This may be solved by allocating
> another slot in vftable for that function and filling original slot with
> some small bridge code that will handle needed boxing/unboxing and call
> method from the right vftable slot. So in case of mixed VT/VO code there
> may be multiple slots for one method (=method descriptor) in vftable.
> Big change, I know…
>
> Other issue is that if we move info about VT from method descriptor to
> metadata, we should do the same also for bytecode of method. So bytecode
> will manipulate VT values using normal reference instructions (aload,
> astore, …). This also means that JVM interpreter will use only boxed VT
> values. It is a performance penalty for interpreter, but may be this is
> not so important as most code will be JITed. JIT compiler can utilize
> information from metadata to do more aggressive stack/register
> allocation (no escape analyses is needed for VT values) and better
> argument passing and result returning.
>
> There are many other issues with this. For some of them I see solution,
> but there are probably many “devils in details” that I can not see.
>
>
> Question: Have you considered such approach to VT? It basically means
> that VT is implemented as value object for which JIT can do more
> aggressive optimizations thanks to metadata included in places where it
> was used as VT in the source code.
More information about the valhalla-dev
mailing list