< prev index next >
src/jdk.incubator.vector/share/classes/jdk/incubator/vector/X-Vector.java.template
Print this page
rev 55589 : 8221816: [vector] IndexOutOfBoundsException for fromArray/intoArray with unset mask lanes
Reviewed-by: duke
@@ -196,21 +196,25 @@
* @return the vector loaded from an array
* @throws IndexOutOfBoundsException if {@code i < 0}, or
* {@code i > a.length - this.length()}
*/
@ForceInline
- @SuppressWarnings("unchecked")
- public static $abstractvectortype$ fromArray($Type$Species species, $type$[] a, int i){
+ public static $abstractvectortype$ fromArray($Type$Species species, $type$[] a, int i) {
Objects.requireNonNull(a);
i = VectorIntrinsics.checkIndex(i, a.length, species.length());
+ return fromArrayWithoutCheck(species, a, i);
+ }
+
+ @ForceInline
+ @SuppressWarnings("unchecked")
+ static $abstractvectortype$ fromArrayWithoutCheck($Type$Species species, $type$[] a, int i) {
return VectorIntrinsics.load((Class<$abstractvectortype$>) species.boxType(), $type$.class, species.length(),
a, (((long) i) << ARRAY_SHIFT) + Unsafe.ARRAY_$TYPE$_BASE_OFFSET,
a, i, species,
(c, idx, s) -> (($Type$Species)s).op(n -> c[idx + n]));
}
-
/**
* Loads a vector from an array starting at offset and using a mask.
* <p>
* For each vector lane, where {@code N} is the vector lane index,
* if the mask lane at index {@code N} is set then the array element at
@@ -227,11 +231,16 @@
* for any vector lane index {@code N} where the mask at lane {@code N}
* is set {@code i > a.length - N}
*/
@ForceInline
public static $abstractvectortype$ fromArray($Type$Species species, $type$[] a, int i, Mask<$Boxtype$> m) {
- return zero(species).blend(fromArray(species, a, i), m);
+ Objects.requireNonNull(a);
+ if (i + species.length() <= a.length) {
+ return zero(species).blend(fromArrayWithoutCheck(species, a, i), m);
+ } else {
+ return species.op(m, n -> a[i + n]);
+ }
}
/**
* Loads a vector from an array using indexes obtained from an index
* map.
@@ -257,33 +266,38 @@
public static $abstractvectortype$ fromArray($Type$Species species, $type$[] a, int i, int[] indexMap, int j) {
return species.op(n -> a[i + indexMap[j + n]]);
}
#else[byteOrShort]
@ForceInline
- @SuppressWarnings("unchecked")
public static $abstractvectortype$ fromArray($Type$Species species, $type$[] a, int i, int[] indexMap, int j) {
Objects.requireNonNull(a);
Objects.requireNonNull(indexMap);
#if[longOrDouble]
if (species.length() == 1) {
return $abstractvectortype$.fromArray(species, a, i + indexMap[j]);
}
-#end[longOrDouble]
+#end[longOrDouble]
// Index vector: vix[0:n] = k -> i + indexMap[j + i]
IntVector vix = IntVector.fromArray(species.indexSpecies(), indexMap, j).add(i);
vix = VectorIntrinsics.checkIndex(vix, a.length);
+ return fromArrayWithoutCheck(species, a, i, indexMap, j, vix);
+ }
+
+ @ForceInline
+ @SuppressWarnings("unchecked")
+ static $abstractvectortype$ fromArrayWithoutCheck($Type$Species species, $type$[] a, int i, int[] indexMap, int j, IntVector vix) {
return VectorIntrinsics.loadWithMap((Class<$abstractvectortype$>) species.boxType(), $type$.class, species.length(),
species.indexSpecies().vectorType(), a, Unsafe.ARRAY_$TYPE$_BASE_OFFSET, vix,
a, i, indexMap, j, species,
(c, idx, iMap, idy, s) -> (($Type$Species)s).op(n -> c[idx + iMap[idy+n]]));
}
-
#end[byteOrShort]
+
/**
* Loads a vector from an array using indexes obtained from an index
* map and using a mask.
* <p>
* For each vector lane, where {@code N} is the vector lane index,
@@ -310,14 +324,28 @@
public static $abstractvectortype$ fromArray($Type$Species species, $type$[] a, int i, Mask<$Boxtype$> m, int[] indexMap, int j) {
return species.op(m, n -> a[i + indexMap[j + n]]);
}
#else[byteOrShort]
@ForceInline
- @SuppressWarnings("unchecked")
public static $abstractvectortype$ fromArray($Type$Species species, $type$[] a, int i, Mask<$Boxtype$> m, int[] indexMap, int j) {
- // @@@ This can result in out of bounds errors for unset mask lanes
- return zero(species).blend(fromArray(species, a, i, indexMap, j), m);
+ Objects.requireNonNull(a);
+ Objects.requireNonNull(indexMap);
+
+#if[longOrDouble]
+ if (species.length() == 1) {
+ return fromArray(species, a, i + indexMap[j], m);
+ }
+
+#end[longOrDouble]
+ // Index vector: vix[0:n] = k -> i + indexMap[j + i]
+ IntVector vix = IntVector.fromArray(species.indexSpecies(), indexMap, j).add(i);
+
+ if (vix.lessThan(0).anyTrue() || vix.greaterThanEq(a.length).anyTrue()) {
+ return species.op(m, n -> a[i + indexMap[j+n]]);
+ } else {
+ return zero(species).blend(fromArrayWithoutCheck(species, a, i, indexMap, j, vix), m);
+ }
}
#end[byteOrShort]
/**
< prev index next >