[vector] Vector API -- alignment with value types

Brian Goetz brian.goetz at oracle.com
Wed Jan 30 20:58:52 UTC 2019



> Part I
> ------
>
> Here's an idea for simplifying Species, which is: let's drive Species 
> down to be a simple class that is really just a constant holder for 
> (element type, shape), and move all the behavior to static methods on 
> XxxVector. 

I've started prototyping this, in a rather slash-and-burn manner.  I am 
about halfway through.  So far, its working, the set of changes I had to 
make to client code is very small (almost all transforming 
species.doSomething(args) to XxxVector.doSomething(species, args)).

The question, of course, is whether the intrinsification will all 
survive the transformation.  The most common case is that I have 
transformed vector intrinsic calls from

     VectorIntrinsic.blah(Int128Vector.class, ...)

to

     VectorIntrinsics.blah(species.boxType(), ...)

The basic assumption is that, under the same conditions that we get 
inlining now, we'll know the species is a constant, and boxType() will 
just inline to a concrete box type anyway.  (The goal is to get species 
to be values, but in the meantime, they can be enum constants.)  This 
should work, but we'll likely have to do some JIT work to get back to 
where we see all the inlining and intrinsification.  (Much of this would 
come free in Valhalla.)

There are a few cases where we can't just do the above, and have to do a 
switch in the lifted method, such as:

public static Shuffle<Byte> shuffle(ByteSpecies species, IntUnaryOperator f) {
     if (species.boxType() == ByteMaxVector.class)
         return new ByteMaxVector.ByteMaxShuffle(f);
     switch (species.bitSize()) {
         case 64:return new Byte64Vector.Byte64Shuffle(f);
         case 128:return new Byte128Vector.Byte128Shuffle(f);
         case 256:return new Byte256Vector.Byte256Shuffle(f);
         case 512:return new Byte512Vector.Byte512Shuffle(f);
         default:throw new IllegalArgumentException(Integer.toString(species.bitSize()));
     }
}


Because again, species is a constant, this should also just inline down 
to the right thing.  So far, other than reshape/rebracket, I haven't 
seen anything requiring more complicated transformations.

The only code I found so far that tries to be agnostic to shape and size 
both is VectorResizeTest; there are strategies for making this work 
without the combinatorial automated specialization, so I don't see this 
as a big impediment.

Where this leads to is:
  - Vector.Species becomes an interface with a handful of methods 
(bitSize, etc), and quite possibly one that no one uses directly;
  - IntSpecies and friends become enums, with enum constants for I64, 
I128, etc (or, values, with static constants for the values);
  - The specialized classes for XxxNnVector.XxxNnSpecies _go away_;
  - Users need not learn about species at all, but if they do care, they 
are just simple data constants that get fed through the API.

I'm not done (and am traveling the next two weeks), but I think I've 
made progress validating the API transformation.  The real question, 
then, is when do we do this.  I think it would be best to do before 
previewing, simply because it is such an intrusive refactoring. But, 
we'd have to evaluate whether we can mitigate the impact in time.




More information about the panama-dev mailing list