MVT-based vectors: experiments with JVM support
Vladimir Ivanov
vladimir.x.ivanov at oracle.com
Wed Nov 22 14:43:27 UTC 2017
Hi,
Based on the initial experience (very pleasant!) with MVT-based vectors
[1], I decided to proceed and tried to port JVM part of vector support
from Panama. I'd like to update you where we stand right now.
Vector support in Panama mostly resides in C2. Vectors are represented
in Java either as super-longs (e.g, Long4 [2]) or typed classes (e.g.,
jdk.incubator.vector.Int256Vector [3]) and C2 tries hard to avoid boxing
by wrapping vector values in VectorBoxNode [4] or VBoxNode [5] nodes and
dragging values through vector store/load chains between vector IR
nodes. Since Panama doesn't support any notion of value types yet in
bytecode (Q-types), it works in adhoc manner.
In Valhalla/MVT there's much more powerful alternative - ValueTypeNode.
Moving from VectorBoxNode/VBoxNode to ValueTypeNode looks very
promising. Some nice synergies between vectors & value types become
possible, like extending VT-specific calling conventions in C2 to vector
calling conventions, e.g:
QLong4(QLong4,QLong4) => ymm0(ymm0,ymm1)
But, unfortunately, simply replacing VectorBoxNode/VBoxNode with
ValueTypeNode doesn't work.
ValueTypeNode represents a value instance as a pack of elements
comprising it. Elements are either primitive/reference values or other
composite values. But for vectors it's desirable to keep them
indivisible on JVM level. And that requires drastic changes across the
JVM, like adding new case into JVM's BasicType structure [6].
ValueTypeNode vbuf v # vector[4]{int}
where
buf is value buffer (optional)
v is vector[4]{int}
The alternative is to pretend that vectors are just a dense homogeneous
packs of primitive elements (e.g., vector of 8 ints):
ValueTypeNode vbuf i0 i1 i2 i3 # vector[4]{int}
But (even leaving endianness aspect aside) that still requires some
special logic (though much more focused compared to new basic type) to
produce efficient vectorized code.
Some examples:
(0) On IR level, every vector value has to be unpacked before used in
ValueTypeNode:
ValueTypeNode _ (Unpack #0 v) (Unpack #1 v)
(Unpack #2 v) (Unpack #3 v) # vector[4]{int}
where: v is vector[4]{int}
Compiler has to thread the vector and connect users directly to it in
order to avoid repacks leaking into generated code.
(1) Vector values are represented as single values in C2 IR and
indivisible w/o special operations.
Extracting/updating element in a vector residing in a register requires
special instructions ([v]pinsr*/[v]pextr*). Simply changing an edge
doesn't (it'll lead to vector repackaging):
#vwithfield
UpdateElement #2 new_i2
(ValueTypeNode (vbuf?) i0 i1 i2 i3 # vector[4]{int})
=\=>
ValueTypeNode _ i0 i1 new_i2 i3 # vector[4]{int}
(2) (Packed) vector values should be loaded & stored in one step
(represented as LoadVectorNode/StoreVectorNode in C2).
If a vector memory operation is represented as per-element operation &
an explicit pack, then C2 has to convert that shape into vectorized
load/store:
Pack (LoadI arr +16) (LoadI arr +20)...(LoadI arr +28) # vector{int,4}
# 4 instructions: pinsrd, pinsrd, pinsrd, pinsrd
===>
LoadVector arr +16 # vector {int,4}
# 1 instruction: vmov
(3) Rematerialization (on deoptimization) has to support vector values.
On rematerialization there are no individual entries for vector
elements, but a single one for the raw vector value. Rematerialization
logic has to know how to properly move it into the buffer.
Current status is:
(1) I played with former approach (full support for vector values
across the JVM) for some time and gave up :-)
(2) Latter approach (vectors as explicit packs of elements) is still
an idea, but looks promising enough to give it a try.
Best regards,
Vladimir Ivanov
[1]
http://mail.openjdk.java.net/pipermail/valhalla-dev/2017-June/002731.html
[2]
http://hg.openjdk.java.net/panama/panama/jdk/file/300a5ac72db8/src/java.base/share/classes/java/lang/Long4.java
[3]
http://hg.openjdk.java.net/panama/panama/jdk/file/300a5ac72db8/src/jdk.incubator.vector/share/classes/jdk/incubator/vector/Int256Vector.java
[4]
http://hg.openjdk.java.net/panama/panama/hotspot/file/69c75a8e7c74/src/share/vm/opto/vectornode.hpp#l822
[5]
http://hg.openjdk.java.net/panama/panama/hotspot/file/69c75a8e7c74/src/share/vm/opto/callnode.hpp#l1172
[6]
http://hg.openjdk.java.net/panama/panama/hotspot/file/69c75a8e7c74/src/share/vm/utilities/globalDefinitions.hpp#l645
More information about the valhalla-dev
mailing list