1 /* 2 * Copyright (c) 2017, Oracle and/or its affiliates. All rights reserved. 3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 4 * 5 * This code is free software; you can redistribute it and/or modify it 6 * under the terms of the GNU General Public License version 2 only, as 7 * published by the Free Software Foundation. Oracle designates this 8 * particular file as subject to the "Classpath" exception as provided 9 * by Oracle in the LICENSE file that accompanied this code. 10 * 11 * This code is distributed in the hope that it will be useful, but WITHOUT 12 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or 13 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License 14 * version 2 for more details (a copy is included in the LICENSE file that 15 * accompanied this code). 16 * 17 * You should have received a copy of the GNU General Public License version 18 * 2 along with this work; if not, write to the Free Software Foundation, 19 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. 20 * 21 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA 22 * or visit www.oracle.com if you need additional information or have 23 * questions. 24 */ 25 package jdk.incubator.vector; 26 27 import java.nio.ByteBuffer; 28 import java.util.Arrays; 29 import java.util.Objects; 30 import jdk.internal.vm.annotation.ForceInline; 31 import static jdk.incubator.vector.VectorIntrinsics.*; 32 33 @SuppressWarnings("cast") 34 final class Short256Vector extends ShortVector<Shapes.S256Bit> { 35 static final Short256Species SPECIES = new Short256Species(); 36 37 static final Short256Vector ZERO = new Short256Vector(); 38 39 static final int LENGTH = SPECIES.length(); 40 41 private final short[] vec; // Don't access directly, use getElements() instead. 42 43 private short[] getElements() { 44 return VectorIntrinsics.maybeRebox(this).vec; 45 } 46 47 Short256Vector() { 48 vec = new short[SPECIES.length()]; 49 } 50 51 Short256Vector(short[] v) { 52 vec = v; 53 } 54 55 @Override 56 public int length() { return LENGTH; } 57 58 // Unary operator 59 60 @Override 61 Short256Vector uOp(FUnOp f) { 62 short[] vec = getElements(); 63 short[] res = new short[length()]; 64 for (int i = 0; i < length(); i++) { 65 res[i] = f.apply(i, vec[i]); 66 } 67 return new Short256Vector(res); 68 } 69 70 @Override 71 Short256Vector uOp(Mask<Short, Shapes.S256Bit> o, FUnOp f) { 72 short[] vec = getElements(); 73 short[] res = new short[length()]; 74 boolean[] mbits = ((Short256Mask)o).getBits(); 75 for (int i = 0; i < length(); i++) { 76 res[i] = mbits[i] ? f.apply(i, vec[i]) : vec[i]; 77 } 78 return new Short256Vector(res); 79 } 80 81 // Binary operator 82 83 @Override 84 Short256Vector bOp(Vector<Short, Shapes.S256Bit> o, FBinOp f) { 85 short[] res = new short[length()]; 86 short[] vec1 = this.getElements(); 87 short[] vec2 = ((Short256Vector)o).getElements(); 88 for (int i = 0; i < length(); i++) { 89 res[i] = f.apply(i, vec1[i], vec2[i]); 90 } 91 return new Short256Vector(res); 92 } 93 94 @Override 95 Short256Vector bOp(Vector<Short, Shapes.S256Bit> o1, Mask<Short, Shapes.S256Bit> o2, FBinOp f) { 96 short[] res = new short[length()]; 97 short[] vec1 = this.getElements(); 98 short[] vec2 = ((Short256Vector)o1).getElements(); 99 boolean[] mbits = ((Short256Mask)o2).getBits(); 100 for (int i = 0; i < length(); i++) { 101 res[i] = mbits[i] ? f.apply(i, vec1[i], vec2[i]) : vec1[i]; 102 } 103 return new Short256Vector(res); 104 } 105 106 // Trinary operator 107 108 @Override 109 Short256Vector tOp(Vector<Short, Shapes.S256Bit> o1, Vector<Short, Shapes.S256Bit> o2, FTriOp f) { 110 short[] res = new short[length()]; 111 short[] vec1 = this.getElements(); 112 short[] vec2 = ((Short256Vector)o1).getElements(); 113 short[] vec3 = ((Short256Vector)o2).getElements(); 114 for (int i = 0; i < length(); i++) { 115 res[i] = f.apply(i, vec1[i], vec2[i], vec3[i]); 116 } 117 return new Short256Vector(res); 118 } 119 120 @Override 121 Short256Vector tOp(Vector<Short, Shapes.S256Bit> o1, Vector<Short, Shapes.S256Bit> o2, Mask<Short, Shapes.S256Bit> o3, FTriOp f) { 122 short[] res = new short[length()]; 123 short[] vec1 = getElements(); 124 short[] vec2 = ((Short256Vector)o1).getElements(); 125 short[] vec3 = ((Short256Vector)o2).getElements(); 126 boolean[] mbits = ((Short256Mask)o3).getBits(); 127 for (int i = 0; i < length(); i++) { 128 res[i] = mbits[i] ? f.apply(i, vec1[i], vec2[i], vec3[i]) : vec1[i]; 129 } 130 return new Short256Vector(res); 131 } 132 133 @Override 134 short rOp(short v, FBinOp f) { 135 short[] vec = getElements(); 136 for (int i = 0; i < length(); i++) { 137 v = f.apply(i, v, vec[i]); 138 } 139 return v; 140 } 141 142 // Binary operations with scalars 143 144 @Override 145 @ForceInline 146 public ShortVector<Shapes.S256Bit> add(short o) { 147 return add(SPECIES.broadcast(o)); 148 } 149 150 @Override 151 @ForceInline 152 public ShortVector<Shapes.S256Bit> add(short o, Mask<Short,Shapes.S256Bit> m) { 153 return add(SPECIES.broadcast(o), m); 154 } 155 156 @Override 157 @ForceInline 158 public ShortVector<Shapes.S256Bit> addSaturate(short o) { 159 return addSaturate(SPECIES.broadcast(o)); 160 } 161 162 @Override 163 @ForceInline 164 public ShortVector<Shapes.S256Bit> addSaturate(short o, Mask<Short,Shapes.S256Bit> m) { 165 return addSaturate(SPECIES.broadcast(o), m); 166 } 167 168 @Override 169 @ForceInline 170 public ShortVector<Shapes.S256Bit> sub(short o) { 171 return sub(SPECIES.broadcast(o)); 172 } 173 174 @Override 175 @ForceInline 176 public ShortVector<Shapes.S256Bit> sub(short o, Mask<Short,Shapes.S256Bit> m) { 177 return sub(SPECIES.broadcast(o), m); 178 } 179 180 @Override 181 @ForceInline 182 public ShortVector<Shapes.S256Bit> subSaturate(short o) { 183 return subSaturate(SPECIES.broadcast(o)); 184 } 185 186 @Override 187 @ForceInline 188 public ShortVector<Shapes.S256Bit> subSaturate(short o, Mask<Short,Shapes.S256Bit> m) { 189 return subSaturate(SPECIES.broadcast(o), m); 190 } 191 192 @Override 193 @ForceInline 194 public ShortVector<Shapes.S256Bit> mul(short o) { 195 return mul(SPECIES.broadcast(o)); 196 } 197 198 @Override 199 @ForceInline 200 public ShortVector<Shapes.S256Bit> mul(short o, Mask<Short,Shapes.S256Bit> m) { 201 return mul(SPECIES.broadcast(o), m); 202 } 203 204 @Override 205 @ForceInline 206 public ShortVector<Shapes.S256Bit> min(short o) { 207 return min(SPECIES.broadcast(o)); 208 } 209 210 @Override 211 @ForceInline 212 public ShortVector<Shapes.S256Bit> max(short o) { 213 return max(SPECIES.broadcast(o)); 214 } 215 216 @Override 217 @ForceInline 218 public Mask<Short, Shapes.S256Bit> equal(short o) { 219 return equal(SPECIES.broadcast(o)); 220 } 221 222 @Override 223 @ForceInline 224 public Mask<Short, Shapes.S256Bit> notEqual(short o) { 225 return notEqual(SPECIES.broadcast(o)); 226 } 227 228 @Override 229 @ForceInline 230 public Mask<Short, Shapes.S256Bit> lessThan(short o) { 231 return lessThan(SPECIES.broadcast(o)); 232 } 233 234 @Override 235 @ForceInline 236 public Mask<Short, Shapes.S256Bit> lessThanEq(short o) { 237 return lessThanEq(SPECIES.broadcast(o)); 238 } 239 240 @Override 241 @ForceInline 242 public Mask<Short, Shapes.S256Bit> greaterThan(short o) { 243 return greaterThan(SPECIES.broadcast(o)); 244 } 245 246 @Override 247 @ForceInline 248 public Mask<Short, Shapes.S256Bit> greaterThanEq(short o) { 249 return greaterThanEq(SPECIES.broadcast(o)); 250 } 251 252 @Override 253 @ForceInline 254 public ShortVector<Shapes.S256Bit> blend(short o, Mask<Short,Shapes.S256Bit> m) { 255 return blend(SPECIES.broadcast(o), m); 256 } 257 258 259 @Override 260 @ForceInline 261 public ShortVector<Shapes.S256Bit> and(short o) { 262 return and(SPECIES.broadcast(o)); 263 } 264 265 @Override 266 @ForceInline 267 public ShortVector<Shapes.S256Bit> and(short o, Mask<Short,Shapes.S256Bit> m) { 268 return and(SPECIES.broadcast(o), m); 269 } 270 271 @Override 272 @ForceInline 273 public ShortVector<Shapes.S256Bit> or(short o) { 274 return or(SPECIES.broadcast(o)); 275 } 276 277 @Override 278 @ForceInline 279 public ShortVector<Shapes.S256Bit> or(short o, Mask<Short,Shapes.S256Bit> m) { 280 return or(SPECIES.broadcast(o), m); 281 } 282 283 @Override 284 @ForceInline 285 public ShortVector<Shapes.S256Bit> xor(short o) { 286 return xor(SPECIES.broadcast(o)); 287 } 288 289 @Override 290 @ForceInline 291 public ShortVector<Shapes.S256Bit> xor(short o, Mask<Short,Shapes.S256Bit> m) { 292 return xor(SPECIES.broadcast(o), m); 293 } 294 295 296 // Unary operations 297 298 299 300 @Override 301 @ForceInline 302 public Short256Vector not() { 303 return (Short256Vector) VectorIntrinsics.unaryOp( 304 VECTOR_OP_NOT, Short256Vector.class, short.class, LENGTH, 305 this, 306 v1 -> ((Short256Vector)v1).uOp((i, a) -> (short) ~a)); 307 } 308 // Binary operations 309 310 @Override 311 @ForceInline 312 public Short256Vector add(Vector<Short,Shapes.S256Bit> o) { 313 Objects.requireNonNull(o); 314 Short256Vector v = (Short256Vector)o; 315 return (Short256Vector) VectorIntrinsics.binaryOp( 316 VECTOR_OP_ADD, Short256Vector.class, short.class, LENGTH, 317 this, v, 318 (v1, v2) -> ((Short256Vector)v1).bOp(v2, (i, a, b) -> (short)(a + b))); 319 } 320 321 @Override 322 @ForceInline 323 public Short256Vector sub(Vector<Short,Shapes.S256Bit> o) { 324 Objects.requireNonNull(o); 325 Short256Vector v = (Short256Vector)o; 326 return (Short256Vector) VectorIntrinsics.binaryOp( 327 VECTOR_OP_SUB, Short256Vector.class, short.class, LENGTH, 328 this, v, 329 (v1, v2) -> ((Short256Vector)v1).bOp(v2, (i, a, b) -> (short)(a - b))); 330 } 331 332 @Override 333 @ForceInline 334 public Short256Vector mul(Vector<Short,Shapes.S256Bit> o) { 335 Objects.requireNonNull(o); 336 Short256Vector v = (Short256Vector)o; 337 return (Short256Vector) VectorIntrinsics.binaryOp( 338 VECTOR_OP_MUL, Short256Vector.class, short.class, LENGTH, 339 this, v, 340 (v1, v2) -> ((Short256Vector)v1).bOp(v2, (i, a, b) -> (short)(a * b))); 341 } 342 343 344 345 @Override 346 @ForceInline 347 public Short256Vector and(Vector<Short,Shapes.S256Bit> o) { 348 Objects.requireNonNull(o); 349 Short256Vector v = (Short256Vector)o; 350 return (Short256Vector) VectorIntrinsics.binaryOp( 351 VECTOR_OP_AND, Short256Vector.class, short.class, LENGTH, 352 this, v, 353 (v1, v2) -> ((Short256Vector)v1).bOp(v2, (i, a, b) -> (short)(a & b))); 354 } 355 356 @Override 357 @ForceInline 358 public Short256Vector or(Vector<Short,Shapes.S256Bit> o) { 359 Objects.requireNonNull(o); 360 Short256Vector v = (Short256Vector)o; 361 return (Short256Vector) VectorIntrinsics.binaryOp( 362 VECTOR_OP_OR, Short256Vector.class, short.class, LENGTH, 363 this, v, 364 (v1, v2) -> ((Short256Vector)v1).bOp(v2, (i, a, b) -> (short)(a | b))); 365 } 366 367 @Override 368 @ForceInline 369 public Short256Vector xor(Vector<Short,Shapes.S256Bit> o) { 370 Objects.requireNonNull(o); 371 Short256Vector v = (Short256Vector)o; 372 return (Short256Vector) VectorIntrinsics.binaryOp( 373 VECTOR_OP_XOR, Short256Vector.class, short.class, LENGTH, 374 this, v, 375 (v1, v2) -> ((Short256Vector)v1).bOp(v2, (i, a, b) -> (short)(a ^ b))); 376 } 377 378 @Override 379 @ForceInline 380 public Short256Vector and(Vector<Short,Shapes.S256Bit> v, Mask<Short, Shapes.S256Bit> m) { 381 return blend(and(v), m); 382 } 383 384 @Override 385 @ForceInline 386 public Short256Vector or(Vector<Short,Shapes.S256Bit> v, Mask<Short, Shapes.S256Bit> m) { 387 return blend(or(v), m); 388 } 389 390 @Override 391 @ForceInline 392 public Short256Vector xor(Vector<Short,Shapes.S256Bit> v, Mask<Short, Shapes.S256Bit> m) { 393 return blend(xor(v), m); 394 } 395 396 @Override 397 @ForceInline 398 public Short256Vector shiftL(int s) { 399 return (Short256Vector) VectorIntrinsics.broadcastInt( 400 VECTOR_OP_LSHIFT, Short256Vector.class, short.class, LENGTH, 401 this, s, 402 (v, i) -> v.uOp((__, a) -> (short) (a << i))); 403 } 404 405 @Override 406 @ForceInline 407 public Short256Vector shiftR(int s) { 408 return (Short256Vector) VectorIntrinsics.broadcastInt( 409 VECTOR_OP_URSHIFT, Short256Vector.class, short.class, LENGTH, 410 this, s, 411 (v, i) -> v.uOp((__, a) -> (short) (a >>> i))); 412 } 413 414 @Override 415 @ForceInline 416 public Short256Vector aShiftR(int s) { 417 return (Short256Vector) VectorIntrinsics.broadcastInt( 418 VECTOR_OP_RSHIFT, Short256Vector.class, short.class, LENGTH, 419 this, s, 420 (v, i) -> v.uOp((__, a) -> (short) (a >> i))); 421 } 422 423 // Ternary operations 424 425 426 // Type specific horizontal reductions 427 428 @Override 429 @ForceInline 430 public short addAll() { 431 return (short) VectorIntrinsics.reductionCoerced( 432 VECTOR_OP_ADD, Short256Vector.class, short.class, LENGTH, 433 this, 434 v -> (long) v.rOp((short) 0, (i, a, b) -> (short) (a + b))); 435 } 436 437 @Override 438 @ForceInline 439 public short andAll() { 440 return (short) VectorIntrinsics.reductionCoerced( 441 VECTOR_OP_AND, Short256Vector.class, short.class, LENGTH, 442 this, 443 v -> (long) v.rOp((short) -1, (i, a, b) -> (short) (a & b))); 444 } 445 446 @Override 447 @ForceInline 448 public short subAll() { 449 return (short) VectorIntrinsics.reductionCoerced( 450 VECTOR_OP_SUB, Short256Vector.class, short.class, LENGTH, 451 this, 452 v -> (long) v.rOp((short) 0, (i, a, b) -> (short) (a - b))); 453 } 454 455 // Memory operations 456 457 @Override 458 @ForceInline 459 public void intoArray(short[] a, int ix) { 460 Objects.requireNonNull(a); 461 ix = VectorIntrinsics.checkIndex(ix, a.length, LENGTH); 462 VectorIntrinsics.store(Short256Vector.class, short.class, LENGTH, 463 a, ix, this, 464 (arr, idx, v) -> v.forEach((i, a_) -> ((short[])arr)[idx + i] = a_)); 465 } 466 467 @Override 468 @ForceInline 469 public void intoArray(short[] a, int ax, Mask<Short, Shapes.S256Bit> m) { 470 // TODO: use better default impl: forEach(m, (i, a_) -> a[ax + i] = a_); 471 Short256Vector oldVal = SPECIES.fromArray(a, ax); 472 Short256Vector newVal = oldVal.blend(this, m); 473 newVal.intoArray(a, ax); 474 } 475 476 // 477 478 @Override 479 public String toString() { 480 return Arrays.toString(getElements()); 481 } 482 483 @Override 484 public boolean equals(Object o) { 485 if (this == o) return true; 486 if (o == null || this.getClass() != o.getClass()) return false; 487 488 Short256Vector that = (Short256Vector) o; 489 return Arrays.equals(this.getElements(), that.getElements()); 490 } 491 492 @Override 493 public int hashCode() { 494 return Arrays.hashCode(vec); 495 } 496 497 // Binary test 498 499 @Override 500 Short256Mask bTest(Vector<Short, Shapes.S256Bit> o, FBinTest f) { 501 short[] vec1 = getElements(); 502 short[] vec2 = ((Short256Vector)o).getElements(); 503 boolean[] bits = new boolean[length()]; 504 for (int i = 0; i < length(); i++){ 505 bits[i] = f.apply(i, vec1[i], vec2[i]); 506 } 507 return new Short256Mask(bits); 508 } 509 510 // Comparisons 511 512 @Override 513 @ForceInline 514 public Short256Mask equal(Vector<Short, Shapes.S256Bit> o) { 515 Objects.requireNonNull(o); 516 Short256Vector v = (Short256Vector)o; 517 518 return (Short256Mask) VectorIntrinsics.compare( 519 BT_eq, Short256Vector.class, Short256Mask.class, short.class, LENGTH, 520 this, v, 521 (v1, v2) -> v1.bTest(v2, (i, a, b) -> a == b)); 522 } 523 524 @Override 525 @ForceInline 526 public Short256Mask notEqual(Vector<Short, Shapes.S256Bit> o) { 527 Objects.requireNonNull(o); 528 Short256Vector v = (Short256Vector)o; 529 530 return (Short256Mask) VectorIntrinsics.compare( 531 BT_ne, Short256Vector.class, Short256Mask.class, short.class, LENGTH, 532 this, v, 533 (v1, v2) -> v1.bTest(v2, (i, a, b) -> a != b)); 534 } 535 536 @Override 537 @ForceInline 538 public Short256Mask lessThan(Vector<Short, Shapes.S256Bit> o) { 539 Objects.requireNonNull(o); 540 Short256Vector v = (Short256Vector)o; 541 542 return (Short256Mask) VectorIntrinsics.compare( 543 BT_lt, Short256Vector.class, Short256Mask.class, short.class, LENGTH, 544 this, v, 545 (v1, v2) -> v1.bTest(v2, (i, a, b) -> a < b)); 546 } 547 548 @Override 549 @ForceInline 550 public Short256Mask lessThanEq(Vector<Short, Shapes.S256Bit> o) { 551 Objects.requireNonNull(o); 552 Short256Vector v = (Short256Vector)o; 553 554 return (Short256Mask) VectorIntrinsics.compare( 555 BT_le, Short256Vector.class, Short256Mask.class, short.class, LENGTH, 556 this, v, 557 (v1, v2) -> v1.bTest(v2, (i, a, b) -> a <= b)); 558 } 559 560 @Override 561 @ForceInline 562 public Short256Mask greaterThan(Vector<Short, Shapes.S256Bit> o) { 563 Objects.requireNonNull(o); 564 Short256Vector v = (Short256Vector)o; 565 566 return (Short256Mask) VectorIntrinsics.compare( 567 BT_gt, Short256Vector.class, Short256Mask.class, short.class, LENGTH, 568 this, v, 569 (v1, v2) -> v1.bTest(v2, (i, a, b) -> a > b)); 570 } 571 572 @Override 573 @ForceInline 574 public Short256Mask greaterThanEq(Vector<Short, Shapes.S256Bit> o) { 575 Objects.requireNonNull(o); 576 Short256Vector v = (Short256Vector)o; 577 578 return (Short256Mask) VectorIntrinsics.compare( 579 BT_ge, Short256Vector.class, Short256Mask.class, short.class, LENGTH, 580 this, v, 581 (v1, v2) -> v1.bTest(v2, (i, a, b) -> a >= b)); 582 } 583 584 // Foreach 585 586 @Override 587 void forEach(FUnCon f) { 588 short[] vec = getElements(); 589 for (int i = 0; i < length(); i++) { 590 f.apply(i, vec[i]); 591 } 592 } 593 594 @Override 595 void forEach(Mask<Short, Shapes.S256Bit> o, FUnCon f) { 596 boolean[] mbits = ((Short256Mask)o).getBits(); 597 forEach((i, a) -> { 598 if (mbits[i]) { f.apply(i, a); } 599 }); 600 } 601 602 603 604 @Override 605 public Short256Vector rotateEL(int j) { 606 short[] vec = getElements(); 607 short[] res = new short[length()]; 608 for (int i = 0; i < length(); i++){ 609 res[(j + i) % length()] = vec[i]; 610 } 611 return new Short256Vector(res); 612 } 613 614 @Override 615 public Short256Vector rotateER(int j) { 616 short[] vec = getElements(); 617 short[] res = new short[length()]; 618 for (int i = 0; i < length(); i++){ 619 int z = i - j; 620 if(j < 0) { 621 res[length() + z] = vec[i]; 622 } else { 623 res[z] = vec[i]; 624 } 625 } 626 return new Short256Vector(res); 627 } 628 629 @Override 630 public Short256Vector shiftEL(int j) { 631 short[] vec = getElements(); 632 short[] res = new short[length()]; 633 for (int i = 0; i < length() - j; i++) { 634 res[i] = vec[i + j]; 635 } 636 return new Short256Vector(res); 637 } 638 639 @Override 640 public Short256Vector shiftER(int j) { 641 short[] vec = getElements(); 642 short[] res = new short[length()]; 643 for (int i = 0; i < length() - j; i++){ 644 res[i + j] = vec[i]; 645 } 646 return new Short256Vector(res); 647 } 648 649 @Override 650 public Short256Vector shuffle(Vector<Short, Shapes.S256Bit> o, Shuffle<Short, Shapes.S256Bit> s) { 651 Short256Vector v = (Short256Vector) o; 652 return uOp((i, a) -> { 653 short[] vec = this.getElements(); 654 int e = s.getElement(i); 655 if(e >= 0 && e < length()) { 656 //from this 657 return vec[e]; 658 } else if(e < length() * 2) { 659 //from o 660 return v.getElements()[e - length()]; 661 } else { 662 throw new ArrayIndexOutOfBoundsException("Bad reordering for shuffle"); 663 } 664 }); 665 } 666 667 @Override 668 public Short256Vector swizzle(Shuffle<Short, Shapes.S256Bit> s) { 669 return uOp((i, a) -> { 670 short[] vec = this.getElements(); 671 int e = s.getElement(i); 672 if(e >= 0 && e < length()) { 673 return vec[e]; 674 } else { 675 throw new ArrayIndexOutOfBoundsException("Bad reordering for shuffle"); 676 } 677 }); 678 } 679 680 @Override 681 @ForceInline 682 public Short256Vector blend(Vector<Short, Shapes.S256Bit> o1, Mask<Short, Shapes.S256Bit> o2) { 683 Objects.requireNonNull(o1); 684 Objects.requireNonNull(o2); 685 Short256Vector v = (Short256Vector)o1; 686 Short256Mask m = (Short256Mask)o2; 687 688 return (Short256Vector) VectorIntrinsics.blend( 689 Short256Vector.class, Short256Mask.class, short.class, LENGTH, 690 this, v, m, 691 (v1, v2, m_) -> v1.bOp(v2, (i, a, b) -> m_.getElement(i) ? b : a)); 692 } 693 694 // Accessors 695 696 @Override 697 public short get(int i) { 698 short[] vec = getElements(); 699 return vec[i]; 700 } 701 702 @Override 703 public Short256Vector with(int i, short e) { 704 short[] res = vec.clone(); 705 res[i] = e; 706 return new Short256Vector(res); 707 } 708 709 // Mask 710 711 static final class Short256Mask extends AbstractMask<Short, Shapes.S256Bit> { 712 static final Short256Mask TRUE_MASK = new Short256Mask(true); 713 static final Short256Mask FALSE_MASK = new Short256Mask(false); 714 715 // FIXME: was temporarily put here to simplify rematerialization support in the JVM 716 private final boolean[] bits; // Don't access directly, use getBits() instead. 717 718 public Short256Mask(boolean[] bits) { 719 this(bits, 0); 720 } 721 722 public Short256Mask(boolean[] bits, int i) { 723 this.bits = Arrays.copyOfRange(bits, i, i + species().length()); 724 } 725 726 public Short256Mask(boolean val) { 727 boolean[] bits = new boolean[species().length()]; 728 Arrays.fill(bits, val); 729 this.bits = bits; 730 } 731 732 boolean[] getBits() { 733 return VectorIntrinsics.maybeRebox(this).bits; 734 } 735 736 @Override 737 Short256Mask uOp(MUnOp f) { 738 boolean[] res = new boolean[species().length()]; 739 boolean[] bits = getBits(); 740 for (int i = 0; i < species().length(); i++) { 741 res[i] = f.apply(i, bits[i]); 742 } 743 return new Short256Mask(res); 744 } 745 746 @Override 747 Short256Mask bOp(Mask<Short, Shapes.S256Bit> o, MBinOp f) { 748 boolean[] res = new boolean[species().length()]; 749 boolean[] bits = getBits(); 750 boolean[] mbits = ((Short256Mask)o).getBits(); 751 for (int i = 0; i < species().length(); i++) { 752 res[i] = f.apply(i, bits[i], mbits[i]); 753 } 754 return new Short256Mask(res); 755 } 756 757 @Override 758 public Short256Species species() { 759 return SPECIES; 760 } 761 762 @Override 763 public Short256Vector toVector() { 764 short[] res = new short[species().length()]; 765 boolean[] bits = getBits(); 766 for (int i = 0; i < species().length(); i++) { 767 res[i] = (short) (bits[i] ? -1 : 0); 768 } 769 return new Short256Vector(res); 770 } 771 772 @Override 773 @ForceInline 774 @SuppressWarnings("unchecked") 775 public <Z> Mask<Z, Shapes.S256Bit> rebracket(Species<Z, Shapes.S256Bit> species) { 776 Objects.requireNonNull(species); 777 // TODO: check proper element type 778 return VectorIntrinsics.reinterpret( 779 Short256Mask.class, short.class, LENGTH, 780 species.elementType(), species.length(), this, 781 (m, t) -> m.reshape(species) 782 ); 783 } 784 785 // Unary operations 786 787 //Mask<E, S> not(); 788 789 // Binary operations 790 791 @Override 792 @ForceInline 793 public Short256Mask and(Mask<Short,Shapes.S256Bit> o) { 794 Objects.requireNonNull(o); 795 Short256Mask m = (Short256Mask)o; 796 return VectorIntrinsics.binaryOp(VECTOR_OP_AND, Short256Mask.class, short.class, LENGTH, 797 this, m, 798 (m1, m2) -> m1.bOp(m2, (i, a, b) -> a & b)); 799 } 800 801 @Override 802 @ForceInline 803 public Short256Mask or(Mask<Short,Shapes.S256Bit> o) { 804 Objects.requireNonNull(o); 805 Short256Mask m = (Short256Mask)o; 806 return VectorIntrinsics.binaryOp(VECTOR_OP_OR, Short256Mask.class, short.class, LENGTH, 807 this, m, 808 (m1, m2) -> m1.bOp(m2, (i, a, b) -> a | b)); 809 } 810 811 // Reductions 812 813 @Override 814 @ForceInline 815 public boolean anyTrue() { 816 return VectorIntrinsics.test(COND_notZero, Short256Mask.class, short.class, LENGTH, 817 this, this, 818 (m1, m2) -> super.anyTrue()); 819 } 820 821 @Override 822 @ForceInline 823 public boolean allTrue() { 824 return VectorIntrinsics.test(COND_carrySet, Short256Mask.class, short.class, LENGTH, 825 this, species().maskAllTrue(), 826 (m1, m2) -> super.allTrue()); 827 } 828 } 829 830 // Shuffle 831 832 static final class Short256Shuffle extends AbstractShuffle<Short, Shapes.S256Bit> { 833 static final IntVector.IntSpecies<Shapes.S256Bit> INT_SPECIES = IntVector.speciesInstance(Shapes.S_256_BIT); 834 835 public Short256Shuffle(int[] reorder) { 836 super(reorder); 837 } 838 839 public Short256Shuffle(int[] reorder, int i) { 840 super(reorder, i); 841 } 842 843 @Override 844 public Short256Species species() { 845 return SPECIES; 846 } 847 848 @Override 849 public IntVector.IntSpecies<Shapes.S256Bit> intSpecies() { 850 return INT_SPECIES; 851 } 852 } 853 854 // Species 855 856 @Override 857 public Short256Species species() { 858 return SPECIES; 859 } 860 861 static final class Short256Species extends ShortSpecies<Shapes.S256Bit> { 862 static final int BIT_SIZE = Shapes.S_256_BIT.bitSize(); 863 864 static final int LENGTH = BIT_SIZE / Short.SIZE; 865 866 @Override 867 public String toString() { 868 StringBuilder sb = new StringBuilder("Shape["); 869 sb.append(bitSize()).append(" bits, "); 870 sb.append(length()).append(" ").append(short.class.getSimpleName()).append("s x "); 871 sb.append(elementSize()).append(" bits"); 872 sb.append("]"); 873 return sb.toString(); 874 } 875 876 @Override 877 @ForceInline 878 public int bitSize() { 879 return BIT_SIZE; 880 } 881 882 @Override 883 @ForceInline 884 public int length() { 885 return LENGTH; 886 } 887 888 @Override 889 @ForceInline 890 public Class<Short> elementType() { 891 return short.class; 892 } 893 894 @Override 895 @ForceInline 896 public int elementSize() { 897 return Short.SIZE; 898 } 899 900 @Override 901 @ForceInline 902 public Shapes.S256Bit shape() { 903 return Shapes.S_256_BIT; 904 } 905 906 @Override 907 Short256Vector op(FOp f) { 908 short[] res = new short[length()]; 909 for (int i = 0; i < length(); i++) { 910 res[i] = f.apply(i); 911 } 912 return new Short256Vector(res); 913 } 914 915 @Override 916 Short256Vector op(Mask<Short, Shapes.S256Bit> o, FOp f) { 917 short[] res = new short[length()]; 918 boolean[] mbits = ((Short256Mask)o).getBits(); 919 for (int i = 0; i < length(); i++) { 920 if (mbits[i]) { 921 res[i] = f.apply(i); 922 } 923 } 924 return new Short256Vector(res); 925 } 926 927 // Factories 928 929 @Override 930 public Short256Mask maskFromValues(boolean... bits) { 931 return new Short256Mask(bits); 932 } 933 934 @Override 935 public Short256Mask maskFromArray(boolean[] bits, int i) { 936 return new Short256Mask(bits, i); 937 } 938 939 @Override 940 public Short256Shuffle shuffleFromValues(int... ixs) { 941 return new Short256Shuffle(ixs); 942 } 943 944 @Override 945 public Short256Shuffle shuffleFromArray(int[] ixs, int i) { 946 return new Short256Shuffle(ixs, i); 947 } 948 949 @Override 950 public Short256Shuffle shuffleFromVector(Vector<Integer, Shapes.S256Bit> v) { 951 int[] a = ((IntVector<Shapes.S256Bit>) v).toArray(); 952 return new Short256Shuffle(a, 0); 953 } 954 955 @Override 956 @ForceInline 957 public Short256Vector zero() { 958 return VectorIntrinsics.broadcastCoerced(Short256Vector.class, short.class, LENGTH, 959 0, 960 (z -> ZERO)); 961 } 962 963 @Override 964 @ForceInline 965 public Short256Vector broadcast(short e) { 966 return VectorIntrinsics.broadcastCoerced( 967 Short256Vector.class, short.class, LENGTH, 968 e, 969 ((long bits) -> SPECIES.op(i -> (short)bits))); 970 } 971 972 @Override 973 @ForceInline 974 public Short256Mask maskAllTrue() { 975 return VectorIntrinsics.broadcastCoerced(Short256Mask.class, short.class, LENGTH, 976 (short)-1, 977 (z -> Short256Mask.TRUE_MASK)); 978 } 979 980 @Override 981 @ForceInline 982 public Short256Mask maskAllFalse() { 983 return VectorIntrinsics.broadcastCoerced(Short256Mask.class, short.class, LENGTH, 984 0, 985 (z -> Short256Mask.FALSE_MASK)); 986 } 987 988 @Override 989 @ForceInline 990 public Short256Vector fromArray(short[] a, int ix) { 991 Objects.requireNonNull(a); 992 ix = VectorIntrinsics.checkIndex(ix, a.length, LENGTH); 993 return (Short256Vector) VectorIntrinsics.load(Short256Vector.class, short.class, LENGTH, 994 a, ix, 995 (arr, idx) -> super.fromArray((short[]) arr, idx)); 996 } 997 998 @Override 999 @ForceInline 1000 public Short256Vector fromArray(short[] a, int ax, Mask<Short, Shapes.S256Bit> m) { 1001 return zero().blend(fromArray(a, ax), m); // TODO: use better default impl: op(m, i -> a[ax + i]); 1002 } 1003 1004 @Override 1005 @ForceInline 1006 @SuppressWarnings("unchecked") 1007 public <F> Short256Vector rebracket(Vector<F, Shapes.S256Bit> o) { 1008 Objects.requireNonNull(o); 1009 if (o.elementType() == byte.class) { 1010 Byte256Vector so = (Byte256Vector)o; 1011 return VectorIntrinsics.reinterpret( 1012 Byte256Vector.class, byte.class, so.length(), 1013 short.class, LENGTH, so, 1014 (v, t) -> (Short256Vector)reshape(v) 1015 ); 1016 } else if (o.elementType() == short.class) { 1017 Short256Vector so = (Short256Vector)o; 1018 return VectorIntrinsics.reinterpret( 1019 Short256Vector.class, short.class, so.length(), 1020 short.class, LENGTH, so, 1021 (v, t) -> (Short256Vector)reshape(v) 1022 ); 1023 } else if (o.elementType() == int.class) { 1024 Int256Vector so = (Int256Vector)o; 1025 return VectorIntrinsics.reinterpret( 1026 Int256Vector.class, int.class, so.length(), 1027 short.class, LENGTH, so, 1028 (v, t) -> (Short256Vector)reshape(v) 1029 ); 1030 } else if (o.elementType() == long.class) { 1031 Long256Vector so = (Long256Vector)o; 1032 return VectorIntrinsics.reinterpret( 1033 Long256Vector.class, long.class, so.length(), 1034 short.class, LENGTH, so, 1035 (v, t) -> (Short256Vector)reshape(v) 1036 ); 1037 } else if (o.elementType() == float.class) { 1038 Float256Vector so = (Float256Vector)o; 1039 return VectorIntrinsics.reinterpret( 1040 Float256Vector.class, float.class, so.length(), 1041 short.class, LENGTH, so, 1042 (v, t) -> (Short256Vector)reshape(v) 1043 ); 1044 } else if (o.elementType() == double.class) { 1045 Double256Vector so = (Double256Vector)o; 1046 return VectorIntrinsics.reinterpret( 1047 Double256Vector.class, double.class, so.length(), 1048 short.class, LENGTH, so, 1049 (v, t) -> (Short256Vector)reshape(v) 1050 ); 1051 } else { 1052 throw new InternalError("Unimplemented size"); 1053 } 1054 } 1055 1056 @Override 1057 @ForceInline 1058 @SuppressWarnings("unchecked") 1059 public <T extends Shape> Short256Vector resize(Vector<Short, T> o) { 1060 Objects.requireNonNull(o); 1061 if (o.bitSize() == 64) { 1062 Short64Vector so = (Short64Vector)o; 1063 return VectorIntrinsics.reinterpret( 1064 Short64Vector.class, short.class, so.length(), 1065 short.class, LENGTH, so, 1066 (v, t) -> (Short256Vector)reshape(v) 1067 ); 1068 } else if (o.bitSize() == 128) { 1069 Short128Vector so = (Short128Vector)o; 1070 return VectorIntrinsics.reinterpret( 1071 Short128Vector.class, short.class, so.length(), 1072 short.class, LENGTH, so, 1073 (v, t) -> (Short256Vector)reshape(v) 1074 ); 1075 } else if (o.bitSize() == 256) { 1076 Short256Vector so = (Short256Vector)o; 1077 return VectorIntrinsics.reinterpret( 1078 Short256Vector.class, short.class, so.length(), 1079 short.class, LENGTH, so, 1080 (v, t) -> (Short256Vector)reshape(v) 1081 ); 1082 } else if (o.bitSize() == 512) { 1083 Short512Vector so = (Short512Vector)o; 1084 return VectorIntrinsics.reinterpret( 1085 Short512Vector.class, short.class, so.length(), 1086 short.class, LENGTH, so, 1087 (v, t) -> (Short256Vector)reshape(v) 1088 ); 1089 } else { 1090 throw new InternalError("Unimplemented size"); 1091 } 1092 } 1093 } 1094 }